Skip to content

6.0.0 Release #292

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 8 commits into from
Jul 14, 2022
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
12 changes: 7 additions & 5 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -285,11 +285,13 @@ The Azure Diagnostic Log Stream ships events from any files in the `D:\home\LogF
.WriteTo.Console()
// Add this line:
.WriteTo.File(
@"D:\home\LogFiles\Application\myapp.txt",
fileSizeLimitBytes: 1_000_000,
rollOnFileSizeLimit: true,
shared: true,
flushToDiskInterval: TimeSpan.FromSeconds(1))
System.IO.Path.Combine(Environment.GetEnvironmentVariable("HOME"), "LogFiles", "Application", "diagnostics.txt"),
rollingInterval: RollingInterval.Day,
fileSizeLimitBytes: 10 * 1024 * 1024,
retainedFileCountLimit: 2,
rollOnFileSizeLimit: true,
shared: true,
flushToDiskInterval: TimeSpan.FromSeconds(1))
.CreateLogger();
```

Expand Down
4 changes: 2 additions & 2 deletions src/Serilog.AspNetCore/AspNetCore/RequestLoggingMiddleware.cs
Original file line number Diff line number Diff line change
Expand Up @@ -86,7 +86,7 @@ bool LogCompletion(HttpContext httpContext, DiagnosticContextCollector collector
// Enrich diagnostic context
_enrichDiagnosticContext?.Invoke(_diagnosticContext, httpContext);

if (!collector.TryComplete(out var collectedProperties))
if (!collector.TryComplete(out var collectedProperties, out var collectedException))
collectedProperties = NoProperties;

// Last-in (correctly) wins...
Expand All @@ -98,7 +98,7 @@ bool LogCompletion(HttpContext httpContext, DiagnosticContextCollector collector
new LogEventProperty("Elapsed", new ScalarValue(elapsedMs))
});

var evt = new LogEvent(DateTimeOffset.Now, level, ex, _messageTemplate, properties);
var evt = new LogEvent(DateTimeOffset.Now, level, ex ?? collectedException, _messageTemplate, properties);
logger.Write(evt);

return false;
Expand Down
4 changes: 2 additions & 2 deletions src/Serilog.AspNetCore/Serilog.AspNetCore.csproj
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@

<PropertyGroup>
<Description>Serilog support for ASP.NET Core logging</Description>
<VersionPrefix>5.0.0</VersionPrefix>
<VersionPrefix>6.0.0</VersionPrefix>
<Authors>Microsoft;Serilog Contributors</Authors>
<TargetFrameworks>netstandard2.0;netstandard2.1;netcoreapp3.1;net5.0</TargetFrameworks>
<TreatWarningsAsErrors>true</TreatWarningsAsErrors>
Expand Down Expand Up @@ -30,7 +30,7 @@

<ItemGroup>
<PackageReference Include="Serilog" Version="2.10.0" />
<PackageReference Include="Serilog.Extensions.Hosting" Version="4.2.0" />
<PackageReference Include="Serilog.Extensions.Hosting" Version="5.0.0" />
<PackageReference Include="Serilog.Sinks.Console" Version="4.0.1" />
<PackageReference Include="Serilog.Sinks.File" Version="5.0.0" />
<PackageReference Include="Serilog.Sinks.Debug" Version="2.0.0" />
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@
using Microsoft.AspNetCore.Hosting;
using Microsoft.AspNetCore.Mvc.Testing;
using Microsoft.AspNetCore.Builder;
using Microsoft.AspNetCore.Http;
using Serilog.Filters;
using Serilog.AspNetCore.Tests.Support;

Expand Down Expand Up @@ -65,7 +66,51 @@ public async Task RequestLoggingMiddlewareShouldEnrich()
Assert.True(completionEvent.Properties.ContainsKey("Elapsed"));
}

WebApplicationFactory<TestStartup> Setup(ILogger logger, bool dispose, Action<RequestLoggingOptions> configureOptions = null)
[Fact]
public async Task RequestLoggingMiddlewareShouldEnrichWithCollectedExceptionIfNoUnhandledException()
{
var diagnosticContextException = new Exception("Exception set in diagnostic context");
var (sink, web) = Setup(options =>
{
options.EnrichDiagnosticContext += (diagnosticContext, _) =>
{
diagnosticContext.SetException(diagnosticContextException);
};
});

await web.CreateClient().GetAsync("/resource");

var completionEvent = sink.Writes.First(logEvent => Matching.FromSource<RequestLoggingMiddleware>()(logEvent));

Assert.Same(diagnosticContextException, completionEvent.Exception);
}

[Theory]
[InlineData(false)]
[InlineData(true)]
public async Task RequestLoggingMiddlewareShouldEnrichWithUnhandledExceptionEvenIfExceptionIsSetInDiagnosticContext(bool setExceptionInDiagnosticContext)
{
var diagnosticContextException = new Exception("Exception set in diagnostic context");
var unhandledException = new Exception("Unhandled exception thrown in API action");
var (sink, web) = Setup(options =>
{
options.EnrichDiagnosticContext += (diagnosticContext, _) =>
{
if (setExceptionInDiagnosticContext)
diagnosticContext.SetException(diagnosticContextException);
};
}, actionCallback: _ => throw unhandledException);

Func<Task> act = () => web.CreateClient().GetAsync("/resource");

Exception thrownException = await Assert.ThrowsAsync<Exception>(act);
var completionEvent = sink.Writes.First(logEvent => Matching.FromSource<RequestLoggingMiddleware>()(logEvent));
Assert.Same(unhandledException, completionEvent.Exception);
Assert.Same(unhandledException, thrownException);
}

WebApplicationFactory<TestStartup> Setup(ILogger logger, bool dispose, Action<RequestLoggingOptions> configureOptions = null,
Action<HttpContext> actionCallback = null)
{
var web = _web.WithWebHostBuilder(
builder => builder
Expand All @@ -80,24 +125,29 @@ WebApplicationFactory<TestStartup> Setup(ILogger logger, bool dispose, Action<Re
.Configure(app =>
{
app.UseSerilogRequestLogging(configureOptions);
app.Run(_ => Task.CompletedTask); // 200 OK
app.Run(ctx =>
{
actionCallback?.Invoke(ctx);
return Task.CompletedTask;
}); // 200 OK
})
.UseSerilog(logger, dispose));

return web;
}

(SerilogSink, WebApplicationFactory<TestStartup>) Setup(Action<RequestLoggingOptions> configureOptions = null)
(SerilogSink, WebApplicationFactory<TestStartup>) Setup(Action<RequestLoggingOptions> configureOptions = null,
Action<HttpContext> actionCallback = null)
{
var sink = new SerilogSink();
var logger = new LoggerConfiguration()
.Enrich.FromLogContext()
.WriteTo.Sink(sink)
.CreateLogger();

var web = Setup(logger, true, configureOptions);
var web = Setup(logger, true, configureOptions, actionCallback);

return (sink, web);
}
}
}
}