Asp.Net Core API 和 WinForm 的 SignalR 例子


什么是 SignalR?

ASP.NET Core SignalR 是一個開源庫,它簡化了向應用程序添加實時 web 功能的功能。 實時 Web 功能使服務器端代碼能夠即時將內容推送到客戶端。
官方列舉的SignalR適用場景:

  • 需要從服務器進行高頻率更新的應用。 示例包括游戲、社交網絡、投票、拍賣、地圖和 GPS 應用。
  • 儀表板和監視應用。 示例包括公司儀表板、即時銷售更新或旅行警報。
  • 協作應用。 協作應用的示例包括白板應用和團隊會議軟件。
  • 需要通知的應用。 社交網絡、電子郵件、聊天、游戲、旅行警報和很多其他應用都需使用通知。

創建SignalR服務端Asp.Net Core API 這參考了Blog系統的寫法
引用SignalR序列化的包
Install-Package Microsoft.AspNetCore.SignalR.Protocols.NewtonsoftJson -Version 3.1.3
Startup類ConfigureServices方法里注冊SignalR服務
services.AddSignalR().AddNewtonsoftJsonProtocol();
創建SignalR的Hub定義消息,分別是IChatClient和ChatHub
IChatClient

  public interface IChatClient
  {
      /// <summary>
      /// SignalR接收信息
      /// </summary>
      /// <param name="message">信息內容</param>
      /// <returns></returns>
      Task ReceiveMessage(object message);

      /// <summary>
      /// SignalR接收信息
      /// </summary>
      /// <param name="user">指定接收客戶端</param>
      /// <param name="message">信息內容</param>
      /// <returns></returns>
      Task ReceiveMessage(string user, string message);

      Task ReceiveUpdate(object message);
  }

ChatHub

  public class ChatHub : Hub<IChatClient>
  {
      /// <summary>
      /// 向指定群組發送信息
      /// </summary>
      /// <param name="groupName">組名</param>
      /// <param name="message">信息內容</param>
      /// <returns></returns>
      public async Task SendMessageToGroupAsync(string groupName, string message)
      {
          await Clients.Group(groupName).ReceiveMessage(message);
      }

      /// <summary>
      /// 加入指定組
      /// </summary>
      /// <param name="groupName">組名</param>
      /// <returns></returns>
      public async Task AddToGroup(string groupName)
      {
          await Groups.AddToGroupAsync(Context.ConnectionId, groupName);
      }

      /// <summary>
      /// 退出指定組
      /// </summary>
      /// <param name="groupName">組名</param>
      /// <returns></returns>
      public async Task RemoveFromGroup(string groupName)
      {
          await Groups.RemoveFromGroupAsync(Context.ConnectionId, groupName);
      }

      /// <summary>
      /// 向指定成員發送信息
      /// </summary>
      /// <param name="user">成員名</param>
      /// <param name="message">信息內容</param>
      /// <returns></returns>
      public async Task SendPrivateMessage(string user, string message)
      {
          await Clients.User(user).ReceiveMessage(message);
      }

      /// <summary>
      /// 當連接建立時運行
      /// </summary>
      /// <returns></returns>
      public override Task OnConnectedAsync()
      {
          //TODO..
          return base.OnConnectedAsync();
      }

      /// <summary>
      /// 當鏈接斷開時運行
      /// </summary>
      /// <param name="ex"></param>
      /// <returns></returns>
      public override Task OnDisconnectedAsync(System.Exception ex)
      {
          //TODO..
          return base.OnDisconnectedAsync(ex);
      }

      public async Task SendMessage(string user, string message)
      {
          await Clients.All.ReceiveMessage(user, message);
      }

      //定於一個通訊管道,用來管理我們和客戶端的連接
      //1、客戶端調用 WinFormsApp,就像訂閱
      //2、服務端主動向客戶端發送數據,名字千萬不能錯
      //3、客戶端再通過 ReceiveUpdate ,來接收
      public async Task WinFormsApp(string name, string msg)
      {
          await Clients.All.ReceiveUpdate($"接收到{name}的消息,消息內容:{msg}");
      }
  }

創建中間件SignalRSendMildd和MiddlewareHelpers
SignalRSendMildd

  /// <summary>
  /// 中間件
  /// </summary>
  public class SignalRSendMildd
  {
      /// <summary>
      ///上下文
      /// </summary>
      private readonly RequestDelegate _next;

      private readonly IHubContext<ChatHub> _hubContext;

      /// <summary>
      ///注入上下文
      /// </summary>
      /// <param name="next"></param>
      /// <param name="hubContext"></param>
      public SignalRSendMildd(RequestDelegate next, IHubContext<ChatHub> hubContext)
      {
          _next = next;
          _hubContext = hubContext;
      }

      /// <summary>
      /// SignalR過濾
      /// </summary>
      /// <param name="context"></param>
      /// <returns></returns>
      public async Task InvokeAsync(HttpContext context)
      {
          await _next(context);
      }
  }

MiddlewareHelpers

  public static class MiddlewareHelpers
  {
      /// <summary>
      /// SignalR中間件
      /// </summary>
      /// <param name="app"></param>
      /// <returns></returns>
      public static IApplicationBuilder UseSignalRSendMildd(this IApplicationBuilder app)
      {
          return app.UseMiddleware<SignalRSendMildd>();
      }
  }

Startup類Configure方法里調用中間件設置SignalR服務路由

     // signalr
         app.UseSignalRSendMildd();
         app.UseEndpoints(endpoints =>
         {
             endpoints.MapControllers();
             endpoints.MapHub<ChatHub>("/signalr/chatHub");
         });

創建SignalR客戶端發送消息返回發送的消息內容,這里客戶端用winform
這是界面

引用SignalR的包
Install-Package Microsoft.AspNetCore.SignalR.Client

      public partial class WinFormsApp : Form
  {
      private HubConnection connection;

      public WinFormsApp()
      {
          InitializeComponent();
          SignalRConnection();
      }

      public async void SignalRConnection()
      {
          connection = new HubConnectionBuilder()
                .WithUrl("http://localhost:5000/signalr/chatHub")
                .Build();
          await connection.StartAsync();
          connection.Closed += async (error) =>
          {
              await Task.Delay(new Random().Next(0, 5) * 1000);
              await connection.StartAsync();
          };
      }

      private async void button1_Click(object sender, EventArgs e)
      {
          try
          {
              await connection.InvokeAsync("WinFormsApp", "SignalRClient", this.textBox1.Text);
              connection.On<object>("ReceiveUpdate", (message) =>
              {
                  this.Invoke(new Action(() =>
                  {
                      this.textBox2.Text = message.ToString();
                  }));
              });
          }
          catch (Exception ex)
          {
              this.textBox2.Text = ex.Message;
          }
      }
  }


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM