Introduction

Nowadays, due to increase in the amount of information and necessity of achieving data in short time, we need technologies to cover our requirement in this issue. Assume when in stock market prices are changing in each moment, do you think that user should refresh page every moment to inform the last price? Obviously, it is not a reasonable solution for such a problem. Or with increase in producing products and services, we need customer service to help user and buyer, the best and cheaper communication is conversation by chat program. By the same token, we cannot force user to press button for receiving our last message.

SignalR is a real time technology which is using the set of asynchrony library to make a persistence connection between client and server. User can receive last update data from server without traditional way such as refresh page or press button.

In the other hand SignalR uses the below approaches to establish real time web:

1. WebSocket

Websocket is a full duplex protocol and uses http handshaking internally and allow stream of messages flow on top of TCP. It supports: Google Chrome (> 16) Fire Fox (> 11) IE (> 10) Win IIS (>8.0). Due to encrypt message and full duplex, websocket is the best solution and at first signalR checks both web server and client server whether they support websocket or not.

Simplex Communication

It just spreads in one way when one point just broadcasts while another point just can listen without sending message, such as television and radio.

Half duplex

One point sends message and in this moment another point cannot send message and should wait until the first point finishes its transmission and then send its message, it is just a one communication line at a time, such as old wireless device walkie-talkie and HTTP protocol.

Full duplex

Both points can send and receive message at a time simultaneously, there is no need to wait until other point finishes its transmission such as telephones and websocket protocol.

2. Server Sent Events (SSE)

The next choice for signalr is server sent event, because of persistence communication between server and client. In this approach, communication does not disconnect and last data from server will update automatically and transmit to client via HTTP connection. EventSource is part of HTML5 technology.

3. Forever Frame

When client sends request to server, then server sends a hidden iframe as chunked block to client so this iframe is responsible to keep connection between client and server forever. Whenever server changes data, then send data as script tag to client (hidden iframe) and these scripts will be received sequentially.

4. Polling

Client sends request to server and server responses immediately but after that, server disconnects connection so again for establishing communication between server and client, we should wait for next request from client. To solve this problem, we have to set timeout manually and for each 10 seconds client sends request to server to check new modification in server side and gets last update data. Polling uses resources and it is not an economic solution.

5. Long Polling

Client sends request to server and server responds immediately and this connection remains until a specific time and during this period clients do not have to send explicit request to server while in polling client has to send explicit request to server during timeout. Comet programming covers this concept.

Briefly SignalR library chooses one type of transmit data between client and server, its priority is websocket, server sent event, long polling and forever iframe. There are two classes inside this library as follows:

1. Persistentconnection

It is low level so it is complex and needs more configuration but in return gives more facility to handle class personally.

2. Hub

It is high level and more popular to use it.

How to implement simple chat scenario by the aid of signalr and hub class?

My aim is just to issue a random scenario for involving signalr. You can use it for your personally scenario and I just follow the below steps to make challenge with server (hub class) and client side and illustrate how client send request and server respond? How they interact with each other?

Scenario Description

I want to establish an application for customer service department. There are some administrations that are responsible to help client and on the other side there are clients who ask question and need help.

Assume two admins are online and connect to chat service and the first client comes to ask a question, so system connects the first client to first free admin and for second client this story will repeat, but third client gives alarm from system that there is no admin to help. Whenever first client disconnects, the first admin becomes free.

My contract for this scenario is to use flag for reminding which user who is connected is user or admin and which one is free or busy. In my database, if admincode is equal to zero so it is user otherwise it is admin, and I define flag “tpflag” (in application) is equal to zero for user and equal to one for admin. Whenever they connect to chat flag “freeflag” becomes zero which shows busy user and as soon as client leaves conversation becomes one which shows free status.

Step 2: Open PM for Installing Dependency Files

Step 3: Instruction for Removing Old Dependency

At first, remove all of the old decencies for installing new version of SignalR 2.x.x In Line:

PM> Uninstall-Package Microsoft.AspNet.SignalR –RemoveDependencies

Step 4: Instruction for Installing Necessary Dependency Files

For new version, use:

PM> Install-Package Microsoft.AspNet.SignalR

I have used signalr version 2.0.1 for this practice:

PM> Install-Package Microsoft.AspNet.SignalR -Version 2.0.1

PM> Install-Package Microsoft.Owin

By writing this instruction, nuget does all of the dependency injection that you need to run signalr. If you look at Reference part in solution, you will fine Microsoft.ASPNet.SignalR.x, Microsoft.Owin.x.x.. and etc, or if you look at Scripts part in solution jquery-1.x , jquery.signalR 2.x.x and etc. so feel comfort about all of dependency.

Solution --> Open Reference -->

Solution --> Scripts -->

On the other hand, after installing signalR dependencies successfully, you will find complete help as readme.txt above the package console. It contains all the necessary instructions to get started with signalr. I explain these instructions in the next steps.

Tips (1): NuGet

If you encounter this error “The remote name could not be resolved: 'www.nuget.org'” So you should change Package Manager Settings which is located in front of the Package Source.

You should change source from https to http protocol to solve this problem.

Step 5: Startup Class

