asp.net core web api項目添加自定義中間件的實現(xiàn)
前言
在asp.net core web api項目中,默認(rèn)提供了很多的中間件,比如訪問靜態(tài)文件中間件UseStaticFiles
,跨域配置中間件UseCors
,路由中間件UseRouting
,身份驗證中間件UseAuthentication
。
那么如何添加一些自定義的中間件呢。
需求
現(xiàn)在有一個需求,我們的所有接口中都有一個
TimeSpan
參數(shù),傳入的是當(dāng)前時間的時間戳,正常需要對時間戳進(jìn)行加密,然后在加一個統(tǒng)一的驗證方法,只正常處理2分鐘以內(nèi)的請求,超時的請求不在處理,直接返回錯誤代碼,這樣可以一定程度上保護(hù)我們的業(yè)務(wù)數(shù)據(jù)。
這時我們就可以添加一個自定義的中間件,對所有過來的請求先進(jìn)行時間戳校驗處理,處理通過的再返回到業(yè)務(wù)邏輯正常處理,時間戳校驗不通過的則直接返回錯誤碼。
實現(xiàn)
接下來看實現(xiàn)。
為了演示,我還是新建一個空的asp.net core web api項目。然后調(diào)用WeatherForecastController
下的Get
方法來做測試。
然后添加一個類,為了簡單點,這個類就一個TimeSpan
參數(shù)。
public class BaseRequest { public string TimeSpan { get; set; } }
為了方便的使用中間件,我們希望可以直接在Program下的Main函數(shù)里直接調(diào)用。類似這樣。
public static void Main(string[] args) { var builder = WebApplication.CreateBuilder(args); builder.Services.AddControllers(); var app = builder.Build(); //這里是自定義添加的中間件 app.UseRequestCheckMiddleware(); app.UseAuthorization(); app.MapControllers(); app.Run(); }
Startup里添加原理一樣。
所以首先我需要添加一個ApplicationBuilder
的擴(kuò)展方法。這樣才能調(diào)用方法一樣用.
出來。
添加一個ApplicationBuilderExtension
類。
public static class ApplicationBuilderExtension { public static IApplicationBuilder UseRequestCheckMiddleware(this IApplicationBuilder builder) { return builder.UseMiddleware<RequestCheckMiddleware>(); } }
在這個類里通過builder.UseMiddleware
傳入一個實現(xiàn)類,就可以實現(xiàn)中間件添加的效果了,如果想添加多個自定義的中間件,可以繼續(xù)添加新的Use
方法。
接下來重點就是RequestCheckMiddleware
的實現(xiàn)。
public class RequestCheckMiddleware { private readonly RequestDelegate _next; public RequestCheckMiddleware(RequestDelegate next) { _next= next; } public async Task InvokeAsync(HttpContext context) { HttpRequest request = context.Request; //緩存下來允許多次讀取 request.EnableBuffering(); var reader = new StreamReader(request.Body, Encoding.UTF8); string data = await reader.ReadToEndAsync(); // 重置流的位置以便后續(xù)中間件可以讀取 request.Body.Position = 0; try { var inputJson = JsonSerializer.Deserialize<BaseRequest>(data); // 假設(shè) BaseRequest.TimeSpan 是一個 long 類型的 UNIX 時間戳 if (string.IsNullOrEmpty(inputJson.TimeSpan)) { await HandleError(context, 500, "時間戳為空!"); return; } var requestTime = UnixTimeStampToDateTime(Convert.ToInt64(inputJson.TimeSpan)); if (DateTime.Now - requestTime > TimeSpan.FromMinutes(2)) { await HandleError(context, 429, "超時請求!"); return; } await _next(context); } catch (Exception ex) { await HandleError(context, 400, $"處理請求失敗: {ex.Message}"); } } private async Task HandleError(HttpContext context, int statusCode, string message) { context.Response.StatusCode = statusCode; var result = new { code = statusCode, message = message, result = new object() }; await context.Response.WriteAsync(JsonSerializer.Serialize(result)); } private DateTime UnixTimeStampToDateTime(long unixTimeStamp) { // UNIX 時間戳轉(zhuǎn)換為 DateTime DateTime dateTime = new DateTime(1970, 1, 1, 0, 0, 0, 0, DateTimeKind.Utc); dateTime = dateTime.AddSeconds(unixTimeStamp).ToLocalTime(); return dateTime; } }
這里有幾點可以解釋一下。
1、這里的主函數(shù)名必須是Invoke
或者InvokeAsync
,且入?yún)⑹?code>HttpContext。表示這是在請求管道中對請求進(jìn)行處理的中間件。
2、這里需要定義RequestDelegate
的委托,因為需要在當(dāng)前邏輯處理完成后,還需要把請求傳遞到下一步。
3、request.Body
默認(rèn)只能被讀取一次,為了傳遞到下一步依然有原模原樣的請求參數(shù),所以需要先對請求進(jìn)行緩存處理。讀取完成之后,需要把流的位置重置到開始。方便后面可以再次讀取請求內(nèi)容。
然后在Program里添加對應(yīng)中間件就行了。
//這里是自定義添加的中間件 app.UseRequestCheckMiddleware();
驗證
最后來演示一下效果。
首先傳遞一個2分鐘內(nèi)正常的時間戳。
請求可以正常返回。
接著等一會吧,等時間戳過期。
到此這篇關(guān)于asp.net core web api項目添加自定義中間件的實現(xiàn)的文章就介紹到這了,更多相關(guān)asp.net core web api中間件內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
.NET 與樹莓派WS28XX 燈帶的顏色漸變動畫效果的實現(xiàn)
所謂顏色漸變動畫,首先,你要確定兩種顏色——起始色和最終色,比如從綠色變成紅色,綠色是起始,紅色是終點。這篇文章主要介紹了.NET 與樹莓派WS28XX 燈帶的顏色漸變動畫,需要的朋友可以參考下2021-12-12Visual Studio 2017 IDE安裝使用圖文教程
這篇文章主要為大家詳細(xì)介紹了Visual Studio 2017 IDE安裝使用圖文教程,具有一定的參考價值,感興趣的小伙伴們可以參考一下2018-09-09asp.net在Repeater嵌套的Repeater中使用復(fù)選框詳解
這篇文章主要介紹了asp.net在Repeater嵌套的Repeater中使用復(fù)選框,小編覺得挺不錯的,現(xiàn)在分享給大家,也給大家做個參考。一起跟隨小編過來看看吧2018-12-12在ASP.NET中支持?jǐn)帱c續(xù)傳下載大文件(ZT)源碼
這篇文章主要為大家介紹了在ASP.NET中如何做到支持?jǐn)帱c續(xù)傳下載大文件(ZT),需要的朋友可以參考下2014-07-07asp.net 模擬提交有文件上傳的表單(通過http模擬上傳文件)
通過HTTP模擬GET或POST請求,提交數(shù)據(jù)到服務(wù)端獲取響應(yīng),比較常見些;但如上傳文件到服務(wù)端,使用html form當(dāng)然簡單了,而因環(huán)境所限有時需要使用模擬方法去提交有附件(文件上傳)的表單。2010-02-02將Access數(shù)據(jù)庫中數(shù)據(jù)導(dǎo)入到SQL Server中的詳細(xì)方法實例
將Access數(shù)據(jù)庫中數(shù)據(jù)導(dǎo)入到SQL Server中的詳細(xì)方法實例,需要的朋友可以參考一下2013-03-03