Explaning SignalR in ASP.NET Core 8

In my recent ticket management project, there is a requirement to send messages between multiple users. I explored some options to achieve this requirement.

There are multiple options like,

  1. Use Microsoft’s own library, SignalR.
  2. Use the SetInterval JQuery method to get the latest message
  3. Use any 3rd part of the JQuery Real-time messaging library.

Then I decided to use Microsoft’s own library SignalR library as it is more reliable and simpler to implement.

Introduction

ASP.NET SignalR is a library for ASP.NET developers that simplifies the process of adding real-time web functionality to applications. Real-time web functionality is the ability to have server code push content to connected clients instantly as it becomes available, rather than having the server wait for a client to request new data.

Playground

Let’s implement it in simple steps and brief wording.

Create a new ASP.Net core project in Visual Studio. I used the VS 2022 community version for it. You can choose a template according to your project.

New Project

Name it as per your project, I have named it “SignalR”.

SignalR

I have used the latest Asp.Net core version 8.

Additional Information

The solution will look like this.

Solution

Now add the SignalR CDN script path and some basic design to the view.

<script 
    src="https://unpkg.com/@@microsoft/signalr@latest/dist/browser/signalr.min.js" 
    type="text/javascript">
</script>
<div class="text-center">
    <h1 class="display-4">Welcome to chat : @ViewBag.User</h1>
    <input type="text" id="txtMessage" />
    <input 
        type="submit" 
        id="btnSendMessage" 
        value="Send" 
        title="Send" 
        text="Send" 
    />
    <input 
        type="hidden" 
        id="hdnUserName" 
        value="@ViewBag.User" 
    />
    <div class="chat"></div>
</div>

I have added a simple random number logic in the Index action just to distinguish different users for the chat.

using Microsoft.AspNetCore.Mvc;
using SignalR.Models;
using System.Diagnostics;

namespace SignalR.Controllers
{
    public class HomeController(ILogger<HomeController> logger) : Controller
    {
        public IActionResult Index()
        {
            Random random = new();
            ViewBag.User = "User " + random.Next(100);
            return View();
        }

        public IActionResult Privacy()
        {
            return View();
        }

        [ResponseCache(Duration = 0, Location = ResponseCacheLocation.None, NoStore = true)]
        public IActionResult Error()
        {
            return View(new ErrorViewModel { RequestId = Activity.Current?.Id ?? HttpContext.TraceIdentifier });
        }
    }
}

SignalR CDN

Now install the Microsoft SignalR nuget package using the following command in the Package Manager console.

Install-Package Microsoft.AspNetCore.SignalR

Package Manager console

After installing it, create a basic hub class that will act as a hub for all connections. It will send a signal to all users who are involved in the chat.

using Microsoft.AspNetCore.SignalR;

namespace SignalR
{
    public class ChatHub: Hub
    {
        public async Task SendMessage(string user, string message, string date)
        {
            await Clients.All.SendAsync("ReceiveMessage", user, message, date);
        }
    }
}

In Program.cs file, add the following code to initialize the ChatHub class to receive SignalR's new request.

builder.Services.AddSignalR();
app.MapHub<ChatHub>("/chathub");

 ChatHub class

Now, add some jQuery code to initialize the SignalR connection and send and receive the message.

const connection = new signalR.HubConnectionBuilder()
    .withUrl("/chathub", {
        skipNegotiation: true,
        transport: signalR.HttpTransportType.WebSockets
    })
    .build();

connection.on("ReceiveMessage", (user, message, date) => {
    let h = `<br/><span class="user-chat">${user} : [${date}] ${message}</span>`;
    $('.chat').append(h);
});

connection.start().catch(err => {
    console.log(err.toString());
});

$(document).on("click", "#btnSendMessage", function (e) {
    e.preventDefault();
    var user = $("#hdnUserName").val();
    var message = $("#txtMessage").val();
    var date = new Date();
    if (message.trim() !== '') {
        connection.invoke("SendMessage", user, message, date)
            .catch(function (err) {
                console.error(err.toString());
            });
    }
});

Now, using this code, when you send a message from a browser, the hub method will be called automatically. This will send a message to other browsers where the same screen is opened (i.e. SignalR connection is connected)

SignalR connection

Debugger

Signal Output

This is just a basic implementation in simple steps. In case this is not working on some hosted server, make sure web sockets are enabled with the sticky session setting of the server, and web.config should have the following code added.

<system.webServer>
    <webSocket enabled="true" />
</system.webServer>

I hope you understand the basic structure and implementation of the SignalR library.


Similar Articles