什麼是跨站請求偽造
跨站請求偽造(英語:Cross-site request forgery),也被稱為 one-click attack 或者 session riding,通常縮寫為 CSRF 或者 XSRF, 是一種挾制使用者在當前已登入的Web應用程式上執行非本意的操作的攻擊方法。【1】 跟跨網站指令碼(XSS)相比,XSS 利用的是使用者對指定網站的信任,CSRF 利用的是網站對使用者網頁瀏覽器的信任。
想瞭解更多,請檢視維基百科上的詳細介紹。
使用 Asp.Net Core 內建的 Antiforgery
Asp.Net Core 應用中內建了 Microsoft.AspNetCore.Antiforgery
包來支援跨站請求偽造。如果你的應用取用了 Microsoft.AspNetCore.App
包, 則就已經包含了 Microsoft.AspNetCore.Antiforgery
。如果沒有, 則可以使用下麵的命令來新增這個包:
dotnet add package Microsoft.AspNetCore.Antiforgery
添加了這個包之後, 需要先修改 Startup.cs
檔案中的 ConfigureServices
方法, 新增下麵的配置:
public class Startup {
public void ConfigureServices(IServiceCollection services) {
services.AddAntiforgery(options => {
options.Cookie.SameSite = SameSiteMode.Lax;
options.HeaderName = "X-XSRF-TOKEN";
});
}
}
在 SecurityController.cs
檔案中新增一個 Api , 來頒發憑據:
[Route("api/[controller]")]
[ApiController]
public class SecurityController : Controller {
private IAntiforgery antiforgery;
public SecurityController(
IAntiforgery antiforgery
) {
this.antiforgery = antiforgery;
}
[HttpGet("xsrf-token")]
public ActionResult GetXsrfToken() {
var tokens = antiforgery.GetAndStoreTokens(HttpContext);
Response.Cookies.Append(
"XSRF-TOKEN",
tokens.RequestToken,
new CookieOptions {
HttpOnly = false,
Path = "/",
IsEssential = true,
SameSite = SameSiteMode.Lax
}
);
return Ok();
}
}
當客戶端請求 ~/api/security/xsrf-token
時, 服務端傳送兩個 Cookie :
- .AspNetCore.Antiforgery.xxxxxx 一個 HTTP Only 的 Cookie , 用於服務端驗證;
- XSRF-TOKEN 客戶端需要將這個 Cookie 的值用 X-XSRF-TOKEN 的 Header 發送回服務端, 進行驗證;
註意:這兩個 Cookie 不支援跨域請求, 只能在相同的站點內請求, 也是出於安全性方面的考慮。
可以為某一個 ApiController 或者 Action 方法單獨新增 ValidateAntiForgeryTokenAttribute
標記來驗證 XSRF-TOKEN
, 也可以全域性註冊一個 AutoValidateAntiforgeryTokenAttribute
過濾器來進行自動驗證, 程式碼如下:
public class Startup {
public void ConfigureServices(
IServiceCollection services,
IHostingEnvironment env
) {
services.AddMvc(options => {
if (env.IsProduction()) {
options.Filters.Add(
new AutoValidateAntiforgeryTokenAttribute()
);
}
});
}
}
註意問題:不是所有的方法都需要進行 XSRF 認證,除了 GET, HEAD, OPTIONS 和 TRACE 之外的方法才支援 XSRF 認證。
Angular 內建支援
Angular 的 Http 模組內建支援 XSRF , 前提條件如下:
- 存在客戶端可以操作的名稱為 XSRF-TOKEN 的 Cookie ;
- 該 Cookie 不能是 HttpOnly 的, 否則客戶端指令碼無法讀取;
- 該 Cookie 的 Path 必須為
/
;
這三個條件都滿足, 則在向服務端請求時自動傳送名稱為 X-XSRF-TOKEN
的 Header , 值則為 XSRF-TOKEN 的 Cookie 的值, 這樣就回自動滿足上面的服務端的設定, 實現自動防禦跨站請求偽造。
朋友會在“發現-看一看”看到你“在看”的內容