Skip to content

Nested BeginScope doesn't replace existing keys #267

Closed
@RogueJay

Description

@RogueJay

In version 8, if you nested a BeginScope using the same KeyValue pair, the inner scope would use the newest value.
In version 9, the inner scope value does not replace the existing value.

The following is an XUnit test that works in 8 and fails in 9

		[Fact]
		public void LoggingScope_ReplaceExecutionTagProperty_yWhenCalledTwicetest()
		{
			// Create a context for this specific test to isolate log messages
			using (Serilog.Sinks.TestCorrelator.TestCorrelator.CreateContext())
			using (var logger = new Serilog.LoggerConfiguration().WriteTo.Sink(new TestCorrelatorSink()).Enrich.FromLogContext().CreateLogger())
			{
				Log.Logger = logger;

				var services = new ServiceCollection();
				services.AddLogging(l => l.AddSerilog());

				using var serviceProvider = services.BuildServiceProvider();
				var msLogger = serviceProvider.GetRequiredService<ILogger<Program>>();

				using (msLogger.BeginScope(new Dictionary<string, object> { { ContextProperties.EXECUTION_TAGS, "[TAG1]" } }))
				{
					msLogger.LogInformation("Message1");
					using (msLogger.BeginScope(new Dictionary<string, object> { { ContextProperties.EXECUTION_TAGS, "[TAG2]" } }))
					{
						msLogger.LogInformation("Message2");
					}
				}

				var logEvent = GetLogEvent("Message1");
				Assert.NotNull(logEvent);
				ValidateProperty(logEvent, ContextProperties.EXECUTION_TAGS, "[TAG1]");

				logEvent = GetLogEvent("Message2");
				Assert.NotNull(logEvent);
				ValidateProperty(logEvent, ContextProperties.EXECUTION_TAGS, "[TAG2]");   <-- FAILS BECAUSE TAG1 IS STILL USED
			}
		}

		private static LogEvent? GetLogEvent(string message)
			=> TestCorrelator.GetLogEventsFromCurrentContext().FirstOrDefault(e => e.MessageTemplate.Text == message);

		private static void ValidateProperty(LogEvent logEvent, string name, string value)
		{
			Assert.Contains(name, logEvent.Properties.Keys);
			Assert.True(logEvent.Properties.TryGetValue(name, out LogEventPropertyValue? result));
			Assert.Equal(value, result.ToString().Replace("\"", ""));
		}

I don't know if this is related, but looking at the stack at the point Message2 is about to be logged, I see the following. For version 8.0, the Scopes variable is null

Image

Metadata

Metadata

Assignees

No one assigned

    Labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions