document language: English | 简体中文
This API mirrors (as close as possible) the official .NET Microsoft.AspNetCore.SignalR.Client. Exceptions are mainly derived from the lack of async
and generics support in .NET nanoFramework.
Component | Build Status | NuGet Package |
---|---|---|
nanoFramework.SignalR.Client |
This is a SignalR Client library that enable you to connect your .net nanoFramework device to a SignalR Hub. SignalR is part of the ASP.NET Framework that makes it easy to create web applications that require high-frequency updates from the server like gaming. In the IoT domain SignalR can be used to create a webapp that for example shows a life graphs of connected smart meters, control a robot arm and many more.
Important: You must be connected to a network with a valid IP address. Please check the examples with the Network Helpers on how to set this up.
To establish a connection, create a HubConnection
Client. You have to set the hub URL upon initialization of the HubConnection. You can also set custom headers by adding ClientWebsocketHeaders
and set extra options by adding HubConnectionOptions
upon initialization. The options are mainly used to change the settings of the underlying websocket and to set extra ssl options.
You can start the connection by calling Start
.
using System;
using System.Diagnostics;
using System.Threading;
using nanoFramework.SignalR.Client;
namespace NFSignalrTestClient
{
public class Program
{
public static void Main()
{
//setup connection
var options = new HubConnectionOptions() { Reconnect = true };
HubConnection hubConnection = new HubConnection("http://YourSignalrTestServer/testhub", options: options);
hubConnection.Closed += HubConnection_Closed;
hubConnection.On("ReceiveMessage", new Type[] { typeof(string), typeof(string) }, (sender, args) =>
{
var name = (string)args[0];
var message = (string)args[1];
Console.WriteLine($"{name} : {message}");
});
//start connection
hubConnection.Start();
AsyncResult dashboardClientConnected = hubConnection.InvokeCoreAsync("AwaitCientConnected", typeof(bool), new object[] { }, -1);
int seconds = 0;
while (!dashboardClientConnected.Completed)
{
Debug.WriteLine($"Waited {seconds} for client to open webapp");
seconds++;
Thread.Sleep(1000);
}
if ((bool)dashboardClientConnected.Value)
{
hubConnection.SendCore("ReportStatus", new object[] { "Client Connected" });
int count = 0;
while (hubConnection.State == HubConnectionState.Connected)
{
hubConnection.InvokeCore("SendMessage", null, new object[] { count, "this is a control message" });
count++;
Thread.Sleep(1000);
}
}
else
{
hubConnection.Stop("client failed to connect");
}
}
private static void HubConnection_Closed(object sender, SignalrEventMessageArgs message)
{
Debug.WriteLine($"closed received with message: {message.Message}");
}
}
}
Reconnecting
By default the HubConnection
Client will not reconnect if a connection is lost or fails upon first connection. By setting the HubConnectionOptions Reconnect
to true upon initialization of the HubConnection, the client will try to reconnect with a interval of 0, 2, 10, and 30 seconds, stopping after four failed attempts.
When the client tries to reconnect the Reconnecting event is fired.
Note: the client will only try to reconnect if the connection is closed after receiving a server close message with the server request to reconnect.
The connection state can be monitored by checking the HubConnection State
. The different states are: Disconnected
Connected
Connecting
and Reconnecting
. After a connection is established every state change will fire a event: Closed
Reconnecting
or Reconnected
. These events can be used to manual handle disconnects and reconnection.
There are three ways to call a method on the hub. All three methods require you to pass the hub method name and any arguments defined in the hub method.
The simples form is calling SendCore
This will call the method without expecting or waiting for any response from the server. It’s a ‘fire and forget’ method.
The second method is InvokeCore
. InvokeCore requires you to pass the hub method name, the hub method return type, the arguments and an optional timeout in milliseconds. If no timeout is given the default ServerTimeout
is used. This is a Synchronous method that will wait until the server replies. The returned object is of the type defined by the method return type argument. The casting of the object to the right type should be done manually.
Note: if the hub method return type is void, the return type upon calling InvokeCore or InvokeCoreAsync should be null.
Note: set timeout to -1 to disable the server timeout. If no return message is received from the server this will wait indefinitely.
The third method is InvokeCoreAsync
. This is the same as InvokeCore but than asynchronous. It will return an AsyncResult.
The AsyncResult
monitors the return message of the hub method. Upon completion Completed
will be true. Upon completion the Value
will hold the return object that needs to be cast to the right Type manually. Calling Value
before completion will result in the awaiting of the server return. If an error occurs, Error
will be true and the error message will be inside ErrorMessage
.
AsyncResult dashboardClientConnected = hubConnection.InvokeCoreAsync("AwaitCientConnected", typeof(bool), new object[] { }, -1);
int seconds = 0;
while (!dashboardClientConnected.Completed)
{
Debug.WriteLine($"Waited {seconds} for client to open webapp");
seconds++;
Thread.Sleep(1000);
}
if ((bool)dashboardClientConnected.Value)
{
Debug.WriteLine("The client connected to the dashboard, start sending live data");
}
Define methods the hub calls using connection.On after building, but before starting the connection.
connection.On("ReceiveMessage", new Type[] { typeof(string), typeof(string) }, (sender, args) =>
{
var name = args[0] as string;
var message = args[1] as string;
Debug.WriteLine($"{name} : {message}");
});
The preceding code in connection.On runs when server-side code calls it using the SendAsync method.
public async Task SendMessage(string user, string message)
{
await Clients.All.SendAsync("ReceiveMessage", user, message);
}
The connection can be closed by calling Stop
. This will stop the connection. If you want to stop the connection because for example a device sensor malfunctions, an error can be conveyed back to the server by stating the error using the optional errorMessage
.
For documentation, providing feedback, issues and finding out how to contribute please refer to the Home repo.
Join our Discord community here.
The list of contributors to this project can be found at CONTRIBUTORS.
The nanoFramework Class Libraries are licensed under the MIT license.
This project has adopted the code of conduct defined by the Contributor Covenant to clarify expected behaviour in our community. For more information see the .NET Foundation Code of Conduct.
This project is supported by the .NET Foundation.