ASP.NET Core 基於JWT的認證(一)

来源:https://www.cnblogs.com/WarrenRyan/archive/2019/02/24/10426204.html
-Advertisement-
Play Games

ASP.NET Core 基於 JWT 的認證(一) Json web token ( JWT ), 是為了在網路應用環境間傳遞聲明而執行的一種基於JSON的開放標準(( RFC 7519 ).該 token 被設計為緊湊且安全的,特別適用於分散式站點的單點登錄( SSO )場景。 JWT 的聲明一 ...


ASP.NET Core 基於JWT的認證(一)

Json web token (JWT), 是為了在網路應用環境間傳遞聲明而執行的一種基於JSON的開放標準((RFC 7519).該token被設計為緊湊且安全的,特別適用於分散式站點的單點登錄(SSO)場景。JWT的聲明一般被用來在身份提供者和服務提供者間傳遞被認證的用戶身份信息,以便於從資源伺服器獲取資源,也可以增加一些額外的其它業務邏輯所必須的聲明信息,該token也可直接被用於認證,也可被加密。

我們知道,http協議本身是一種無狀態的協議,而這就意味著如果用戶向我們的應用提供了用戶名和密碼來進行用戶認證,那麼下一次請求時,用戶還要再一次進行用戶認證才行,因為根據http協議,我們並不能知道是哪個用戶發出的請求,所以為了讓我們的應用能識別是哪個用戶發出的請求,我們只能在伺服器存儲一份用戶登錄的信息,這份登錄信息會在響應時傳遞給瀏覽器,告訴其保存為cookie,以便下次請求時發送給我們的應用,這樣我們的應用就能識別請求來自哪個用戶了。

幾種常見的傳統認證機制

HTTP Basic Auth

HTTP Basic Auth簡單點說明就是每次請求API時都提供用戶的usernamepassword,簡言之,Basic Auth是配合RESTful API 使用的最簡單的認證方式,只需提供用戶名密碼即可,但由於有把用戶名密碼暴露給第三方客戶端的風險,在生產環境下被使用的越來越少。因此,在開發對外開放的RESTful API時,儘量避免採用HTTP Basic Auth

OAuth

OAuth(開放授權)是一個開放的授權標準,允許用戶讓第三方應用訪問該用戶在某一web服務上存儲的私密的資源(如照片,視頻,聯繫人列表),而無需將用戶名和密碼提供給第三方應用。

OAuth允許用戶提供一個令牌,而不是用戶名和密碼來訪問他們存放在特定服務提供者的數據。每一個令牌授權一個特定的第三方系統(例如,視頻編輯網站)在特定的時段(例如,接下來的2小時內)內訪問特定的資源(例如僅僅是某一相冊中的視頻)。這樣,OAuth讓用戶可以授權第三方網站訪問他們存儲在另外服務提供者的某些特定信息,而非所有內容
下麵是OAuth2.0的流程:

Cookie認證機制就是為一次請求認證在服務端創建一個Session對象,同時在客戶端的瀏覽器端創建了一個Cookie對象;通過客戶端帶上來Cookie對象來與伺服器端的session對象匹配來實現狀態管理的。預設的,當我們關閉瀏覽器的時候,cookie會被刪除。但可以通過修改Cookieexpire time使cookie在一定時間內有效;
兩種對比

Token 簡介

JWT (Json Web Token)是為了在網路應用環境間傳遞聲明而執行的一種基於JSON的開放標準。

JWT的聲明一般被用來在身份提供者和服務提供者間傳遞被認證的用戶身份信息,以便於從資源伺服器獲取資源。比如用在用戶登錄上。

有些朋友可能會認為,我登錄只需要用緩存或者資料庫記錄下一個特征碼或者是Cookies就可以了,為什麼要使用JWT呢?我們知道一個資料庫或者是一個軟體,損耗時間最大的地方就是我們的 I/O(輸入輸出,通常指的就是硬碟的讀寫),因此我們選擇解碼一次HS256,對於現在的計算能力強大的電腦而言,解一次HS256比訪問一次磁碟要快得多。

基於token的鑒權機制類似於http協議也是無狀態的,它不需要在服務端去保留用戶的認證信息或者會話信息。這就意味著基於token認證機制的應用不需要去考慮用戶在哪一臺伺服器登錄了,這就為應用的擴展提供了便利。
流程上是這樣的:

  • 用戶使用用戶名密碼來請求伺服器
  • 伺服器進行驗證用戶的信息
  • 伺服器通過驗證發送給用戶一個token
  • 客戶端存儲token,併在每次請求時附送上這個token值
  • 服務端驗證token值,並返回數據

這個token必須要在每次請求時傳遞給服務端,它應該保存在請求頭裡, 另外,服務端要支持CORS(跨來源資源共用)策略,一般我們在服務端這麼做就可以了Access-Control-Allow-Origin: *。
那麼我們現在回到JWT的主題上。

JWT 的組成

我們先來看一段jwt

eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiYWRtaW4iOnRydWV9.TJVA95OrM7E2cBab30RMHrHDcEfxjoYZgeFONFh7HgQ

仔細觀察我們可以發現這一段字元串中含有兩個 " . ",這兩個 " . "jwt分成了三份,我們分別成為頭部、荷載信息、簽證信息。那麼這三部分的分工是什麼呢?

JWT的頭部承載了兩個信息

  • 聲明類型,對於Jwt來說就是jwt
  • 加密演算法,通常使用SHA256,HS256

完整的頭部應該是像這樣的一個Json

{
  'typ': 'JWT',
  'alg': 'HS256'
}

將頭部Json進行base64加密就得到了我們的第一部分

eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9

Payload

第二部分是荷載信息,Payload,你可以理解為我們的JWT是一輛大倉庫,第一部分頭部就是倉庫的名稱編號等基礎信息,而荷載信息就是倉庫的本身,包含了倉庫裡面的所有貨物。這些信息又包含了三個部分:

  • 標準中註冊的聲明
  • 公共的聲明
  • 私有的聲明

標準中註冊的聲明 (建議但不強制使用)

  • iss: jwt簽發者

  • sub: jwt所面向的用戶

  • aud: 接收jwt的一方

  • exp: jwt的過期時間,這個過期時間必須要大於簽發時間

  • nbf: 定義在什麼時間之前,該jwt都是不可用的.

  • iat: jwt的簽發時間

  • jti: jwt的唯一身份標識,主要用來作為一次性token,從而迴避重放攻擊。

公共的聲明 :

公共的聲明可以添加任何的信息,一般添加用戶的相關信息或其他業務需要的必要息。但不建議添加敏感信息,因為該部分在客戶端可解密。

私有的聲明 :

私有聲明是提供者和消費者所共同定義的聲明,一般不建議存放敏感信息,因為base64是對稱解密的,意味著該部分信息可以歸類為明文信息。

事實上我們的Header和Payload都是基於base64加密的,這種密文都是可以對稱解密的,因此請不要存放敏感信息。

定義一個payload:

{
  "sub": "1234567890",
  "name": "John Doe",
  "admin": true
}

進行base64加密後,得到了我們的第二部分

eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiYWRtaW4iOnRydWV9

Signature

Jwt的第三部分是一個簽證信息,這個簽證信息由三部分組成:

  • header (base64後的)
  • payload (base64後的)
  • secret

這一部分可以理解為對前部分的一個校驗,將前兩部分加密後的密文通過在Header中定義的加密方式,與服務端所傳入的密鑰進行一次加密,假如前兩部分的信息被篡改的話,必然通不過最後一部分簽證的校驗。因此通過這樣保證了Jwt的安全性。

因此,保存並隱藏好我們的加密密鑰是非常重要的,假設泄露了,就意味著任何知道密鑰的人都可以輕鬆的對jwt進行自我簽發和驗證。


您的分享是我們最大的動力!

-Advertisement-
Play Games
更多相關文章
  • 一、vector類型簡介 標準庫:集合或動態數組,我們可以放若幹對象放在裡面。 vector他能把其他對象裝進來,也被稱為容器 二、定義和初始化vector對象 (1)空的vector (2)元素拷貝的初始化方式 (3)C++11標準中,用列表初始化方法給值,用{}括起來 (4)創建指定數量的元素 ...
  • 原文地址:http://www.runoob.com/python/python-func-open.html ...
  • 一、前言 int,float,char,C++標準庫提供的類型:string,vector。 string:可變長字元串的處理;vector一種集合或者容器的概念。 二、string類型簡介 C++標準庫中的類型,代表一個可變長的字元串 char str[100] = “I Love China”; ...
  • 對二維數組指定的鍵名排序,首先大家想到的是array_multisort函數,關於array_multisort的用法我之前也寫了一篇廢話不多言,我們看個實例: 細心的朋友會看到,鍵名重置了,鍵名從0開始,顯然這可能不是我們想要的結果,那如何保持鍵名不變? 我們再看個示例: 這裡我們也可以精簡下ar ...
  • 一、前言 在非靜態頁面的項目開發中,必定會涉及到對於資料庫的訪問,最開始呢,我們使用 Ado.Net,通過編寫 SQL 幫助類幫我們實現對於資料庫的快速訪問,後來,ORM(Object Relational Mapping,對象關係映射)出現了,我們開始使用 EF、Dapper、NHibernate ...
  • 百度一下資料庫事務隔離,臟讀等,我想也是一堆。有些老學究扯一堆理論,有些通篇全是代碼,都讓人看的有種說不出蛋疼的感覺。本文用圖文並茂的方式,配上行雲流水般的代碼,非要擺清楚這個問題。本文代碼已提交至碼雲(點擊這裡下載)。 事務是現代關係型資料庫的核心之一。在多個事務併發操作資料庫(多線程、網路併發等 ...
  • 先準備一個耗時方法 /// <summary>/// 耗時方法/// </summary>/// <param name="name"></param>private void DoSomeThing(string name){ Console.WriteLine($"開始執行{name}, {Th ...
  • public class EPPlus { public static string ExcelContentType { get { return "application/vnd.openxmlformats-officedocument.spreadsheetml.sh... ...
一周排行
    -Advertisement-
    Play Games
  • 移動開發(一):使用.NET MAUI開發第一個安卓APP 對於工作多年的C#程式員來說,近來想嘗試開發一款安卓APP,考慮了很久最終選擇使用.NET MAUI這個微軟官方的框架來嘗試體驗開發安卓APP,畢竟是使用Visual Studio開發工具,使用起來也比較的順手,結合微軟官方的教程進行了安卓 ...
  • 前言 QuestPDF 是一個開源 .NET 庫,用於生成 PDF 文檔。使用了C# Fluent API方式可簡化開發、減少錯誤並提高工作效率。利用它可以輕鬆生成 PDF 報告、發票、導出文件等。 項目介紹 QuestPDF 是一個革命性的開源 .NET 庫,它徹底改變了我們生成 PDF 文檔的方 ...
  • 項目地址 項目後端地址: https://github.com/ZyPLJ/ZYTteeHole 項目前端頁面地址: ZyPLJ/TreeHoleVue (github.com) https://github.com/ZyPLJ/TreeHoleVue 目前項目測試訪問地址: http://tree ...
  • 話不多說,直接開乾 一.下載 1.官方鏈接下載: https://www.microsoft.com/zh-cn/sql-server/sql-server-downloads 2.在下載目錄中找到下麵這個小的安裝包 SQL2022-SSEI-Dev.exe,運行開始下載SQL server; 二. ...
  • 前言 隨著物聯網(IoT)技術的迅猛發展,MQTT(消息隊列遙測傳輸)協議憑藉其輕量級和高效性,已成為眾多物聯網應用的首選通信標準。 MQTTnet 作為一個高性能的 .NET 開源庫,為 .NET 平臺上的 MQTT 客戶端與伺服器開發提供了強大的支持。 本文將全面介紹 MQTTnet 的核心功能 ...
  • Serilog支持多種接收器用於日誌存儲,增強器用於添加屬性,LogContext管理動態屬性,支持多種輸出格式包括純文本、JSON及ExpressionTemplate。還提供了自定義格式化選項,適用於不同需求。 ...
  • 目錄簡介獲取 HTML 文檔解析 HTML 文檔測試參考文章 簡介 動態內容網站使用 JavaScript 腳本動態檢索和渲染數據,爬取信息時需要模擬瀏覽器行為,否則獲取到的源碼基本是空的。 本文使用的爬取步驟如下: 使用 Selenium 獲取渲染後的 HTML 文檔 使用 HtmlAgility ...
  • 1.前言 什麼是熱更新 游戲或者軟體更新時,無需重新下載客戶端進行安裝,而是在應用程式啟動的情況下,在內部進行資源或者代碼更新 Unity目前常用熱更新解決方案 HybridCLR,Xlua,ILRuntime等 Unity目前常用資源管理解決方案 AssetBundles,Addressable, ...
  • 本文章主要是在C# ASP.NET Core Web API框架實現向手機發送驗證碼簡訊功能。這裡我選擇是一個互億無線簡訊驗證碼平臺,其實像阿裡雲,騰訊雲上面也可以。 首先我們先去 互億無線 https://www.ihuyi.com/api/sms.html 去註冊一個賬號 註冊完成賬號後,它會送 ...
  • 通過以下方式可以高效,並保證數據同步的可靠性 1.API設計 使用RESTful設計,確保API端點明確,並使用適當的HTTP方法(如POST用於創建,PUT用於更新)。 設計清晰的請求和響應模型,以確保客戶端能夠理解預期格式。 2.數據驗證 在伺服器端進行嚴格的數據驗證,確保接收到的數據符合預期格 ...