Creating Manual Javascript SignalR Client

Introduction

The SignalR automatically creates the JavaScript proxy script, which helps us to create the SignalR client in JavaScript, but sometimes we don't want to use the proxy script or we are not able to use the proxy script.

Example

  1. When the client is not running at the same Server, we want to write the proxy script by itself.
  2. For security reasons, the SignalR Server is configured not to generate the proxy script.
  3. You want to customize your SignalR client and want full control over your implementation etc.

Hence, I am going to explain how you can create the JavaScript SignalR client on your own without using the generated proxy.

I am going to create a weather app. It will be the same as my previous implementation of weather app, but instead of using the generated proxy script, I will write my own.

If you have not checked my previous article about – Creating a weather app, using SignalR, check it out at the link, given below.

Prerequisites

You should have a basic knowledge of the following
  • C#
  • ASP.NET
  • JavaScript
  • jQuery
  • Socket Communication (Not necessary)

Let’s start.

Create a new project

Create a new Web project with the name WeatherAppDemo with .NET framewrok version 4.5. I am using .NET 4.5, because this will let us use the latest SignalR 2.x version.

Please do not change the name because I am going to use this namespace throughout the article.

namespace

Adding signalr Library

  1. Open NuGet Package Manager.

    namespace

  2. Search SignalR in NuGet search and click on First Search Result.

    namespace

    It will install all the libraries needed to create SignalR Application. It will add both the Server library and JavaScript client library.
    You will notice there are many results of SignaR search, so the question will be- what will happen, if you click on others.

    Actually they are separate libraries of SignalR for different purposes but we need the complete package because we are going to create SignalR Server as well as client.

  3. Add new folder in the project with name SignalR.


I am doing this because I want to keep the code related to SignalR to a different folder.

Configuring signalr

  1. Creating hub class
    Add a new class in the SignalR folder with the name ChatHub and paste the code, given below.
    1. using Microsoft.AspNet.SignalR;  
    2. using Microsoft.AspNet.SignalR.Hubs;  
    3. using System;  
    4. using System.Collections.Generic;  
    5. using System.Linq;  
    6. using System.Web;  
    7.   
    8. namespace WeatherAppDemo.SignalR {  
    9.     public class ChatHub: Hub {  
    10.         [HubMethodName("change_weather")]  
    11.         public void ChangeWeather(int temperature) {  
    12.             //Clients is ConnectionContext, it holds the information about all the connection.   
    13.             //Others in 'Clients.Others' is holding the list of all connected user except the caller user   
    14.             //(the user which has called this method).   
    15.             //NotifyUser is a function on the clientside, you will understand it later.   
    16.             Clients.Others.NotifyUser(temperature);  
    17.         }  
    18.     }  
    19. }  
    WHAT WE ARE DOING HERE

    The class ChatHub is inhereting a hub class, that means we are making the ChatHub class act like hub of the communication.

    We have defined a ChangeWeather function, which is taking a parameter temperature and it is calling NotifyUser of the client side with the parameter temperature.

  2. Mapping hubs to the SignalR pipeline
    Add a new class in the SignalR folder with the name StartUp and paste the code, given below, in the StartUp.cs.
    1. using Microsoft.Owin;  
    2. using Owin;  
    3. using System;  
    4. using System.Collections.Generic;  
    5. using System.Linq;  
    6. using System.Web;  
    7. [assembly: OwinStartup(typeof(WeatherAppDemo.SignalR.StartUp))]  
    8. namespace WeatherAppDemo.SignalR {  
    9.     public class StartUp {  
    10.         public void Configuration(IAppBuilder app) {  
    11.             app.MapSignalR();  
    12.         }  
    13.     }  
    14. }  
    WHAT WE ARE DOING HERE.

    1. We are calling owinstartup with the parameter WeatherAppDemo.SignalR.StartUp, which will initialize our StartUp class.
    2. In the StartUp class, we are using app.MapSignalR() – it will map SignalR hubs to the app builder pipeline. Simply, what it does is that it will add the hubs to the SignalR pipeline, so that you can access it with URL. The URL of the SignalR is in the form of- /SignalR.

      e.g abc.com/signalr

      Basically, we are doing two things -- we are first starting the StartUp class and adding the hubs to the SignalR pipeline.

