Warning: file_get_contents(/data/phpspider/zhask/data//catemap/0/asp.net-core/3.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# 使用Serilog ASP.NET Core复制错误消息_C#_Asp.net Core_Razor Pages_Serilog - Fatal编程技术网

C# 使用Serilog ASP.NET Core复制错误消息

C# 使用Serilog ASP.NET Core复制错误消息,c#,asp.net-core,razor-pages,serilog,C#,Asp.net Core,Razor Pages,Serilog,使用Serilog的ASP.NET Core 5 Razor页面 按预期工作,并在转到my/CustomError页面后重新执行页面 如何抑制对重新执行页面的第二次调用的Serilog日志记录 全样本 //program.cs 公共静态void Main(字符串[]args) { Logger.Logger=新的LoggerConfiguration() //如果仅执行警告,则在引发异常时将获得重复的错误消息,然后在重新执行时再次获得 //我们每个错误都会收到2条错误消息,但只有1条堆栈跟踪 .

使用Serilog的ASP.NET Core 5 Razor页面

按预期工作,并在转到my/CustomError页面后重新执行页面

如何抑制对重新执行页面的第二次调用的Serilog日志记录

全样本

//program.cs
公共静态void Main(字符串[]args)
{
Logger.Logger=新的LoggerConfiguration()
//如果仅执行警告,则在引发异常时将获得重复的错误消息,然后在重新执行时再次获得
//我们每个错误都会收到2条错误消息,但只有1条堆栈跟踪
.MinimumLevel.Override(“Microsoft.AspNetCore”,LogEventLevel.Fatal)
.Enrich.FromLogContext()的
.WriteTo.Console()
.CreateLogger();
尝试
{
日志信息(“启动”);
CreateHostBuilder(args.Build().Run();
}
捕获(例外情况除外)
{
Log.Fatal(例如,“应用程序启动失败”);
}
最后
{
Log.CloseAndFlush();
}
}
公共静态IHostBuilder CreateHostBuilder(字符串[]args)=>
Host.CreateDefaultBuilder(args)
.useserlog()//
{
webBuilder.UseStartup();
});
}
然后

公共类启动
{
public void配置服务(IServiceCollection服务)
{
//剪断
}
public void配置(IApplicationBuilder应用程序、IWebHostEnvironment环境)
{
if(env.IsDevelopment())
{
app.UseDeveloperExceptionPage();
}
其他的
{
app.UseExceptionHandler(“/CustomError”);
}
app.UseStaticFiles();
// https://khalidabuhakmeh.com/handle-http-status-codes-with-razor-pages
// https://andrewlock.net/retrieving-the-path-that-generated-an-error-with-the-statuscodepages-middleware/
app.UseStatusCodePagesWithReExecute(“/CustomError”,“?statusCode={0}”);
app.UseRouting();
//不希望对静态文件进行请求日志记录,所以将此serilog中间件放在管道中
app.useserlogrequestlogging();//
{
endpoints.MapRazorPages();
});
}
}
然后

//CustomError.cshtml.cs
[ResponseCache(持续时间=0,位置=ResponseCache位置。无,NoStore=true)]
[IgnoreAntiforgeryToken]
公共类CustomErrorModel:PageModel
{
public int?CustomStatusCode{get;set;}
公共无效OnGet(int?状态码=null)
{
var feature=HttpContext.Features.Get();
//非500 eg 404
//这可以是非页面请求,例如/js/site-chart.js
//当抛出500时,功能可以为null
如果(功能!=null)
{
//Log.Warning({feature.OriginalPath}上的$“Http状态代码{statusCode}”);
CustomStatusCode=状态代码;
返回;
}
//500美元
//依靠serilog输出错误
//var exceptionHandlerPathFeature=HttpContext.Features.Get();
//集成测试可以调用exceptionHandlerPathFeature可以为null的页面
CustomStatusCode=500;
//其他地方正在发送日志。错误stacktracke
//Log.Error($“异常为{exceptionHandlerPathFeature.Error}”);
//OriginalPath=exceptionHandlerPathFeature.Path;
//Exception Exception=exceptionHandlerPathFeature.Error;
}
邮政署公告
{
Log.Warning(“ASP.NET失败-可能是反伪造。被OnPost自定义错误捕获。可能向用户发送400”);
日志警告(“需要在Program.cs中取消最低级别覆盖以获取更多信息”);
CustomStatusCode=400;
}
}

错误的重复日志条目,如404-理想情况下只需要1

更新 感谢Alan在下面的回答,我将SerilogRequestLogging放在了配置的开头

public void配置(IApplicationBuilder应用程序,IWebHostEnvironment环境)
{
app.useserlogrequestlogging();
if(env.IsDevelopment())
{
app.UseDeveloperExceptionPage();
}
其他的
{
app.UseExceptionHandler(“/CustomError”);
}
app.UseStaticFiles();
app.UseStatusCodePagesWithReExecute(“/CustomError”,“?statusCode={0}”);
//剪断。。
}
这会在日志中显示2条
ERR
消息:

我同意

可能有一种方法可以合并2
ERR
条目,但这很简单。另外,这两个条目用于不同的概念。请求和例外情况

可以像样板文件Error.cshtml.cs提供的那样,为每个日志条目提供一个
RequestId

RequestId=Activity.Current?.Id??HttpContext.TraceIdentifier;
但是,这个解决方案对我来说已经足够好了。谢谢你,艾伦

简短答复: 在这种情况下,为了防止重复日志记录,您可以将
useserlogrequestlogging()
放在
UseStatusCodePagesWithReExecute()
配置方法中:

    app.UseSerilogRequestLogging();
    app.UseStatusCodePagesWithReExecute("/CustomError", "?statusCode={0}");

长答覆: 根据该协议,用于构建中间件的订单很重要:

启动中添加中间件组件的顺序。Configure
方法定义在请求时调用中间件组件的顺序以及响应的相反顺序。订单对于安全性、性能和功能至关重要

现在,根据,
useserlogrequestlogging
将只处理中间件管道中出现的组件

考虑到这一点,我注意到在
Startup
类中,您在
UseStatusCodePagesWithReExecute
之后添加了
UseSerilogRequestLogging
中间件

UseStatusCodePagesWithReExecute
说它做两件事:

  • 将原始状态代码返回给客户端
  • 通过使用备用路径重新执行请求管道来生成响应主体