2021年10月18日 星期一

使用 SignalR 讓 server 主動推播資料給 client (Asp.Net Core)

c#
1. startup.cs 加入signalr
public void ConfigureServices(IServiceCollection services)
{
    ...
    services.AddSignalR();
    services.AddCors(options =>
                options.AddDefaultPolicy(builder => builder.WithOrigins("https://localhost:44331").AllowAnyHeader().AllowAnyMethod().AllowCredentials())); // 針對跨網域呼叫加入來源白名單
}
public void Configure(IApplicationBuilder application)
{
    application.UseRouting();
    application.UseCors(); // 處理跨網域呼叫
    application.UseEndpoints(endpoints =>
    {
        endpoints.MapHub<ChatHub>("/hub");
    });
    ....
}

2. 建立hub class
using Microsoft.AspNetCore.SignalR;
    public class ChatHub : Hub
    {
        // 接收通知
        public Task ClientMessage(string name,string message)
        {
           ...
        }
    }


3. 發送通知
private readonly Microsoft.AspNetCore.SignalR.IHubContext<ChatHub> _hubContext;
public xxxController(Microsoft.AspNetCore.SignalR.IHubContext<ChatHub> hubContext) {
    _hubContext = hubContext;
}
public async Task<IActionResult> xxx() {
   await _hubContext.Clients.All.SendCoreAsync("訂單異動", new object?[] { 訂單編號});
}

----

js
1. 安裝 signalr : npm install @microsoft/signalr
2. 引入 node_modules\@microsoft\signalr\dist\browser\signalr.min.js
3. 設定SignalR的連線資訊
var connection = new signalR.HubConnectionBuilder().withUrl("https://xxx/hub").withAutomaticReconnect().build();
4. 與Server建立連線
async function start() {
    try {
        await connection.start({ transport: 'webSockets' });
        console.log("SignalR Connected.");
    } catch (err) {
        console.log(err);
        setTimeout(start, 5000);
    }
};
// Start the connection.
start();
5. 接收通知
connection.on("訂單成立", function (message) {
    console.log(message);
});
6. 發送通知
connection.invoke("ClientMessage", 'ReceiveMessage', 'hihihi').catch(function (err) {
    return console.error(err.toString());
});

沒有留言:

自訂權限驗證機制

// 使用 filter [Route("api/[controller]")] [ApiController] [Authorize] [TypeFilter(typeof(CustomAsyncAuthorizationFilter))] public c...