Skip to content

Commit 1ece34b

Browse files
log context-info if available
1 parent 1b4a3ac commit 1ece34b

3 files changed

Lines changed: 65 additions & 5 deletions

File tree

Olive/Logging/FileLogger/BatchingLogger.cs

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -34,6 +34,9 @@ public virtual void Log<TState>(DateTimeOffset timestamp, LogLevel logLevel, Eve
3434

3535
if (exception != null) r.AppendLine(exception.ToFullMessage());
3636

37+
var contextInfo = Olive.Log.ContextProvider?.Invoke();
38+
if (contextInfo.HasValue()) r.AppendLine(contextInfo);
39+
3740
Provider.AddMessage(timestamp, r.ToString(), exception?.GetUsefulStack(), (int)logLevel);
3841
}
3942

Olive/Logging/Log.cs

Lines changed: 61 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -3,16 +3,17 @@
33
using Microsoft.Extensions.Logging;
44
using System;
55
using System.ComponentModel;
6+
using System.Security.Claims;
67
using System.Text;
78

89
namespace Olive
910
{
1011
public static class LogExtensions
1112
{
12-
public static ILoggingBuilder AddFile(this ILoggingBuilder @this, Action<FileLoggerOptions> configure = null)
13+
public static ILoggingBuilder AddFile(this ILoggingBuilder @this, Action<FileLoggerOptions> configure = null)
1314
{
14-
@this.Services.AddSingleton<ILoggerProvider, FileLoggerProvider>();
15-
if (configure != null) @this.Services.Configure(configure);
15+
@this.Services.AddSingleton<ILoggerProvider, FileLoggerProvider>();
16+
if (configure != null) @this.Services.Configure(configure);
1617
return @this;
1718
}
1819

@@ -53,7 +54,7 @@ static string ToYaml(string description, object relatedObject, string userId, st
5354
{
5455
r.Append(" Description: ");
5556
var firstLine = true;
56-
57+
5758
foreach (var line in description.ToLines().Trim())
5859
{
5960
if (!firstLine) r.Append(" Description: ".Length);
@@ -70,6 +71,11 @@ public static class Log
7071
{
7172
public static ILoggerFactory Factory { get; private set; }
7273

74+
/// <summary>
75+
/// When set, provides contextual information (e.g. UserId, RequestUrl, UserIP) to append to log entries.
76+
/// </summary>
77+
public static Func<string> ContextProvider { get; set; }
78+
7379
[EditorBrowsable(EditorBrowsableState.Never)]
7480
public static void Init(Action<ILoggingBuilder> configure = null)
7581
{
@@ -97,6 +103,57 @@ public static void Init(ILoggerFactory factory)
97103
{
98104
if (Factory != null) return;
99105
Factory = factory;
106+
InitDefaultContextProvider();
107+
}
108+
109+
static void InitDefaultContextProvider()
110+
{
111+
var httpContextAccessorType = Type.GetType(
112+
"Microsoft.AspNetCore.Http.IHttpContextAccessor, Microsoft.AspNetCore.Http.Abstractions");
113+
114+
if (httpContextAccessorType == null) return;
115+
116+
var httpContextProp = httpContextAccessorType.GetProperty("HttpContext");
117+
118+
ContextProvider = () =>
119+
{
120+
try
121+
{
122+
var accessor = Context.Current.GetOptionalService(httpContextAccessorType);
123+
if (accessor == null) return null;
124+
125+
var httpContext = httpContextProp?.GetValue(accessor);
126+
if (httpContext == null) return null;
127+
128+
var contextType = httpContext.GetType();
129+
130+
var user = contextType.GetProperty("User")?.GetValue(httpContext) as ClaimsPrincipal;
131+
var userId = user?.GetId();
132+
133+
var request = contextType.GetProperty("Request")?.GetValue(httpContext);
134+
string requestUrl = null;
135+
if (request != null)
136+
{
137+
var reqType = request.GetType();
138+
var pathBase = reqType.GetProperty("PathBase")?.GetValue(request)?.ToString();
139+
var path = reqType.GetProperty("Path")?.GetValue(request)?.ToString();
140+
var queryString = reqType.GetProperty("QueryString")?.GetValue(request)?.ToString();
141+
requestUrl = $"{pathBase}{path}{queryString}";
142+
}
143+
144+
var connection = contextType.GetProperty("Connection")?.GetValue(httpContext);
145+
var userIp = connection?.GetType().GetProperty("RemoteIpAddress")?.GetValue(connection)?.ToString();
146+
147+
if (userId.IsEmpty() && requestUrl.IsEmpty() && userIp.IsEmpty()) return null;
148+
149+
var r = new StringBuilder();
150+
if (userId.HasValue()) r.AppendLine($" UserId: {userId}");
151+
if (requestUrl.HasValue()) r.AppendLine($" RequestUrl: {requestUrl}");
152+
if (userIp.HasValue()) r.AppendLine($" UserIP: {userIp}");
153+
return r.ToString().TrimEnd();
154+
}
155+
catch { return null; }
156+
};
100157
}
101158
public static bool AddProvider<TProvider>() where TProvider : ILoggerProvider
102159
{

Olive/Olive.csproj

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
<Project Sdk="Microsoft.NET.Sdk">
22
<PropertyGroup>
33
<TargetFramework>netstandard2.0</TargetFramework>
4-
<Version>8.3.0</Version>
4+
<Version>8.3.1</Version>
55
<OutputType>Library</OutputType>
66
<LangVersion>latest</LangVersion>
77
<Authors>Geeks Ltd, UK</Authors>

0 commit comments

Comments
 (0)