zoukankan      html  css  js  c++  java
  • NetCore 中间件获取请求报文和返回报文

      

    using System;
    using System.IO;
    
    namespace WebApi.Restful.Middlewares
    {
        public class MemoryWrappedHttpResponseStream : MemoryStream
        {
            private Stream _innerStream;
            public MemoryWrappedHttpResponseStream(Stream innerStream)
            {
                this._innerStream = innerStream ?? throw new ArgumentNullException(nameof(innerStream));
            }
            public override void Flush()
            {
                this._innerStream.Flush();
                base.Flush();
            }
    
            public override void Write(byte[] buffer, int offset, int count)
            {
                base.Write(buffer, offset, count);
                this._innerStream.Write(buffer, offset, count);
            }
    
            protected override void Dispose(bool disposing)
            {
                base.Dispose(disposing);
                if (disposing)
                {
                    this._innerStream.Dispose();
                }
            }
    
            public override void Close()
            {
                base.Close();
                this._innerStream.Close();
            }
        }
    }
    

        

    using Exceptionless;
    using gateway.api;
    using Microsoft.AspNetCore.Http;
    using Microsoft.AspNetCore.Mvc.Formatters;
    using Microsoft.AspNetCore.WebUtilities;
    using Microsoft.Extensions.Logging;
    using Newtonsoft.Json;
    using System;
    using System.Collections.Generic;
    using System.IO;
    using System.Net.Http;
    using System.Text;
    using System.Threading;
    using System.Threading.Tasks;
    
    namespace WebApi.Restful.Middlewares
    {

    /// <summary> /// 请求日志记录中间件 /// </summary> public class RequestLoggingMiddleware { private readonly RequestDelegate _next; private readonly ILogger _logger; public RequestLoggingMiddleware(RequestDelegate next, ILogger<RequestLoggingMiddleware> logger) { _next = next; _logger = logger; } public async Task Invoke(HttpContext context) { context.TraceIdentifier = Guid.NewGuid().ToString("N"); var request = context.Request; await RequestEnableRewindAsync(request).ConfigureAwait(false); var encoding = GetRequestEncoding(request); var requestContent = await ReadStreamAsync(request.Body, encoding).ConfigureAwait(false); WritLog(context, JsonConvert.SerializeObject(requestContent)); await ResponseEnableRewindAsync(context.Response); context.Response.OnCompleted(ResponseCompletedCallback, context); await _next(context); } private async Task ResponseCompletedCallback(object obj) { if (obj is HttpContext context) { var response = await ResponseReadStreamAsync(context.Response);
             //记录日志 //ExceptionlessClient.Default.CreateLog(JsonConvert.SerializeObject(response)).AddTags(context.TraceIdentifier).Submit(); } } private async Task<string> ResponseReadStreamAsync(HttpResponse response) { if (response.Body.Length > 0) { response.Body.Seek(0, SeekOrigin.Begin); var encoding = GetEncoding(response.ContentType); var retStr = await ReadStreamAsync(response.Body, encoding, false).ConfigureAwait(false); return retStr; } return null; } private async Task<string> ReadStreamAsync(Stream stream, Encoding encoding, bool forceSeekBeginZero = true) { using (StreamReader sr = new StreamReader(stream, encoding, true, 1024, true))//这里注意Body部分不能随StreamReader一起释放 { var str = await sr.ReadToEndAsync(); if (forceSeekBeginZero) { stream.Seek(0, SeekOrigin.Begin);//内容读取完成后需要将当前位置初始化,否则后面的InputFormatter会无法读取 } return str; } } private void WritLog(HttpContext context, string body) { var request = context.Request; try { Task.Factory.StartNew(() => { LogMode logMode = new LogMode { Body = body, CententLength = request.ContentLength, CententType = request.ContentType, Headers = JsonConvert.SerializeObject(request.Headers), Host = request.Host.Host, Method = request.Method, Path = request.Path, Query = JsonConvert.SerializeObject(request.Query) };
               // 记录日志 // ExceptionlessClient.Default.CreateLog(JsonConvert.SerializeObject(logMode)).AddTags(context.TraceIdentifier).Submit(); }); } catch (Exception ex) {
              //记录日志 //ex.ToExceptionless().Submit(); } } private async Task ResponseEnableRewindAsync(HttpResponse response) { if (!response.Body.CanRead || !response.Body.CanSeek) { response.Body = new MemoryWrappedHttpResponseStream(response.Body); } } private async Task RequestEnableRewindAsync(HttpRequest request) { if (!request.Body.CanSeek) { request.EnableBuffering(); await request.Body.DrainAsync(CancellationToken.None); request.Body.Seek(0L, SeekOrigin.Begin); } } private async Task<string> ReadStreamAsync(Stream stream, Encoding encoding) { using (StreamReader sr = new StreamReader(stream, encoding, true, 1024, true))//这里注意Body部分不能随StreamReader一起释放 { var str = await sr.ReadToEndAsync(); stream.Seek(0, SeekOrigin.Begin);//内容读取完成后需要将当前位置初始化,否则后面的InputFormatter会无法读取 return str; } } private Encoding GetRequestEncoding(HttpRequest request) { var requestContentType = request.ContentType; var requestMediaType = requestContentType == null ? default(MediaType) : new MediaType(requestContentType); var requestEncoding = requestMediaType.Encoding; if (requestEncoding == null) { requestEncoding = Encoding.UTF8; } return requestEncoding; } private Encoding GetEncoding(string contentType) { var mediaType = contentType == null ? default(MediaType) : new MediaType(contentType); var encoding = mediaType.Encoding; if (encoding == null) { encoding = Encoding.UTF8; } return encoding; } public class LogMode { public string Body { get; set; } public long? CententLength { get; set; } public string CententType { get; set; } public string Headers { get; set; } public string Host { get; set; } public string Method { get; set; } public string Path { get; set; } public string Query { get; set; } } private Dictionary<string, IEnumerable<string>> GetHeaders(HttpRequestMessage request) { var result = new Dictionary<string, IEnumerable<string>>(); foreach (var pair in request.Headers) { result.Add(pair.Key, pair.Value); } return result; } } }  
  • 相关阅读:
    iOS开发Quzrtz2D 十:圆形图片的绘制以及加边框圆形图片的绘制
    团队项目(周日站立会议)
    团队项目(周六站立会议)
    团队项目(spring会议)
    团队项目(第一次会议)
    结对开发项目 电梯调度发布版(已完成) 刘佳琪、兰梦
    结对测试二(求二维数组的子数组之和最大值)(兰梦、刘佳琪)
    敏捷开发(对于敏捷开发模式的理解)
    上课结对测试项目(求整数数组的子数组之和的最大值)(兰梦,刘佳琪)
    结对开发项目:多部电梯调度(一)(兰梦、刘佳琪)
  • 原文地址:https://www.cnblogs.com/sunqiang/p/10174972.html
Copyright © 2011-2022 走看看