在 .NET 8 中使用自定義令牌身份驗證掌握 SignalR Hub 安全性

最近在練習做一個 Web 開發項目,需要使用 WebSockets 傳輸數據,實現實時通信。這是一個 React.js 項目,后端是 .NET。

雖然 MSDN 提供了出色的頂級文檔,但它通常缺少高級用例所需的低級細節。

一種這樣的場景是使用自定義令牌對 SignalR Hub 進行身份驗證。是的,自定義令牌,而不是 JWT 或默認 Bearer 令牌。本文探討如何實現這一點。最后,您將擁有一個需要身份驗證并使用自定義令牌的 SignalR Hub。

自定義Token

我們將使用的自定義令牌是 Base64 編碼的用戶信息分隔字符串,格式如下:

userId:userName

從這個標記中,我們將提取userId并userName創建聲明。

項目設置

以下是設置項目的基本步驟:

創建一個.NET項目:

dotnet new webapi

添加 SignalR 服務:
在Program.cs文件中,構建應用程序時注冊 SignalR 服務:
builder.Services.AddSignalR();

創建 Hub :
創建一個名為 的目錄hubs,并添加一個名為 的文件GameHub.cs。執行以下操作:
public class GameHub : Hub
{
? ?public override Task OnConnectedAsync()
? ?{
? ? ? ?return base.OnConnectedAsync();
? ?}

? ?public override Task OnDisconnectedAsync(Exception? exception)
? ?{
? ? ? ?return base.OnDisconnectedAsync(exception);
? ?}
}

映射中心:
將其GameHub作為端點公開Program.cs:
app.MapHub<GameHub>("/hubs/game");

實現自定義令牌認證
要使用自定義令牌并從中提取用戶信息,我們需要一個自定義身份驗證方案。在 .NET 中,身份驗證方案是一個命名標識符,它指定用于對用戶進行身份驗證的方法或協議,例如 Cookie、JWT 持有者令牌或 Windows 身份驗證。對于此場景,我們將創建一個名為的方案CustomToken。

自定義身份驗證方案實現

定義自定義令牌方案選項:
public class CustomTokenSchemeOptions : AuthenticationSchemeOptions
{
? ?public CustomTokenSchemeOptions()
? ?{
? ? ? ?Events = new CustomTokenEvents();
? ?}

? ?public new CustomTokenEvents Events
? ?{
? ? ? ?get => (CustomTokenEvents)base.Events!;
? ? ? ?set => base.Events = value;
? ?}
}

定義方案處理程序:包含驗證令牌和提取用戶聲明的邏輯
:CustomTokenSchemeHandler
public class CustomTokenSchemeHandler : AuthenticationHandler<CustomTokenSchemeOptions>
{
? ?private new CustomTokenEvents Events => (CustomTokenEvents)base.Events!;

? ?public CustomTokenSchemeHandler(
? ? ? ?IOptionsMonitor<CustomTokenSchemeOptions> options,
? ? ? ?ILoggerFactory logger,
? ? ? ?UrlEncoder encoder) : base(options, logger, encoder) {}

? ?protected override async Task<AuthenticateResult> HandleAuthenticateAsync()
? ?{
? ? ? ?var messageReceivedContext = new MessageReceivedContext(Context, Scheme, Options);
? ? ? ?await Events.MessageReceivedAsync(messageReceivedContext);

? ? ? ?var token = messageReceivedContext.Token ?? GetTokenFromQuery();

? ? ? ?if (token is null)
? ? ? ?{
? ? ? ? ? ?return AuthenticateResult.NoResult();
? ? ? ?}

? ? ? ?byte[] data = Convert.FromBase64String(token);
? ? ? ?string decodedString = Encoding.UTF8.GetString(data);
? ? ? ?string[] userInfoArray = decodedString.Split(":");

? ? ? ?var claims = new[]
? ? ? ?{
? ? ? ? ? ?new Claim(ClaimTypes.Name, userInfoArray[1]),
? ? ? ? ? ?new Claim(ClaimTypes.Sid, userInfoArray[0])
? ? ? ?};
? ? ? ?var principal = new ClaimsPrincipal(new ClaimsIdentity(claims, Scheme.Name));
? ? ? ?var ticket = new AuthenticationTicket(principal, Scheme.Name);
? ? ? ?return AuthenticateResult.Success(ticket);
? ?}

? ?private string? GetTokenFromQuery()
? ?{
? ? ? ?var accessToken = Context.Request.Query["access_token"].ToString();
? ? ? ?return string.IsNullOrEmpty(accessToken) ? null : accessToken;
? ?}
}


