Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/298.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 请求和响应日志的自然链接.NET核心应用程序_C#_.net Core - Fatal编程技术网

C# 请求和响应日志的自然链接.NET核心应用程序

C# 请求和响应日志的自然链接.NET核心应用程序,c#,.net-core,C#,.net Core,我正在尝试按GUID链接请求和响应日志。我要么为每个请求和响应获得相同的GUID,要么为每个请求和响应获得完全不同的GUID。我需要的是链接的请求和响应具有相同的GUID,但与所有其他请求和响应不同。在我目前的结构中,有可能做到这一点吗 public class RequestResponseLoggingMiddleware { private readonly RequestDelegate _next; private readon

我正在尝试按GUID链接请求和响应日志。我要么为每个请求和响应获得相同的GUID,要么为每个请求和响应获得完全不同的GUID。我需要的是链接的请求和响应具有相同的GUID,但与所有其他请求和响应不同。在我目前的结构中,有可能做到这一点吗

public class RequestResponseLoggingMiddleware
    {
        
        private readonly RequestDelegate _next;
        private readonly ILogger _logger;
        private readonly RecyclableMemoryStreamManager _recyclableMemoryStreamManager;

        public RequestResponseLoggingMiddleware(RequestDelegate next, ILoggerFactory loggerFactory)
        {
            _next = next;
            _logger = loggerFactory.CreateLogger<RequestResponseLoggingMiddleware>();
            _recyclableMemoryStreamManager = new RecyclableMemoryStreamManager();
        }

        public async Task Invoke(HttpContext context)
        {
            await LogRequest(context);
            await LogResponse(context);

        }

        private async Task LogRequest(HttpContext context)
        {
            context.Request.EnableBuffering();

            await using var requestStream = _recyclableMemoryStreamManager.GetStream();
            await context.Request.Body.CopyToAsync(requestStream);


            var Request = new Dictionary<string, string>(){
                {"Http Request Information", $"{DateTime.UtcNow}"},
                {"ID", Guid.NewGuid().ToString()},
                {"IP", $"{context.Request.HttpContext.Connection.RemoteIpAddress}" },
                {"Schema", context.Request.Scheme},
                {"Path", context.Request.Path},
                {"QueryString", $"{context.Request.QueryString}"},
                {"Request Body", ReadStreamInChunks(requestStream)}
            };

            var requestJson = JsonConvert.SerializeObject(Request, Formatting.None);

            _logger.LogInformation(requestJson);

            context.Request.Body.Position = 0;
        }


        private async Task LogResponse(HttpContext context)
        {
            var originalBodyStream = context.Response.Body;

            await using var responseBody = _recyclableMemoryStreamManager.GetStream();
            context.Response.Body = responseBody;

            await _next(context);

            context.Response.Body.Seek(0, SeekOrigin.Begin);
            var text = await new StreamReader(context.Response.Body).ReadToEndAsync();
            context.Response.Body.Seek(0, SeekOrigin.Begin);

            var Response = new Dictionary<string, string>(){
                {"Http Response Information", $"{DateTime.UtcNow}"},
                {"ID", Guid.NewGuid().ToString()},
                {"IP", $"{context.Request.HttpContext.Connection.RemoteIpAddress}" },
                {"Schema", context.Request.Scheme},
                {"Path", context.Request.Path },
                {"QueryString", $"{context.Request.QueryString}"},
                {"Response Body", text}
            };

            var responseJson = JsonConvert.SerializeObject(Response, Formatting.None);

            _logger.LogInformation(responseJson);

            await responseBody.CopyToAsync(originalBodyStream);
        }

        private static string ReadStreamInChunks(Stream stream)
        {
            const int readChunkBufferLength = 4096;

            stream.Seek(0, SeekOrigin.Begin);

            using var textWriter = new StringWriter();
            using var reader = new StreamReader(stream);

            var readChunk = new char[readChunkBufferLength];
            int readChunkLength;

            do
            {
                readChunkLength = reader.ReadBlock(readChunk, 0, readChunkBufferLength);
                textWriter.Write(readChunk, 0, readChunkLength);
            } while (readChunkLength > 0);

            return textWriter.ToString();
        }
公共类RequestResponseLoggingMiddleware
{
private readonly RequestDelegate\u next;
专用只读ILogger\u记录器;
私有只读可回收内存流管理器\u可回收内存流管理器;
公共RequestResponseLoggingMiddleware(RequestDelegate下一步,iLogger工厂loggerFactory)
{
_下一个=下一个;
_logger=loggerFactory.CreateLogger();
_recyclableMemoryStreamManager=新的recyclableMemoryStreamManager();
}
公共异步任务调用(HttpContext上下文)
{
等待日志请求(上下文);
等待日志响应(上下文);
}
专用异步任务日志请求(HttpContext上下文)
{
context.Request.enableBuffer();
使用var requestStream=_recyclableMemoryStreamManager.GetStream()等待;
wait context.Request.Body.CopyToAsync(requestStream);
var请求=新字典(){
{“Http请求信息”,$“{DateTime.UtcNow}”,
{“ID”,Guid.NewGuid().ToString()},
{“IP”,$“{context.Request.HttpContext.Connection.RemoteIpAddress}”,
{“Schema”,context.Request.Scheme},
{“Path”,context.Request.Path},
{“QueryString”,$“{context.Request.QueryString}”,
{“请求正文”,ReadStreamInChunks(requestStream)}
};
var requestJson=JsonConvert.SerializeObject(请求,格式化.None);
_logger.LogInformation(requestJson);
context.Request.Body.Position=0;
}
专用异步任务日志响应(HttpContext上下文)
{
var originalBodyStream=context.Response.Body;
使用var responseBody=_recyclableMemoryStreamManager.GetStream()等待;
context.Response.Body=responseBody;
等待下一步(上下文);
context.Response.Body.Seek(0,SeekOrigin.Begin);
var text=wait new StreamReader(context.Response.Body).ReadToEndAsync();
context.Response.Body.Seek(0,SeekOrigin.Begin);
var Response=newdictionary(){
{“Http响应信息”,$“{DateTime.UtcNow}”,
{“ID”,Guid.NewGuid().ToString()},
{“IP”,$“{context.Request.HttpContext.Connection.RemoteIpAddress}”,
{“Schema”,context.Request.Scheme},
{“Path”,context.Request.Path},
{“QueryString”,$“{context.Request.QueryString}”,
{“答复正文”,正文}
};
var responseJson=JsonConvert.SerializeObject(Response,Formatting.None);
_日志信息(responseJson);
wait responseBody.CopyToAsync(originalBodyStream);
}
私有静态字符串ReadStreamInChunks(流)
{
const int readChunkBufferLength=4096;
stream.Seek(0,SeekOrigin.Begin);
使用var textWriter=new StringWriter();
使用var reader=newstreamreader(流);
var readChunk=新字符[readChunkBufferLength];
int-readChunkLength;
做
{
readChunkLength=reader.ReadBlock(readChunk,0,readChunkBufferLength);
Write(readChunk,0,readChunkLength);
}而(readChunkLength>0);
返回textWriter.ToString();
}

我将扩展请求和响应json对象,并在其中添加一些ID字段,并使用相同的Guid填充:

public class RequestResponseLoggingMiddleware
    {
        
        private readonly RequestDelegate _next;
        private readonly ILogger _logger;
        private readonly RecyclableMemoryStreamManager _recyclableMemoryStreamManager;

        public RequestResponseLoggingMiddleware(RequestDelegate next, ILoggerFactory loggerFactory)
        {
            _next = next;
            _logger = loggerFactory.CreateLogger<RequestResponseLoggingMiddleware>();
            _recyclableMemoryStreamManager = new RecyclableMemoryStreamManager();
        }

        public async Task Invoke(HttpContext context)
        {
            var guid = Guid.NewGuid();
            await LogRequest(context, guid);
            await LogResponse(context, guid);

        }

        private async Task LogRequest(HttpContext context, Guid guid)
        {
            context.Request.EnableBuffering();

            await using var requestStream = _recyclableMemoryStreamManager.GetStream();
            await context.Request.Body.CopyToAsync(requestStream);


            var Request = new Dictionary<string, string>(){
                {"Request ID", guid.ToString()}
                {"Http Request Information", $"{DateTime.UtcNow}"},
                {"ID", Guid.NewGuid().ToString()},
                {"IP", $"{context.Request.HttpContext.Connection.RemoteIpAddress}" },
                {"Schema", context.Request.Scheme},
                {"Path", context.Request.Path},
                {"QueryString", $"{context.Request.QueryString}"},
                {"Request Body", ReadStreamInChunks(requestStream)}
            };

            var requestJson = JsonConvert.SerializeObject(Request, Formatting.None);

            _logger.LogInformation(requestJson);

            context.Request.Body.Position = 0;
        }


        private async Task LogResponse(HttpContext context, Guid guid)
        {
            var originalBodyStream = context.Response.Body;

            await using var responseBody = _recyclableMemoryStreamManager.GetStream();
            context.Response.Body = responseBody;

            await _next(context);

            context.Response.Body.Seek(0, SeekOrigin.Begin);
            var text = await new StreamReader(context.Response.Body).ReadToEndAsync();
            context.Response.Body.Seek(0, SeekOrigin.Begin);

            var Response = new Dictionary<string, string>(){
                {"Request ID", guid.ToString()}
                {"Http Response Information", $"{DateTime.UtcNow}"},
                {"ID", Guid.NewGuid().ToString()},
                {"IP", $"{context.Request.HttpContext.Connection.RemoteIpAddress}" },
                {"Schema", context.Request.Scheme},
                {"Path", context.Request.Path },
                {"QueryString", $"{context.Request.QueryString}"},
                {"Response Body", text}
            };

            var responseJson = JsonConvert.SerializeObject(Response, Formatting.None);

            _logger.LogInformation(responseJson);

            await responseBody.CopyToAsync(originalBodyStream);
        }

        private static string ReadStreamInChunks(Stream stream)
        {
            const int readChunkBufferLength = 4096;

            stream.Seek(0, SeekOrigin.Begin);

            using var textWriter = new StringWriter();
            using var reader = new StreamReader(stream);

            var readChunk = new char[readChunkBufferLength];
            int readChunkLength;

            do
            {
                readChunkLength = reader.ReadBlock(readChunk, 0, readChunkBufferLength);
                textWriter.Write(readChunk, 0, readChunkLength);
            } while (readChunkLength > 0);

            return textWriter.ToString();
        }
公共类RequestResponseLoggingMiddleware
{
private readonly RequestDelegate\u next;
专用只读ILogger\u记录器;
私有只读可回收内存流管理器\u可回收内存流管理器;
公共RequestResponseLoggingMiddleware(RequestDelegate下一步,iLogger工厂loggerFactory)
{
_下一个=下一个;
_logger=loggerFactory.CreateLogger();
_recyclableMemoryStreamManager=新的recyclableMemoryStreamManager();
}
公共异步任务调用(HttpContext上下文)
{
var guid=guid.NewGuid();
等待日志请求(上下文、guid);
等待日志响应(上下文、guid);
}
专用异步任务日志请求(HttpContext上下文,Guid)
{
context.Request.enableBuffer();
使用var requestStream=_recyclableMemoryStreamManager.GetStream()等待;
wait context.Request.Body.CopyToAsync(requestStream);
var请求=新字典(){
{“请求ID”,guid.ToString()}
{“Http请求信息”,$“{DateTime.UtcNow}”,
{“ID”,Guid.NewGuid().ToString()},
{“IP”,$“{context.Request.HttpContext.Connection.RemoteIpAddress}”,
{“Schema”,context.Request.Scheme},
{“Path”,context.Request.Path},
{“QueryString”,$“{context.Request.QueryString}”,
{“请求正文”,ReadStreamInChunks(requestStream)}
};
var requestJson=JsonConvert.SerializeObject(请求,格式化.None);
_logger.LogInformation(requestJson);
context.Request.Body.Position=0;
}
专用异步任务日志响应(HttpContext上下文,Guid)
{
var originalBodyStream=context.Response.Body;
等待使用var responseBody=\u recyclableMemorySt
class GuidProvider {
   public string CorrelationId {get; private set;}
   public GuidProvider() {
      CorrelationId = Guid.NewGuid().ToString()
   }
}
services.AddScoped(typeof(GuidProvider));
public RequestResponseLoggingMiddleware(..., GuidProvider guidProvider) 
{ 
   guidProvider.CorrelationId; // should stay the same within request 
   ... 
}```