SignalR.EasyUse — это фреймворк, который помогает избежать ошибок несоответствия контрактов при создании клиентских и серверных приложений на C# с использованием SignalR.
- Создайте новый проект-библиотеку в своем решении, который будет содержать контракты.
- Добавьте пакет NuGet в этот проект:
Install-Package SignalR.EasyUse.Interface
- Создайте интерфейс с методами сервера. Имена методов интерфейса будут использоваться как идентификаторы, а параметры — передаваться как есть. Возвращаемое значение метода должно быть типа Task или Task<TResult>.
- Интерфейс может наследоваться от
SignalR.EasyUse.Interface.IServerMethods
для удобного различения, но это не обязательно.
Пример:
public interface IChatHub: IServerMethods
{
Task SendMessage(string user, string message);
Task<List<User>> Login(string name, byte[] photo);
}
- Для методов клиента создайте класс для каждого метода. Имя класса будет использоваться как идентификатор, а все его публичные свойства будут передаваться как параметры в порядке их объявления.
- Эти классы могут наследоваться от
SignalR.EasyUse.Interface.IClientMethod
, но это не обязательно.
Пример:
public class ReceiveMessage: IClientMethod
{
public string User { get; set; }
public string Message { get; set; }
}
- Добавьте ссылку на проект с контрактами.
- Добавьте пакет NuGet в проект сервера:
Install-Package SignalR.EasyUse.Server
- Реализуйте интерфейс сервера. Благодаря этому реализации будут соответствовать описанным контрактам.
- Для отправки сообщений клиентам можно использовать строго типизированные вызовы с помощью метода расширения:
async Task SendAsync<T>(this IClientProxy clients, T payload)
Пример:
public class ChatHub : Hub, IChatHub
{
public async Task SendMessage(string user, string message)
{
await Clients.All.SendAsync(new ReceiveMessage
{
User = user,
Message = message,
});
// Эквивалентный нативный вызов
await Clients.All.SendAsync("ReceiveMessage", user, message);
}
}
- Добавьте ссылку на проект с контрактами.
- Добавьте пакет NuGet в проект клиента:
Install-Package SignalR.EasyUse.Client
- Создайте подключение к хабу:
_connection = new HubConnectionBuilder()
.WithUrl("http://localhost:53353/ChatHub")
.Build();
- Создайте динамический прокси для хаба на основе интерфейса:
var hub = _connection.CreateHub<IChatHub>();
- Используйте прокси для вызова методов сервера:
var users = await hub.Login(UserName, Photo);
await hub.SendMessage(UserName, MessageText);
Пример без использования EasyUse:
var users = await connection.InvokeCoreAsync<List<User>>("Login", new object[] { UserName, Photo });
await _connection.InvokeAsync("SendMessage", UserName, MessageText);
- Для подписки на сообщения от сервера используйте метод расширения:
void Subscribe<T>(this HubConnection connection, Action<T> action)
Пример:
_connection.Subscribe<ReceiveMessage>(data =>
{
var newMessage = $"{data.User}: {data.Message}";
Messages.Add(newMessage);
});
Пример без использования EasyUse:
_connection.On<string, string>("ReceiveMessage", (user, message) =>
{
var newMessage = $"{user}: {message}";
Messages.Add(newMessage);
});
Для ознакомления с работающими проектами, использующими этот фреймворк, перейдите по следующим ссылкам:
- Простой чат на .NetCore 3.1 и три клиента: WPF(.Net 4.6.1), WPF(.NetCore 3.1) и AvaloniaUI MVVM(.NetCore 3.1)
- Чат с более сложным функционалом и красивым дизайном на MVVM (сервер на .NetCore 3.1, клиент на WPF MVVM(.Net 4.6.2))
Буду рад вашим предложениям и комментариям. Для связи используйте Telegram.