Now, compile the code and append this “/SignalR/hubs” at the URL. You will have some JavaScript code.

If you are able to see JavaScript code, then you have successfully configured a SignalR Server.

namespace

Creating Client

Hence, we need to create two clients, which are-

  • First, who will change the weather?
  • Second, who will receive the notification?

STEP TO CREATE A BASIC JAVASCRIPT CLIENT

  • Create a HTML page.
  • Include jquery.js library into HTML page. (You will find jQuery into the script folder).
  • Include signalr.js library into HTML page.(You will find SignalR into the script folder).
  • Add a script with the src=”/signalr/hubs”. (It is a JavaScript proxy generated by SignalR Server). We are going to write our own code to create the proxy.
  • Write some JS code to talk with Signalr Server (I am going to write this code in the next paragraph).

CREATE CHANGEWEATHER CLIENT

Follow the steps to create a basic JavaScript client and in the last step paste the code, given below, in the script tag.

  1. var SignalrConnection;  
  2. var ChatProxy;  
  3.   
  4. function Connect() {  
  5.     ChatServerUrl = "http://localhost:58416/";  
  6.     var ChatUrl = ChatServerUrl + "signalr";  
  7.     //This will hold the connection to the signalr hub   
  8.     SignalrConnection = $.hubConnection(ChatUrl, {  
  9.         useDefaultPath: false  
  10.     });  
  11.     ChatProxy = SignalrConnection.createHubProxy('ChatHub');  
  12.     //connecting the client to the signalr hub   
  13.     SignalrConnection.start().done(function() {  
  14.             alert("Connected to Signalr Server");  
  15.         })  
  16.         .fail(function() {  
  17.             alert("failed in connecting to the signalr server");  
  18.         })  
  19. }  
  20.   
  21. function ChangeWeather() {  
  22.     //get the temperature from a textfield with id txtTemprature   
  23.     var Temperature = document.getElementById('txtTemperature').value;  
  24.     //calling the ChangeWeather function on the signalr server   
  25.     ChatProxy.invoke('change_weather', Temperature);  
  26. }  
In the code, given above, I have described most of the parts with the comments.

It’s time for our HTML page design; just copy the code, given below.
  1. <body onload="Connect();">  
  2.     <div style="text-align:center;">  
  3.         <input type="text" id="txtTemperature" />  
  4.         <button id="btnChange" onclick="ChangeWeather();">Change Weather</button>  
  5.     </div>  
  6. </body>  
I assume you understand the HTML code, given above, so I am not describing this. Finally, we have created the client, who will change the weather.

CREATE RECIEVEWEATHERNOTIFICATION CLIENT

Follow the steps to create a basic JavaScript client and in the last step, paste the code, given below in the script tag.
  1. var SignalrConnection;  
  2. var ChatProxy;  
  3.   
  4. function Connect() {  
  5.     ChatServerUrl = "http://localhost:58416/";  
  6.     var ChatUrl = ChatServerUrl + "signalr";  
  7.     //This will hold the connection to the signalr hub   
  8.     SignalrConnection = $.hubConnection(ChatUrl, {  
  9.         useDefaultPath: false  
  10.     });  
  11.     ChatProxy = SignalrConnection.createHubProxy('ChatHub');  
  12.     //This will be called by signalr   
  13.     ChatProxy.on("NotifyUser",function (temperature) {   
  14.         $('span').text(temperature);  
  15.     });  
  16.   
  17. //connecting the client to the signalr hub   
  18. SignalrConnection.start().done(function() {  
  19.         alert("Connected to Signalr Server");  
  20.     })  
  21.     .fail(function() {  
  22.         alert("failed in connecting to the signalr server");  
  23.     })  
  24.   
  25. }  
Notice that “NotifyUser” in the code. “SignalrConnection.client.NotifyUser” is a function, which will be called by SignalR Server, so try not to mismatch the word.

Html page design is very simple, check the code, given below.
  1. <div style="text-align:center;">   
  2. Temperature : <span></span> ℃   
  3. </div>   
