Extended using exception as full log

alphons <alphons@heijden.com> 9 Apr 2026, 10:06
4b6ac0d8d00313e39623531f7c27b86208e565e3
10 files changed
  • src/VanDerHeijden.Logging.File/FileLoggingBuilderExtensions.cs
  • src/VanDerHeijden.Logging.File/VanDerHeijden.Logging.File.csproj
  • src/VanDerHeijden.Logging.MongoDb/MongoDbLoggingBuilderExtensions.cs
  • src/VanDerHeijden.Logging.MongoDb/VanDerHeijden.Logging.MongoDb.csproj
  • src/VanDerHeijden.Logging.Redis/RedisLoggingBuilderExtensions.cs
  • src/VanDerHeijden.Logging.Redis/VanDerHeijden.Logging.Redis.csproj
  • src/VanDerHeijden.Logging.Sql/SqlLoggingBuilderExtensions.cs
  • src/VanDerHeijden.Logging.Sql/VanDerHeijden.Logging.Sql.csproj
  • src/VanDerHeijden.Logging/BatchedLogger.cs
  • src/VanDerHeijden.Logging/VanDerHeijden.Logging.csproj
diff --git a/src/VanDerHeijden.Logging.File/FileLoggingBuilderExtensions.cs b/src/VanDerHeijden.Logging.File/FileLoggingBuilderExtensions.cs
index 67110a7..30b1437 100644
--- a/src/VanDerHeijden.Logging.File/FileLoggingBuilderExtensions.cs
+++ b/src/VanDerHeijden.Logging.File/FileLoggingBuilderExtensions.cs
@@ -30,10 +30,11 @@ public static class FileLoggingBuilderExtensions
var batchedLogger = new BatchedLogger<string>(logWriter, fullMode: BoundedChannelFullMode.Wait);
return new BatchedLoggerProvider<string>(
batchedLogger,
- entryFactory: (message, _, ctx) =>
+ entryFactory: (message, _, ctx, exception) =>
{
var http = ctx is null ? "" : $" [{ctx.Method} {ctx.Path} {ctx.ClientIp}]";
- return $"{DateTime.Now:yyyy-MM-dd HH:mm:ss.fff}{http} {message}{Environment.NewLine}";
+ var ex = exception is null ? "" : $"{Environment.NewLine}{exception}";
+ return $"{DateTime.Now:yyyy-MM-dd HH:mm:ss.fff}{http} {message}{ex}{Environment.NewLine}";
},
httpContextAccessor
);
diff --git a/src/VanDerHeijden.Logging.File/VanDerHeijden.Logging.File.csproj b/src/VanDerHeijden.Logging.File/VanDerHeijden.Logging.File.csproj
index 9ee1135..8ac1704 100644
--- a/src/VanDerHeijden.Logging.File/VanDerHeijden.Logging.File.csproj
+++ b/src/VanDerHeijden.Logging.File/VanDerHeijden.Logging.File.csproj
@@ -6,7 +6,7 @@
<Nullable>enable</Nullable>
<PackageId>VanDerHeijden.Logging.File</PackageId>
- <Version>10.0.6</Version>
+ <Version>10.0.7</Version>
<Authors>VanDerHeijden</Authors>
<Description>File log writer for VanDerHeijden.Logging: writes batched log entries to daily rotating text files.</Description>
<PackageTags>logging;file;batched</PackageTags>
diff --git a/src/VanDerHeijden.Logging.MongoDb/MongoDbLoggingBuilderExtensions.cs b/src/VanDerHeijden.Logging.MongoDb/MongoDbLoggingBuilderExtensions.cs
index 2edeb95..362b320 100644
--- a/src/VanDerHeijden.Logging.MongoDb/MongoDbLoggingBuilderExtensions.cs
+++ b/src/VanDerHeijden.Logging.MongoDb/MongoDbLoggingBuilderExtensions.cs
@@ -39,12 +39,13 @@ public static class MongoDbLoggingBuilderExtensions
var batchedLogger = new BatchedLogger<LogEntry>(logWriter, batchSize: 100, maxIdleMs: 3000, fullMode: BoundedChannelFullMode.DropOldest);
return new BatchedLoggerProvider<LogEntry>(
batchedLogger,
- entryFactory: (message, logLevel, ctx) => new LogEntry
+ entryFactory: (message, logLevel, ctx, exception) => new LogEntry
{
Timestamp = DateTime.UtcNow,
Level = logLevel.ToString(),
Category = message.Split(':')[0],
Message = message,
+ Exception = exception?.ToString(),
Path = ctx?.Path,
Method = ctx?.Method,
ClientIp = ctx?.ClientIp,
diff --git a/src/VanDerHeijden.Logging.MongoDb/VanDerHeijden.Logging.MongoDb.csproj b/src/VanDerHeijden.Logging.MongoDb/VanDerHeijden.Logging.MongoDb.csproj
index 3c8fccb..9ac1a5f 100644
--- a/src/VanDerHeijden.Logging.MongoDb/VanDerHeijden.Logging.MongoDb.csproj
+++ b/src/VanDerHeijden.Logging.MongoDb/VanDerHeijden.Logging.MongoDb.csproj
@@ -6,7 +6,7 @@
<Nullable>enable</Nullable>
<PackageId>VanDerHeijden.Logging.MongoDb</PackageId>
- <Version>10.0.7</Version>
+ <Version>10.0.8</Version>
<Authors>VanDerHeijden</Authors>
<Description>MongoDB log writer for VanDerHeijden.Logging: writes batched log entries to a MongoDB collection.</Description>
<PackageTags>logging;mongodb;batched</PackageTags>
diff --git a/src/VanDerHeijden.Logging.Redis/RedisLoggingBuilderExtensions.cs b/src/VanDerHeijden.Logging.Redis/RedisLoggingBuilderExtensions.cs
index 8574e80..4e23fba 100644
--- a/src/VanDerHeijden.Logging.Redis/RedisLoggingBuilderExtensions.cs
+++ b/src/VanDerHeijden.Logging.Redis/RedisLoggingBuilderExtensions.cs
@@ -35,12 +35,13 @@ public static class RedisLoggingBuilderExtensions
var batchedLogger = new BatchedLogger<RedisLogEntry>(logWriter, batchSize: 200, maxIdleMs: 2000, fullMode: BoundedChannelFullMode.DropOldest);
return new BatchedLoggerProvider<RedisLogEntry>(
batchedLogger,
- entryFactory: (message, logLevel, ctx) => new RedisLogEntry
+ entryFactory: (message, logLevel, ctx, exception) => new RedisLogEntry
{
Timestamp = DateTime.UtcNow,
Level = logLevel.ToString(),
Category = message.Split(':')[0],
Message = message,
+ Exception = exception?.ToString(),
Path = ctx?.Path,
Method = ctx?.Method,
ClientIp = ctx?.ClientIp,
diff --git a/src/VanDerHeijden.Logging.Redis/VanDerHeijden.Logging.Redis.csproj b/src/VanDerHeijden.Logging.Redis/VanDerHeijden.Logging.Redis.csproj
index c3850e8..f78213a 100644
--- a/src/VanDerHeijden.Logging.Redis/VanDerHeijden.Logging.Redis.csproj
+++ b/src/VanDerHeijden.Logging.Redis/VanDerHeijden.Logging.Redis.csproj
@@ -6,7 +6,7 @@
<Nullable>enable</Nullable>
<PackageId>VanDerHeijden.Logging.Redis</PackageId>
- <Version>10.0.6</Version>
+ <Version>10.0.7</Version>
<Authors>VanDerHeijden</Authors>
<Description>Redis log writer for VanDerHeijden.Logging: writes batched log entries to a Redis list using RPUSH.</Description>
<PackageTags>logging;redis;batched</PackageTags>
diff --git a/src/VanDerHeijden.Logging.Sql/SqlLoggingBuilderExtensions.cs b/src/VanDerHeijden.Logging.Sql/SqlLoggingBuilderExtensions.cs
index 29b52a2..aaea802 100644
--- a/src/VanDerHeijden.Logging.Sql/SqlLoggingBuilderExtensions.cs
+++ b/src/VanDerHeijden.Logging.Sql/SqlLoggingBuilderExtensions.cs
@@ -32,12 +32,13 @@ public static class SqlLoggingBuilderExtensions
var batchedLogger = new BatchedLogger<SqlLogEntry>(logWriter, batchSize: 200, maxIdleMs: 4000, fullMode: BoundedChannelFullMode.Wait);
return new BatchedLoggerProvider<SqlLogEntry>(
batchedLogger,
- entryFactory: (message, logLevel, ctx) => new SqlLogEntry
+ entryFactory: (message, logLevel, ctx, exception) => new SqlLogEntry
{
Timestamp = DateTime.UtcNow,
Level = logLevel.ToString(),
Category = message.Split(':')[0],
Message = message,
+ Exception = exception?.ToString(),
Path = ctx?.Path,
Method = ctx?.Method,
ClientIp = ctx?.ClientIp,
diff --git a/src/VanDerHeijden.Logging.Sql/VanDerHeijden.Logging.Sql.csproj b/src/VanDerHeijden.Logging.Sql/VanDerHeijden.Logging.Sql.csproj
index c56b2eb..3a83094 100644
--- a/src/VanDerHeijden.Logging.Sql/VanDerHeijden.Logging.Sql.csproj
+++ b/src/VanDerHeijden.Logging.Sql/VanDerHeijden.Logging.Sql.csproj
@@ -6,7 +6,7 @@
<Nullable>enable</Nullable>
<PackageId>VanDerHeijden.Logging.Sql</PackageId>
- <Version>10.0.6</Version>
+ <Version>10.0.7</Version>
<Authors>VanDerHeijden</Authors>
<Description>SQL Server log writer for VanDerHeijden.Logging: writes batched log entries to a SQL Server table using SqlBulkCopy.</Description>
<PackageTags>logging;sql;sqlserver;batched</PackageTags>
diff --git a/src/VanDerHeijden.Logging/BatchedLogger.cs b/src/VanDerHeijden.Logging/BatchedLogger.cs
index 5d66d8a..f3309d1 100644
--- a/src/VanDerHeijden.Logging/BatchedLogger.cs
+++ b/src/VanDerHeijden.Logging/BatchedLogger.cs
@@ -161,8 +161,8 @@ public sealed class BatchedLogger<T> : IDisposable
/// <typeparam name="T">The type of log entry produced by <paramref name="entryFactory"/>.</typeparam>
/// <param name="batchedLogger">The shared batched logger used by all created loggers.</param>
/// <param name="entryFactory">
-/// A factory that converts a formatted message, <see cref="LogLevel"/>, and optional <see cref="HttpLogContext"/>
-/// into a <typeparamref name="T"/> entry.
+/// A factory that converts a formatted message, <see cref="LogLevel"/>, an optional <see cref="HttpLogContext"/>,
+/// and an optional <see cref="Exception"/> into a <typeparamref name="T"/> entry.
/// </param>
/// <param name="httpContextAccessor">
/// Optional <see cref="IHttpContextAccessor"/> used to enrich log entries with request metadata.
@@ -170,7 +170,7 @@ public sealed class BatchedLogger<T> : IDisposable
/// </param>
public sealed class BatchedLoggerProvider<T>(
BatchedLogger<T> batchedLogger,
- Func<string, LogLevel, HttpLogContext?, T> entryFactory,
+ Func<string, LogLevel, HttpLogContext?, Exception?, T> entryFactory,
IHttpContextAccessor? httpContextAccessor = null) : ILoggerProvider
{
/// <summary>
@@ -190,7 +190,7 @@ public sealed class BatchedLoggerProvider<T>(
internal sealed class BatchedCategoryLogger<T>(
BatchedLogger<T> batchedLogger,
string categoryName,
- Func<string, LogLevel, HttpLogContext?, T> entryFactory,
+ Func<string, LogLevel, HttpLogContext?, Exception?, T> entryFactory,
IHttpContextAccessor? httpContextAccessor) : ILogger
{
public IDisposable? BeginScope<TState>(TState state) where TState : notnull => null;
@@ -199,8 +199,8 @@ internal sealed class BatchedCategoryLogger<T>(
public void Log<TState>(LogLevel logLevel, EventId eventId, TState state, Exception? exception, Func<TState, Exception?, string> formatter)
{
if (!IsEnabled(logLevel)) return;
- var message = $"{categoryName}: {formatter(state, exception)}{(exception != null ? $"{Environment.NewLine}{exception}" : "")}";
- batchedLogger.Write(entryFactory(message, logLevel, BuildHttpContext()));
+ var message = $"{categoryName}: {formatter(state, exception)}";
+ batchedLogger.Write(entryFactory(message, logLevel, BuildHttpContext(), exception));
}
private HttpLogContext? BuildHttpContext()
diff --git a/src/VanDerHeijden.Logging/VanDerHeijden.Logging.csproj b/src/VanDerHeijden.Logging/VanDerHeijden.Logging.csproj
index 8e901b2..02b5c27 100644
--- a/src/VanDerHeijden.Logging/VanDerHeijden.Logging.csproj
+++ b/src/VanDerHeijden.Logging/VanDerHeijden.Logging.csproj
@@ -6,7 +6,7 @@
<Nullable>enable</Nullable>
<PackageId>VanDerHeijden.Logging</PackageId>
- <Version>10.0.6</Version>
+ <Version>10.0.7</Version>
<Authors>VanDerHeijden</Authors>
<Description>Core batched logging abstractions for .NET: IBatchedLogWriter&lt;T&gt;, BatchedLogger&lt;T&gt; and BatchedLoggerProvider&lt;T&gt;.</Description>
<PackageTags>logging;batched;core</PackageTags>