Is there anyway to enrich all Serilog output with the Method Name.
For Instance consider If I have the following;
Public Class MyClassName
Private Function MyFunctionName() As Boolean
Logger.Information("Hello World")
Return True
End Function
End Class
The desired output would be as follows;
2015-04-06 18:41:35.361 +10:00 [Information] [MyFunctionName] Hello World!
Actually the Fully Qualified Name would be good.
2015-04-06 18:41:35.361 +10:00 [Information] [MyClassName.MyFunctionName] Hello World!
It seems that "Enrichers" are only good for Static Information and won't work each time.
It's possible to do this with an enricher by reflecting over the call stack, but very expensive to do so, so Serilog doesn't offer it.
Instead you can use something like:
Logger.Here().Information("Hello, world!");
and implement the Here()
method as an extension method on ILogger
:
<Extension>
Public Sub Here(ByVal logger as ILogger,
<CallerMemberName> Optional memberName As String = Nothing)
Return logger.ForContext("MemberName", memberName)
End Sub
in case you need a version in C#:
public static class LoggerExtensions
{
public static ILogger Here(this ILogger logger,
[CallerMemberName] string memberName = "",
[CallerFilePath] string sourceFilePath = "",
[CallerLineNumber] int sourceLineNumber = 0) {
return logger
.ForContext("MemberName", memberName)
.ForContext("FilePath", sourceFilePath)
.ForContext("LineNumber", sourceLineNumber);
}
}
use like this:
Logger.Here().Information("Hello, world!");
Remember to add those properties in the message template. You can use something like this:
var outputTemplate = "[{Timestamp:HH:mm:ss} {Level}] {SourceContext}{NewLine}{Message}{NewLine}in method {MemberName} at {FilePath}:{LineNumber}{NewLine}{Exception}{NewLine}";
Log.Logger = new LoggerConfiguration()
.MinimumLevel.Warning()
.Enrich.FromLogContext()
.WriteTo.RollingFile("log/{Date}.log", outputTemplate, LogEventLevel.Warning)
.WriteTo.Console(LogEventLevel.Warning, outputTemplate, theme: AnsiConsoleTheme.Literate)
.CreateLogger();
In outputTemplate for the Serilog , configure for logs to write Properties
. Method name will be written as part of ActionName
column.
ActionName
can also be configured individually (instead of all properties) in outputTemplate.
Configuring Properties/ActionName
will write the method name in Namespace.ClassName.MethodName
format.
The version on C# could be simplified. Just use AutofacSerilogIntegration:
var path = Server.MapPath("~/");
var outputTemplate = "[{Timestamp:HH:mm:ss} {Level:u3}] {SourceContext} {Message} {NewLine}{Exception}";
Log.Logger = new LoggerConfiguration()
.MinimumLevel.Debug()
.WriteTo.File($"{path}/log/serilog-.log", LogEventLevel.Debug, outputTemplate, rollingInterval: RollingInterval.Day)
.CreateLogger();
var builder = new ContainerBuilder();
builder.RegisterLogger(); // from AutofacSerilogIntegration
builder.RegisterControllers(typeof(MvcApplication).Assembly);
var container = builder.Build();
DependencyResolver.SetResolver(new AutofacDependencyResolver(container));
Based on MovGP0's answer (for C#),
I created a solution that doesn't require the Here()
-Method in every line where you want to log, by simply adding a custom Log.cs
-Class in the root namespace.
For more info see: https://gist.github.com/litetex/b88fe0531e5acea82df1189643fb1f79
来源:https://stackoverflow.com/questions/29470863/serilog-output-enrich-all-messages-with-methodname-from-which-log-entry-was-ca