Skip to content

A lightweight publisher / subscriber implementation using WebSockets.

License

MIT, MIT licenses found

Licenses found

MIT
LICENSE
MIT
LICENSE.txt
Notifications You must be signed in to change notification settings

grantcolley/dipsocket

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

dipsocket

A lightweight publisher / subscriber implementation using WebSockets.

.NET Standard 2.0, .NET Core 2.1 and ASP .NET Core

Build status

NuGet



Example of dipsocket being used as a chat application where users connect to a channel and join the discussion.

Alt text

Table of Contents

DipSocketServer

.NET Standard 2.0

DipSocketServer hosts and manages a collection of DipSocketClient connections. It also manages a collection of Channels. A Channel is a group of client connections that subscribe to it. Messages from one client connection to another client or to a channel get routed via the server. When a client sends a message to a channel the message is broadcast to all connections subscribing to the channel.

DipSocketClient

.NET Standard 2.0

DipSocketClient represents a client connection to the DipSocketServer. Client connections can send messages to each other, routed via the server. Client connections can also create and subscribe to channels hosted by the DipSocketServer.

DipSocket NetCore Extensions

.NET Core 2.1 and ASP NET Core

DipSocket.NetCore.Extensions.dll provides the middleware and extension methods necessary for ASP .NET Core. Simply add dip socket to the services collection and get the app builder to use it.

Example Usage

Client Connect

Full example here...

Establish a DipSocketClient connection to the DipSocketServer.

                var dipSocketClient = new DipSocketClient(@"ws://localhost:6000/chat", "clientId");
                dipSocketClient.Closed += DipSocketClientClosed; ;
                dipSocketClient.Error += DipSocketClientError;

                dipSocketClient.On("OnConnected", (result) =>
                {
                    OnConnected(result);
                });

                dipSocketClient.On("OnMessageReceived", (result) =>
                {
                    OnMessageReceived(result);
                });

                await dipSocketClient.StartAsync();

Client Message

Full example here...

Send a message from one DipSocketClient to another. Messages are routed via the server.

                var clientMessage = new Message
                {
                    SenderConnectionId = senderConnectionId,
                    RecipientConnectionId = recipientConnectionId,
                    Data = myMessage,
                    MessageType = MessageType.SendToClient
                };
                
                await dipSocketClient.SendMessageAsync(clientMessage);

Send a message from a DipSocketClient to a channel on the DipSocketServer. The message is broadcast to all clients subscribing to the channel.

                var clientMessage = new Message
                {
                    SenderConnectionId = senderConnectionId,
                    RecipientConnectionId = channelConnectionId,
                    Data = myMessage,
                    MessageType = MessageType.SendToChannel
                };
                
                await dipSocketClient.SendMessageAsync(clientMessage);

Server Implementation

Full example here...

Inherit the abstract DipSocketServer class and override abstract methods OnClientConnectAsync and ReceiveAsync.

    public class Chat : DipSocketServer
    {
        public async override Task OnClientConnectAsync(WebSocket websocket, string clientId)
        {
            if (string.IsNullOrWhiteSpace(clientId))
            {
                throw new ArgumentNullException("clientId cannot be null or empty.");
            }

            var connection = await base.AddWebSocketAsync(websocket).ConfigureAwait(false);

            connection.Name = clientId;

            var connectionInfo = connection.GetConnectionInfo();

            var json = JsonConvert.SerializeObject(connectionInfo);
            
            var message = new Message { MethodName = "OnConnected", SenderConnectionId = "Chat", Data = json };

            await SendMessageAsync(websocket, message).ConfigureAwait(false);
        }

        public async override Task ReceiveAsync(WebSocket webSocket, Message message)
        {
            switch (message.MessageType)
            {
                case MessageType.SendToAll:
                    message.MethodName = "OnMessageReceived";
                    await SendMessageToAllAsync(message).ConfigureAwait(false);
                    break;

                case MessageType.SendToClient:
                    message.MethodName = "OnMessageReceived";
                    await SendMessageAsync(message).ConfigureAwait(false);
                    break;

                case MessageType.SubscribeToChannel:
                    var channel = SubscribeToChannel(message.Data, webSocket);
                    await ChannelUpdateAsync().ConfigureAwait(false);
                    break;
            }
        }
    }

Server Configure and Build

In the Startup class use the IServiceCollection extension method AddDipSocket and the IApplicationBuilder extension method UseDipSocket<T>. This will register each implementation of the DipSocketServer as a singleton in the service collection and add the middleware.

The following shows how to set up the Chat implementation of the DipSocketServer in the example code.

    public class Startup
    {
        public void ConfigureServices(IServiceCollection services)
        {
            services.AddDipSocket();
        }

        public void Configure(IApplicationBuilder app, IHostingEnvironment env, ILoggerFactory loggerFactory)
        {
            app.UseDipSocket<Chat>("/chat");
        }
    }

Running the Example

The example solution provided is a simple chat application. It consists of a WPF client and a ASP .NET Core server.

First launch the server. Then run multiple instances of the Client.exe.

For each instance of the client provide a unique user name:

Alt text

The client will automatically attempt to connect to the server.

Either add a new channel, or select an existing connection or channel from the drop down list:

Alt text

Write your message in the text box at the bottom and hit enter:

Alt text

About

A lightweight publisher / subscriber implementation using WebSockets.

Resources

License

MIT, MIT licenses found

Licenses found

MIT
LICENSE
MIT
LICENSE.txt

Stars

Watchers

Forks

Releases

No releases published

Packages

No packages published

Languages