配置身份驗證方案:
在以下位置注冊自定義身份驗證方案Program.cs:
builder.Services.AddAuthentication("CustomToken")
? ?.AddScheme<CustomTokenSchemeOptions, CustomTokenSchemeHandler>("CustomToken", opts =>
? ?{
? ? ? ?opts.Events = new CustomTokenEvents
? ? ? ?{
? ? ? ? ? ?OnMessageReceived = context =>
? ? ? ? ? ?{
? ? ? ? ? ? ? ?var accessToken = context.Request.Query["access_token"];
? ? ? ? ? ? ? ?var path = context.HttpContext.Request.Path;

? ? ? ? ? ? ? ?if (!string.IsNullOrEmpty(accessToken) && path.StartsWithSegments("/hubs/game"))
? ? ? ? ? ? ? ?{
? ? ? ? ? ? ? ? ? ?context.Token = accessToken;
? ? ? ? ? ? ? ?}

? ? ? ? ? ? ? ?return Task.CompletedTask;
? ? ? ? ? ?};
? ? ? ?};
? ?});

免責聲明

本文介紹的實現靈感來自 .NET 官方存儲庫中的 BearerTokenScheme 源代碼。我們對其進行了調整以適應此場景的自定義令牌要求。

總結

通過實施此自定義令牌身份驗證方案,您可以保護 SignalR 中心并根據應用程序的獨特要求定制身份驗證過程。此方法允許對令牌驗證和聲明提取進行細粒度控制,從而確保安全可靠的實時通信系統。

歡迎隨意擴展此實現,添加額外的驗證、日志記錄或與外部身份提供商的集成,以獲得更全面的解決方案。

如果您喜歡此文章,請收藏、點贊、評論,謝謝,祝您快樂每一天。?

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/bicheng/75688.shtml
繁體地址,請注明出處:http://hk.pswp.cn/bicheng/75688.shtml
英文地址,請注明出處:http://en.pswp.cn/bicheng/75688.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

[2018][note]用于超快偏振開關和動態光束分裂的all-optical有源THz超表——

前言 類型 太赫茲 + 超表面 太赫茲 + 超表面 太赫茲+超表面 期刊 O p e n A c c e s s Open Access Open

家里網絡訪問Github有時候打不開,解決辦法

1、修改Hosts文件修改法 通過DNS查詢工具&#xff08;如&#xff09;獲取最新GitHub域名解析IP修改系統hosts文件&#xff08;路徑&#xff1a;C:\Windows\System32\drivers\etc\hosts&#xff09;&#xff0c;添加&#xff1a;20.205.243.166 github.com 20.27.177.113 github…

MyBatis操作數據庫(1)

1. MyBatis 簡介 MyBatis 是一款持久層框架&#xff0c;簡化了 JDBC 的復雜操作&#xff0c;通過配置和映射文件將 Java 對象與數據庫表關聯。核心優勢&#xff1a; 自動管理資源&#xff1a;無需手動關閉連接、釋放資源。 動態 SQL&#xff1a;支持參數綁定、條件查詢等。 …

ModuleNotFoundError: No module named ‘matplotlib_inline‘

ModuleNotFoundError: No module named matplotlib_inline 1. ModuleNotFoundError: No module named matplotlib_inline2. matplotlib-inlineReferences 如果你在普通的 Python 腳本或命令行中運行代碼&#xff0c;那么不需要 matplotlib_inline&#xff0c;因為普通的 Python…

SSL證書自動化管理(ACME協議)工作流程介紹

SSL證書自動化管理&#xff08;ACME協議&#xff09;是一種用于自動化管理SSL/TLS證書的協議&#xff0c;以下是其詳細介紹&#xff1a; 一、ACME協議概述 ACME協議由互聯網安全研究小組&#xff08;ISRG&#xff09;設計開發&#xff0c;旨在實現SSL證書獲取流程的自動化。通…

基于FPGA的特定序列檢測器verilog實現,包含testbench和開發板硬件測試

目錄 1.課題概述 2.系統測試效果 3.核心程序與模型 4.系統原理簡介 5.完整工程文件 1.課題概述 本課題采用基于偽碼匹配相關峰檢測的方式實現基于FPGA的特定序列檢測器verilog實現,包含testbench和開發板硬件測試。 2.系統測試效果 仿真測試 當檢測到序列的時候&#xf…

#管理Node.js的多個版本

在 Windows 11 上管理 Node.js 的多個版本&#xff0c;最方便的方法是使用 nvm-windows&#xff08;Node Version Manager for Windows&#xff09;。它允許你輕松安裝、切換和管理多個 Node.js 版本。 &#x1f4cc; 方法 1&#xff1a;使用 nvm-windows&#xff08;推薦 ?&a…

【已解決】Webstorm 每次使用 git pull/push 都要輸入令牌/密碼登錄

解決辦法&#xff1a;勾上【使用憑據幫助程序】&#xff08;英文&#xff1a;Use credential helper&#xff09;

大模型架構記錄13【hr agent】

