In this post, I demonstrate how to create a simple SignalR application using SignalR open source library. SignalR makes it easy to do real time asynchronous two way communication with server and client.
Open Visual Studio and hit Ctrl+Shift+N to create a new project and click on “ASP.NET Empty Web Application”. I am using Visual Studio 2012 and .Net Framework 4.5.
Then we are going to install SignalR dlls using Nuget Package Manager. Right click the project in solution explorer and click on Manage Nuget Packages as shown below.
Or hit Ctrl+Q and type “Nuget” in the quick launch box and click on the first one as shown below.
Hit Ctrl+E and Search for “SignalR” then Click on Install on the first one which is what we need. Then again install lastest version of jQuery by doing the same thing because SignalR will bring down one or two minor version older.
Hit Ctrl+Shift+A on your keyboard to Add a new class named “myUtilHub.cs” to our solution and add the following code to it.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 | using System; using System.Collections.Generic; using System.Linq; using System.Web; using SignalR.Hubs; using SignalR; using SignalR.Hosting; using SignalR.Infrastructure; using System.Threading; namespace SimpleSignalR { [HubName( "myUtil" )] public class myUtilHub : Hub { public void sendMessage() { while ( true ) { Clients.talk( "The current time is: " + DateTime.Now.ToString()); Thread.Sleep(1000); } } } } |
sendMessage()
. The add code that will talk to our clients will be through Clients class and a dynamic expression which should be a javascript function defined on the individual clients. If you mouseover talk you will see that it is a dynamic expression. The Clients class is available to you when you import SignalR namespace.
Ctrl+Shift+A and add javascript file named
myUtil.js
to solution and add this function in the extend method of myUtil.js
. The $.extend
method of jquery will add properties to our util hub on the client side. You can add as many functions as you want. The server will be able to communicate with these methods via a dynamic expression.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 | /// <reference path="../scripts/jquery-1.8.2.js" /> /// <reference path="../scripts/jquery.signalR-0.5.3.js" /> $( function () { var util = $.connection.myUtil; $.connection.hub.start() .pipe( function () { }).done( function () { util.sendMessage(); }); //extending util hub to add a talk function //you can pass any .Net object into this function and you can access it in javascript. $.extend(util, { talk: function (data) { } }); }); |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 | < html > < head > < title > Hello world. </ title > </ head > < body > < div id = "data" > </ div > < script src="../Scripts/jquery-1.8.2.js"></ script > < script src="../Scripts/jquery.signalR-0.5.3.js"></ script > < script src="../Scripts/jquery.color.js"></ script > < script src="../signalr/hubs"></ script > < script src="myUtil.js"></ script > </ body > </ html > |
1 2 3 4 5 6 7 8 9 | $.extend(util, { talk: function (data) { $dt = $( "#data" ); var ddate = new Date(); $dt.append( "<p> " + data + " " + "</p> " ); } }); |
Right click on demo.html in solution explorer and then click on setup as start page and hit F5 to run the application. You will start seeing the messages as shown below and if you open another browser and type type the same url you will see same output appear in real time. In IE9 check the document mode, it should be to IE9 for this demo to work.
We can pass data to our sendMessage function like
sendMessage("Hello world");
and on the server side we can change our function to accept values from clients like sendMessage(string myvalue)
.
1 2 3 4 5 6 7 8 9 10 11 12 | [HubName( "myUtil" )] public class myUtilHub : Hub { public void sendMessage( string myvalue) { while ( true ) { Clients.talk( myvalue + " , current time is " + DateTime.Now.ToString()); System.Threading.Thread.Sleep(500); } } } |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 | [HubName( "myUtil" )] public class myUtilHub : Hub { public void sendMessage( string myvalue) { var processorCategory = PerformanceCounterCategory.GetCategories() .FirstOrDefault(cat => cat.CategoryName == "Processor" ); var countersInCategory = processorCategory.GetCounters( "_Total" ); while ( true ) { PerformanceCounter perfCounter = countersInCategory.First(cnt => cnt.CounterName == "% Processor Time" ); Clients.talk(perfCounter); System.Threading.Thread.Sleep(500); } } } |
1 2 3 4 5 6 7 | talk: function (data) { $dt = $( "#data" ); var ddate = new Date(); $dt.append( "<p> Processor time Raw Value: " + data.RawValue.toString() + " " + "</p> " ); } |
All looks good but there is a problem here. We don't want to keep scrolling for every new value so we would like to update the UI as the data comes in and I wanted to see if I could do this with the help of Knockout.js or not. So here it goes. First of all follow the step to add a Nuget package and then install "Knockout.js" package and add script reference to our demo.html add bindings to it. Final demo.html
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 | < html > < head > < title > Hello world. </ title > </ head > < body > < div id = "data" > < p > % Processor Time : < strong data-bind = "text: totalTime" ></ strong ></ p > </ div > < script src="../Scripts/jquery-1.8.2.js"></ script > < script src="../Scripts/jquery.signalR-0.5.3.js"></ script > < script src="../Scripts/jquery.color.js"></ script > < script src="../signalr/hubs"></ script > < script src="myUtil.js"></ script > < script src="../Scripts/knockout-2.1.0.js"></ script > </ body > </ html > |
1 2 3 4 5 6 7 8 9 10 11 12 13 | function AppViewModel(mydata){ this .totalTime = ko.observable(mydata.RawValue.toString()); } $.extend(util, { talk: function (data) { //$dt = $("#data"); //var ddate = new Date(); //$dt.append("<p> Processor time Raw Value: " + data.RawValue.toString() + " " + "</p> " ); ko.applyBindings( new AppViewModel(data)); } }); |
Could you please update this to the latest RC version? I can't follow the tutorial properly with the new version...
ReplyDeleteThanks for that simple explanation. I find signalr very interesting. Now I have planned to learn more on signalr from a new book yet to be published at https://leanpub.com/signalr. If anyone is interested you can also get this book. I am sure that I will enjoy learning signalr.
ReplyDelete