For enabling signalr in project, you should create class as startup. (If in previous version of signalr , I mean first version, you used to write RouteTable.Routes.MapHubs(); in Application Start in global.asax, now forget about it and just use startup class. Right Click: On Project Name {SignalR} --> Add Class --> Name: Startup.cs

Step 6: Organize Database According To Our Scenario

Step 6.1: Create “tbl_User”

“tbl_user” will collect user and admin, if “AdminCode” was filled by number from previous table so it is admin who belongs to department otherwise if it was filled by (zero) illustrate to ordinary user.{ “UserID” int + identity=yes and “AdminCode” default value = 0 }

Step 6.2: Create “tbl_Conversation”

“tbl_Conversation” which will collect data from conversation between user and admin. This table will be filled after finishing conversation. { “ConID” int + identity=yes }

Step 7.5: Create Model1.edmx

To have a simple way to fetch and insert data from and to database, I create model as follows: Right click on project name --> Add New Item --> Select “ADO.NET Entity Data Model” --> Select “Generate From Data Base” --> Make Connection to your data base --> Select your tables.

Step 8: Create folder and name it Hubs then create simple class and name it “MyHub.cs”

{If you have the last update version of Visual Studio, you can add new item and select “SignalR Hub Class”}

Clients.all.methodname() // all means all of connected user

Clients.Group(groupName).methodname() // Group means just users who are in same group

When there is ***** Return to Client ***** in “MyHub.cs” class, it means you have to write jquery function with the same name in client side.

Indeed their interaction is such as follow:

Tips (3): Call Server Class

There are tiny tips whenever you want to call your server class; always in client side you should use specific naming convention which is camel type, for instance if your hub class name is “MyHub”, you should instantiate your object from “myHub” or if you have “SendMessageToGroup”, you should call it from “sendMessageToGroup” so it should be like:

Test Case

To have the same result, you should have database as same as I have explained in the seventh step.

Case 1

Test Plan: If Client tries to login and there is no admin, then system shows an alarm.

Testing Steps

Run project

UserName: mahsa

Password :123

Expected Output: System shows alarm

Case 2

Test Plan: There is at least on free admin and then one client login and then the first admin will be assigned to the first free client who needs help.

Testing Steps

Run project

UserName: admin1

Password :123

Login {admin1 as first admin}

Copy URL to another web browser

UserName: mahsa

Password :123

Login {mahsa as first client}

If “mahsa” send message, so “admin1” will see it, because they are in same group. When the first client true to login then add to the first free admin.

Copy URL to another web browser

UserName: kashi

Password :123

Login { kashi as second client}

System shows alarm and says “there is no admin then system shows an alarm”

Copy URL to another web browser

UserName: admin2

Password :123

“kashi” and “admin2” cannot see conversation between “admin1” and “mahsa”

Share

About the Author

I have been working with different technologies and data more than 10 years.
I`d like to challenge with complex problem, then make it easy for using everyone. This is the best joy.

ICT Master in Norway 2013
Doctorandin at Technische Universität Berlin in Data Scientist ( currently )
-------------------------------------------------------------
Diamond is nothing except the pieces of the coal which have continued their activities finally they have become Diamond.

*Article of The Community Spotlight in Microsoft ASP.NET, Wednesday, February 11, 2015, www.asp.net
*Article of The Day in Microsoft ASP.NET Tuesday, February 3, 2015, www.asp.net/community/articles
*1 Jan 2015: CodeProject MVP 2015
*22 Mar 2014: Best Web Dev Article of February 2014 - Second Prize

Hey, nice tutorial, but I have problem with displaying users who are waiting to get connected to admins.
I can display the userName in the login div when the user is trying to log-in, but there is no free admin, but I cannot display it in the admin div. Another clue that can give you idea what is wrong with the code is - when user tries to log-in and he can't, since there is no free admin and admin logs from the same log-in form he sees the name of the user that tried to log through this same form. I cannot display the userName to already logged admins. Do you have any ideas?

Using CORS in server for a cross domain Javascript client, when I don't subscribe client methods, it gets connected but it doesn't connect when I subscribe client methods. It shows, error during the start request, stopping the connection. A screenshot could be helpful, I suppose.

Hello,
It is a very good article. I learnt a lot about Signalr. I have been trying to save conversations in database but I am not successful. Could you please post a revised version where you show how to save the conversation in DB ?

You should wait until conversation is finishing so you have to implement your code on "OnDisconnected()" OR you can save on event "click" for button and etc.
You should pass all of argument which you need to save to this function, I mean "OnDisconnected()"
OnDisconnected(string ordinaryUser, string adminUser, string chatconversation, etc )
How to feed these arguments? From chat.cshtml page : you should write something like:

please highlight the code which mapping user and connection id because when we refresh the browser then connection id will be change. in this case how other connected user in chat will be able to know another user new connection id.

Your scenario is different but it is very similar to this scenario, if you pay close attention to diagram and shape and figure.

Make a "div" on the interface, then whenever user login in "on connect" MyHub.cs force -> write your interface method to pass user info to interface and add it to div. If you want to click it add its info inside and make a windows by java script code (which is easy) and make a link to specific users who are grouped on "MyHub.cs" class.

You asked several times that can I speak Persian?
Yes Persian is my native language but in international site you should talk by international language to discuss about technical issues. For example if you read Q&A with me and Member 11569899 with the title of "Very nice article, one urgent question" you can find your answer. So please bear in mind to speak in English as far as you can in order to your words and question might be question for others.