一 Function calling 函數調用 from dotenv import load_dotenv, find_dotenvload_dotenv(find_dotenv())from openai import OpenAI import jsonclient OpenAI()# Example dummy function hard coded to return the same weather # In production, this could be your back…

Spring Boot向Vue發送消息通過WebSocket實現通信

注意&#xff1a;如果后端有contextPath&#xff0c;如/app&#xff0c;那么前端訪問的url就是ip:port/app/ws 后端實現步驟 添加Spring Boot WebSocket依賴配置WebSocket端點和消息代理創建控制器&#xff0c;使用SimpMessagingTemplate發送消息 前端實現步驟 安裝sockjs-…

【嵌入式學習5】PyQt5模塊介紹、創建第一個窗口

目錄 1、PyQt介紹 ①特點 ②主要組件 2、創建第一個窗口 exce_() 1、PyQt介紹 PyQt 是一個用于創建圖形用戶界面&#xff08;GUI&#xff09;應用程序的 Python 庫&#xff0c;它是 Qt 框架的 Python 綁定。 ①特點 跨平臺&#xff1a;支持多種操作系統&#xff0c;包括…

封裝自己的api簽名sdk

api平臺接口調用&#xff0c;需要通過簽名去核對是不是有效的用戶&#xff0c;&#xff0c;一般會給兩個key&#xff0c;acceeKey 和 secretKey,第一個相當于用戶名&#xff0c;第二個相當于密鑰&#xff0c;&#xff0c;&#xff0c;前端通過一定的算法&#xff0c;&#xff0…

很簡單 的 將字幕生成視頻的 方法

一、一鍵將字幕生成視頻的 方法 1、下載任性動圖 10.7 以上版本 2、設置背景 1&#xff09;背景大小 拉伸背景到合適大小&#xff0c;或者選擇右側比例 2&#xff09;、直接空背景&#xff0c;設置背景顏色等詳細信息 3&#xff09;、或者 復制或者突然圖片做背景 3、設置文…

Spring 核心技術解析【純干貨版】- XXI:Spring 第三方工具整合模塊 Spring-Context-Suppor 模塊精講

在企業級開發中&#xff0c;我們經常需要與 第三方工具 進行集成&#xff0c;如 郵件發送、任務調度、緩存管理等。Spring 為此提供了 Spring-Context-Support 模塊&#xff0c;它封裝了多個常見的第三方工具庫&#xff0c;使得開發者可以更方便地將它們集成到 Spring 項目中。…

c++柔性數組、友元、類模版

目錄 1、柔性數組&#xff1a; 2、友元函數&#xff1a; 3、靜態成員 注意事項 面試題&#xff1a;c/c static的作用? C語言&#xff1a; C: 為什么可以創建出 objx 4、對象與對象之間的關系 5、類模版 1、柔性數組&#xff1a; #define _CRT_SECURE_NO_WARNINGS #…

主相機綁定小地圖

資源初始化&#xff1a;在類中通過 property 裝飾器定義主相機、小地圖相機、小地圖精靈等資源屬性&#xff0c;便于在編輯器中賦值。在 start 方法里&#xff0c;當確認這些資源存在后&#xff0c;創建渲染紋理并設置其大小&#xff0c;將渲染紋理與小地圖相機關聯&#xff0c…

linux-core分析-柔性數組越界訪問

文章目錄 core的調用棧core分析修改修改原因柔性數組定義代碼修改總結core的調用棧 vocb core 崩潰:core的大小都是573M左右 Program terminated with signal SIGSEGV, Segmentation fault. #0 0x0000007f789af0d0 in strlen () from /lib/libc.so.6[Current thread is 1 (LW…

leetcode 代碼隨想錄 數組-區間和

題目 給定一個整數數組 Array&#xff0c;請計算該數組在每個指定區間內元素的總和。 輸入&#xff1a; 第一行輸入&#xff1a;為整數數組 Array 的長度 n&#xff0c;接下來 n 行&#xff0c;每行一個整數&#xff0c;表示數組的元素。隨后的輸入為需要計算總和的區間&…

部署nerdctl工具

nerdctl 是一個專為Containerd設計的容器管理命令行工具&#xff0c;旨在提供類似 Docker 的用戶體驗&#xff0c;同時支持 Containerd 的高級特性&#xff08;如命名空間、compose等&#xff09;。 1、下載安裝 wget https://github.com/containerd/nerdctl/releases/downlo…

【論文筆記】DeepSeek-R1 技術報告

最強開源LLM&#xff0c;性能和效果都很棒&#xff1b;在數學、代碼這種有標準正確答案的場景&#xff0c;表現尤為突出&#xff1b;一些其他場景的效果&#xff0c;可能不如DeepSeek-V3和Qwen。 Deepseek-R1沒有使用傳統的有監督微調sft方法來優化模型&#xff0c;而使用了大規…