項目中有時介面訪問時間過長,但是通過瀏覽器F12查看時,介面訪問時間很正常,所以就很奇怪,於是寫一個中間件,記錄所有介面訪問時間的中間件。 一、中間件 中間件是應用程式處理管道中的組件,用來處理請求和響應。如下圖,請求來之後,第一個中間件處理,處理完後調用下一個中間件(當然也可以選擇不調用下一個中間 ...
項目中有時介面訪問時間過長,但是通過瀏覽器F12查看時,介面訪問時間很正常,所以就很奇怪,於是寫一個中間件,記錄所有介面訪問時間的中間件。
一、中間件
中間件是應用程式處理管道中的組件,用來處理請求和響應。如下圖,請求來之後,第一個中間件處理,處理完後調用下一個中間件(當然也可以選擇不調用下一個中間件),這樣形成一個請求處理管道。每一個中間件通過一個名為RequestDelegate的委托調用下一個中間件。當所有的中間件處理完請求後,再依次返回Response。
微軟提供的中間件有:Authentication(認證)、Cors(跨域資源共用)、Session StaticFiles(靜態文件)、Caching(緩存)、MVC等等。
二、實現記錄介面執行時間中間件
首先中間件不需要繼承什麼介面,也沒有什麼限制。我們可以仿照微軟提供的中間件起名建一個 CalculateExecutionTimeMiddleware和 CalculateExecutionTimeMiddlewareExtensions,如果中間件中涉及配置相關的參數,可以建一個Option。此中間件沒有配置參數就沒有Option。還有就是此中間件必須放在第一位,這樣才能儘可能記錄請求時間。
public class CalculateExecutionTimeMiddleware { private readonly RequestDelegate _next;//下一個中間件 private readonly ILogger _logger; Stopwatch stopwatch; public CalculateExecutionTimeMiddleware(RequestDelegate next, ILoggerFactory loggerFactory) { if (next == null) { throw new ArgumentNullException(nameof(next)); } if (loggerFactory == null) { throw new ArgumentNullException(nameof(loggerFactory)); } this._next = next; _logger = loggerFactory.CreateLogger<CalculateExecutionTimeMiddleware>(); } public async Task Invoke(HttpContext context) { stopwatch = new Stopwatch(); stopwatch.Start();//在下一個中間價處理前,啟動計時器 await _next.Invoke(context); stopwatch.Stop();//所有的中間件處理完後,停止秒錶。 _logger.LogInformation($@"介面{context.Request.Path}耗時{stopwatch.ElapsedMilliseconds}ms"); } }
拓展方法 將中間件加入到請求處理通道中。
public static class CalculateExecutionTimeMiddlewareExtensions { public static IApplicationBuilder UseCalculateExecutionTime(this IApplicationBuilder app) { if (app == null) { throw new ArgumentNullException(nameof(app)); } return app.UseMiddleware<CalculateExecutionTimeMiddleware>(); } }
使用:
public void Configure(IApplicationBuilder app, IHostingEnvironment env, IDataProtectionProvider dataProtectionProvider) { app.UseCalculateExecutionTime();//只需在此添加 if (env.IsDevelopment()) { app.UseDeveloperExceptionPage(); } else { app.UseHsts(); } app.UseHttpsRedirection(); app.UseSession(); app.UseMvc(); }
三、總結
此中間件只記錄了程式處理請求的時間,不能記錄網路傳輸時間,所以記錄的時間比瀏覽器中的時間短一點,但不影響我們找長時間相應的介面。源碼在https://github.com/MicroHeartWangZheng/ExecutionTime。