Now, we have everything that we need. It’s time to check out  what we have made. Perform the steps, given below. 
  • Compile the code.
  • Open the ChangeWeather.html.
  • Open RecieveWeatherNotification in the other tabs (open in multiple tab or multiple Browser).
  • Change the weather in ChangeWeather.html and observe the temperature in the RecieveWeatherNotification.html.

Notice, when you will open RecieveWeatherNotification.html for the first time, there is no temperature, which is not good – I mean there should be some initial temperature. Now, what do we need to do?

  1. We need to keep the temperature in a static variable, so that it will be the same for all the objects of ChatHub.
  2. When the RecieveWeatherNotification.html will be connected to SignalR Server, it will call the SignalR Server to get the current temperature.
  3. We will have to create a function (HubMethod) in Chathub, which will be called by RecieveWeatherNotification.html to get the currenttemperature. The function will call NotifyUser of the client side to set the temperature.

Adding Extra Feature(Making more real)

I have described above, what I am going to do, so just copy the code, given below and update the ChatHub class.

  1. using Microsoft.AspNet.SignalR;  
  2. using Microsoft.AspNet.SignalR.Hubs;  
  3. using System;  
  4. using System.Collections.Generic;  
  5. using System.Linq;  
  6. using System.Web;  
  7. namespace WeatherAppDemo.SignalR {  
  8.     public class ChatHub: Hub {  
  9.         //keeping temperature variable static will make the value temperature   
  10.         //to be stored in memory permanently and will be equal to all the   
  11.         //object of chathub.   
  12.         static int Temperature;  
  13.   
  14.         [HubMethodName("change_weather")]  
  15.         public void ChangeWeather(int temperature) {  
  16.             //change the temperature   
  17.             Temperature = temperature;  
  18.   
  19.             //Clients is ConnectionContext, it holds the information about all   
  20.             //the connection.   
  21.             //Others in 'Clients.Others' is holding the list of all connected   
  22.             //user except the caller user (the user which has called this method)   
  23.   
  24.             //NotifyUser is a function on the clientside, you will understand it   
  25.             //later.   
  26.             Clients.Others.NotifyUser(temperature);  
  27.   
  28.         }  
  29.   
  30.         [HubMethodName("get_weather")]  
  31.         public void GetWeather()  
  32.              {  
  33.                  //pushing the data only to the user which has called this method.   
  34.                 Clients.Caller.NotifyUser(Temperature);  
  35.             }  
  36.   
  37.     }  
  38. }  
Hence, we have updated ChatHub class. Now, let’s call the GetWeather method in client side.

To update RecieveWeatherNotification.html, copy the code, given below and update with previous code.
  1. var SignalrConnection;  
  2. var ChatProxy;  
  3.   
  4. function Connect() {  
  5.     ChatServerUrl = "http://localhost:58416/";  
  6.     var ChatUrl = ChatServerUrl + "signalr";  
  7.     //This will hold the connection to the signalr hub   
  8.     SignalrConnection = $.hubConnection(ChatUrl, {  
  9.         useDefaultPath: false  
  10.     });  
  11.     ChatProxy = SignalrConnection.createHubProxy('ChatHub');  
  12.   
  13.     //This will be called by signalr   
  14.     ChatProxy.on("NotifyUser",function (temperature) {   
  15.         $('span').text(temperature);  
  16.     });  
  17.   
  18. //connecting the client to the signalr hub   
  19. SignalrConnection.start().done(function() {  
  20.         GetWeather();  
  21.         alert("Connected to Signalr Server");  
  22.     })  
  23.     .fail(function() {  
  24.         alert("failed in connecting to the signalr server");  
  25.     })  
  26.   
  27. }  
  28.   
  29. function GetWeather() {  
  30.     //calling the GetWeather function on the signalr server   
  31.     ChatProxy.invoke('get_weather');  
  32. }  
What we have done here?  
  • I have created a method GetWeather, which will call the ChatHubmethod “get_weather”
  • I am calling the GetWeather, when the client is connected to the SignalR.

Hence, compile the code and check out everything.

References

  • https://www.asp.net/signalr/overview/guide-to-the-api/hubs-api-guide-javascript-client

X

Build smarter apps with Machine Learning, Bots, Cognitive Services - Start free.

Start Learning Now