Skip to content
Merged
Show file tree
Hide file tree
Changes from 3 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
1 change: 1 addition & 0 deletions docs/list-of-diagnostics.md
Original file line number Diff line number Diff line change
Expand Up @@ -51,6 +51,7 @@ You may continue using obsolete APIs in your application, but we advise explorin
| Diagnostic ID | Description |
| :---------------- | :---------- |
| `EXTOBS0001` | This API is obsolete and will be removed in a future version. Consider using [Resource Monitoring observable instruments](https://learn.microsoft.com/dotnet/core/diagnostics/built-in-metrics-diagnostics#microsoftextensionsdiagnosticsresourcemonitoring). |
| `EXTOBS0002` | This API is obsolete and will be removed in a future version. Instead of the AddServiceLogEnricher() methods, consider using the respective AddApplicationLogEnricher() methods. |

# LoggerMessage

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,10 @@
// The .NET Foundation licenses this file to you under the MIT license.

using System;
using System.Diagnostics.CodeAnalysis;
using Microsoft.Extensions.Configuration;
using Microsoft.Extensions.Diagnostics.Enrichment;
using Microsoft.Shared.DiagnosticIds;
using Microsoft.Shared.Diagnostics;

namespace Microsoft.Extensions.DependencyInjection;
Expand All @@ -19,22 +21,65 @@ public static class ApplicationEnricherServiceCollectionExtensions
/// <param name="services">The <see cref="IServiceCollection"/> to add the service enricher to.</param>
/// <returns>The value of <paramref name="services"/>.</returns>
/// <exception cref="ArgumentNullException"><paramref name="services"/> is <see langword="null"/>.</exception>
public static IServiceCollection AddServiceLogEnricher(this IServiceCollection services)
[Obsolete(
DiagnosticIds.Obsoletions.ObsoleteTelemetryApiMessage,
DiagnosticId = DiagnosticIds.Obsoletions.ObsoleteTelemetryApiDiagId,
UrlFormat = DiagnosticIds.UrlFormat)]
public static IServiceCollection AddServiceLogEnricher(this IServiceCollection services) =>
services.AddApplicationLogEnricher(_ => { });

/// <summary>
/// Adds an instance of the service enricher to the <see cref="IServiceCollection"/>.
/// </summary>
/// <param name="services">The <see cref="IServiceCollection"/> to add the service enricher to.</param>
/// <param name="configure">The <see cref="ApplicationLogEnricherOptions"/> configuration delegate.</param>
/// <returns>The value of <paramref name="services"/>.</returns>
/// <exception cref="ArgumentNullException">Any of the arguments is <see langword="null"/>.</exception>
[Obsolete(
DiagnosticIds.Obsoletions.ObsoleteTelemetryApiMessage,
DiagnosticId = DiagnosticIds.Obsoletions.ObsoleteTelemetryApiDiagId,
UrlFormat = DiagnosticIds.UrlFormat)]
public static IServiceCollection AddServiceLogEnricher(this IServiceCollection services, Action<ApplicationLogEnricherOptions> configure) =>
services.AddApplicationLogEnricher(configure);

/// <summary>
/// Adds an instance of the service enricher to the <see cref="IServiceCollection"/>.
/// </summary>
/// <param name="services">The <see cref="IServiceCollection"/> to add the service enricher to.</param>
/// <param name="section">The <see cref="IConfigurationSection"/> to use for configuring <see cref="ApplicationLogEnricherOptions"/> in the service enricher.</param>
/// <returns>The value of <paramref name="services"/>.</returns>
/// <exception cref="ArgumentNullException">Any of the arguments is <see langword="null"/>.</exception>
[Obsolete(
DiagnosticIds.Obsoletions.ObsoleteTelemetryApiMessage,
DiagnosticId = DiagnosticIds.Obsoletions.ObsoleteTelemetryApiDiagId,
UrlFormat = DiagnosticIds.UrlFormat)]
public static IServiceCollection AddServiceLogEnricher(this IServiceCollection services, IConfigurationSection section) =>
services.AddApplicationLogEnricher(section);

/// <summary>
/// Adds an instance of the application enricher to the <see cref="IServiceCollection"/>.
/// </summary>
/// <param name="services">The <see cref="IServiceCollection"/> to add application enricher to.</param>
/// <returns>The value of <paramref name="services"/>.</returns>
/// <exception cref="ArgumentNullException"><paramref name="services"/> is <see langword="null"/>.</exception>
[Experimental(diagnosticId: DiagnosticIds.Experiments.Telemetry, UrlFormat = DiagnosticIds.UrlFormat)]
public static IServiceCollection AddApplicationLogEnricher(this IServiceCollection services)
{
_ = Throw.IfNull(services);

return services
.AddServiceLogEnricher(_ => { });
.AddApplicationLogEnricher(_ => { });
}

/// <summary>
/// Adds an instance of the service enricher to the <see cref="IServiceCollection"/>.
/// Adds an instance of the application enricher to the <see cref="IServiceCollection"/>.
/// </summary>
/// <param name="services">The <see cref="IServiceCollection"/> to add the service enricher to.</param>
/// <param name="services">The <see cref="IServiceCollection"/> to add the application enricher to.</param>
/// <param name="configure">The <see cref="ApplicationLogEnricherOptions"/> configuration delegate.</param>
/// <returns>The value of <paramref name="services"/>.</returns>
/// <exception cref="ArgumentNullException">Any of the arguments is <see langword="null"/>.</exception>
public static IServiceCollection AddServiceLogEnricher(this IServiceCollection services, Action<ApplicationLogEnricherOptions> configure)
[Experimental(diagnosticId: DiagnosticIds.Experiments.Telemetry, UrlFormat = DiagnosticIds.UrlFormat)]
public static IServiceCollection AddApplicationLogEnricher(this IServiceCollection services, Action<ApplicationLogEnricherOptions> configure)
{
_ = Throw.IfNull(services);
_ = Throw.IfNull(configure);
Expand All @@ -45,13 +90,14 @@ public static IServiceCollection AddServiceLogEnricher(this IServiceCollection s
}

/// <summary>
/// Adds an instance of the service enricher to the <see cref="IServiceCollection"/>.
/// Adds an instance of the application enricher to the <see cref="IServiceCollection"/>.
/// </summary>
/// <param name="services">The <see cref="IServiceCollection"/> to add the service enricher to.</param>
/// <param name="services">The <see cref="IServiceCollection"/> to add the application enricher to.</param>
/// <param name="section">The <see cref="IConfigurationSection"/> to use for configuring <see cref="ApplicationLogEnricherOptions"/> in the service enricher.</param>
/// <returns>The value of <paramref name="services"/>.</returns>
/// <exception cref="ArgumentNullException">Any of the arguments is <see langword="null"/>.</exception>
public static IServiceCollection AddServiceLogEnricher(this IServiceCollection services, IConfigurationSection section)
[Experimental(diagnosticId: DiagnosticIds.Experiments.Telemetry, UrlFormat = DiagnosticIds.UrlFormat)]
public static IServiceCollection AddApplicationLogEnricher(this IServiceCollection services, IConfigurationSection section)
{
_ = Throw.IfNull(services);
_ = Throw.IfNull(section);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@
namespace Microsoft.Extensions.Diagnostics.Enrichment;

/// <summary>
/// Options for the service log enricher.
/// Options for the application log enricher.
/// </summary>
public class ApplicationLogEnricherOptions
{
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@
<Workstream>Telemetry</Workstream>
<!-- disable "Published symbols cannot be deleted to maintain compatibility" because we have different APIs for different TFMs -->
<NoWarn Condition="!$([MSBuild]::IsTargetFrameworkCompatible('$(TargetFramework)', 'net9.0'))">$(NoWarn);LA0006</NoWarn>
<NoWarn Condition="!$([MSBuild]::IsTargetFrameworkCompatible('$(TargetFramework)', 'net8.0'))">$(NoWarn);CS0436</NoWarn>
</PropertyGroup>

<PropertyGroup>
Expand All @@ -20,6 +21,7 @@
<InjectSharedNumericExtensions>true</InjectSharedNumericExtensions>
<InjectSharedPools>true</InjectSharedPools>
<InjectSharedRentedSpan>true</InjectSharedRentedSpan>
<InjectObsoleteAttributeOnLegacy>true</InjectObsoleteAttributeOnLegacy>
<EnableConfigurationBindingGenerator>true</EnableConfigurationBindingGenerator>
<UseLoggingGenerator>true</UseLoggingGenerator>
</PropertyGroup>
Expand Down
10 changes: 5 additions & 5 deletions src/Libraries/Microsoft.Extensions.Telemetry/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -126,16 +126,16 @@ revisited in future. Namely, this library uses `Microsoft.Extensions.Logging.Abs
- `Microsoft.Extensions.Logging.Abstractions.BufferedLogRecord.ManagedThreadId`
- `Microsoft.Extensions.Logging.Abstractions.BufferedLogRecord.MessageTemplate`

### Service Log Enrichment
### Application Log Enrichment

Enriches logs with application-specific information based on `ApplicationMetadata` information. The bellow calls will add the service log enricher to the service collection.
Enriches logs with application-specific information based on `ApplicationMetadata` information. The bellow calls will add the application log enricher to the service collection.

```csharp
// Add service log enricher with default settings
builder.Services.AddServiceLogEnricher();
builder.Services.AddApplicationLogEnricher();

// Or configure with options
builder.Services.AddServiceLogEnricher(options =>
builder.Services.AddApplicationLogEnricher(options =>
{
options.ApplicationName = true;
options.BuildVersion = true;
Expand Down Expand Up @@ -197,7 +197,7 @@ builder.Logging.EnableEnrichment(options =>
options.UseFileInfoForStackTraces = true;
});

builder.Services.AddServiceLogEnricher(); // <- This call is required in order for the enricher to be added into the service collection.
builder.Services.AddApplicationLogEnricher(); // <- This call is required in order for the enricher to be added into the service collection.

// Enable log redaction
builder.Logging.EnableRedaction(options =>
Expand Down
6 changes: 5 additions & 1 deletion src/Shared/DiagnosticIds/DiagnosticIds.cs
Original file line number Diff line number Diff line change
Expand Up @@ -123,7 +123,11 @@ internal static class AuditReports
internal static class Obsoletions
{
internal const string NonObservableResourceMonitoringApiDiagId = "EXTOBS0001";
internal const string NonObservableResourceMonitoringApiMessage = "This API is obsolete and will be removed in a future version. Consider using Resource Monitoring observable instruments.";
internal const string ObsoleteTelemetryApiDiagId = "EXTOBS0002";
internal const string NonObservableResourceMonitoringApiMessage =
"This API is obsolete and will be removed in a future version. Consider using Resource Monitoring observable instruments.";
internal const string ObsoleteTelemetryApiMessage =
"This API is obsolete and will be removed in a future version. Instead of the AddServiceLogEnricher() methods, consider using the respective AddApplicationLogEnricher() methods.";
}
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -18,24 +18,24 @@ public class ApplicationEnricherExtensionsTests
public void ServiceLogEnricher_GivenAnyNullArgument_Throws()
{
Assert.Throws<ArgumentNullException>(() =>
((IServiceCollection)null!).AddServiceLogEnricher());
((IServiceCollection)null!).AddApplicationLogEnricher());

Assert.Throws<ArgumentNullException>(() =>
((IServiceCollection)null!).AddServiceLogEnricher(_ => { }));
((IServiceCollection)null!).AddApplicationLogEnricher(_ => { }));

Assert.Throws<ArgumentNullException>(() =>
((IServiceCollection)null!).AddServiceLogEnricher(Mock.Of<IConfigurationSection>()));
((IServiceCollection)null!).AddApplicationLogEnricher(Mock.Of<IConfigurationSection>()));

Assert.Throws<ArgumentNullException>(() =>
new ServiceCollection().AddServiceLogEnricher((IConfigurationSection)null!));
new ServiceCollection().AddApplicationLogEnricher((IConfigurationSection)null!));
}

[Fact]
public void ServiceLogEnricher_GivenNoArguments_RegistersInDI()
{
// Arrange & Act
using var host = FakeHost.CreateBuilder()
.ConfigureServices(services => services.AddServiceLogEnricher())
.ConfigureServices(services => services.AddApplicationLogEnricher())
.Build();

// Assert
Expand All @@ -48,7 +48,7 @@ public void HostLogEnricher_GivenOptions_RegistersInDI()
// Arrange & Act
using var host = FakeHost.CreateBuilder()
.ConfigureLogging(builder => builder
.Services.AddServiceLogEnricher(e =>
.Services.AddApplicationLogEnricher(e =>
{
e.ApplicationName = false;
e.EnvironmentName = false;
Expand All @@ -68,17 +68,17 @@ public void HostLogEnricher_GivenOptions_RegistersInDI()
}

[Fact]
public void ServiceLogEnricher_GivenConfiguration_RegistersInDI()
public void ApplicationLogEnricher_GivenConfiguration_RegistersInDI()
{
// Arrange & Act
using var host = FakeHost.CreateBuilder()
.ConfigureAppConfiguration(
("Serviceenrichersection:ApplicationName", "true"),
("Serviceenrichersection:EnvironmentName", "false"),
("Serviceenrichersection:BuildVersion", "true"),
("Serviceenrichersection:DeploymentRing", "true"))
("Applicationenrichersection:ApplicationName", "true"),
("Applicationenrichersection:EnvironmentName", "false"),
("Applicationenrichersection:BuildVersion", "true"),
("Applicationenrichersection:DeploymentRing", "true"))
.ConfigureServices((context, services) => services
.AddServiceLogEnricher(context.Configuration.GetSection("Serviceenrichersection")))
.AddApplicationLogEnricher(context.Configuration.GetSection("Applicationenrichersection")))
.Build();

// Assert
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ namespace Microsoft.Extensions.Diagnostics.Enrichment.Test;
public class ApplicationEnricherOptionsTests
{
[Fact]
public void ServiceLogEnricherOptions_EnsureDefaultValues()
public void ApplicationLogEnricherOptions_EnsureDefaultValues()
{
var options = new ApplicationLogEnricherOptions();
options.EnvironmentName.Should().BeTrue();
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -39,20 +39,20 @@ public void HostLogEnricher_GivenInvalidArguments_Throws()
var optionsNull = new Mock<IOptions<ApplicationLogEnricherOptions>>();
optionsNull.Setup(o => o.Value).Returns<IOptions<ApplicationLogEnricherOptions>>(null!);

var serviceOptionsNull = new Mock<IOptions<ApplicationMetadata>>();
serviceOptionsNull.Setup(o => o.Value).Returns<IOptions<ApplicationMetadata>>(null!);
var applicationOptionsNull = new Mock<IOptions<ApplicationMetadata>>();
applicationOptionsNull.Setup(o => o.Value).Returns<IOptions<ApplicationMetadata>>(null!);

// Act & Assert
Assert.Throws<ArgumentException>(() => new ApplicationLogEnricher(optionsNull.Object, null!));
Assert.Throws<ArgumentException>(() => new ApplicationLogEnricher(options, serviceOptionsNull.Object));
Assert.Throws<ArgumentException>(() => new ApplicationLogEnricher(options, applicationOptionsNull.Object));
}

[Theory]
[InlineData(true, true, true, true, null, null)]
[InlineData(true, true, true, true, BuildVersion, DeploymentRing)]
[InlineData(false, false, false, false, null, null)]
[InlineData(false, false, false, false, BuildVersion, DeploymentRing)]
public void ServiceLogEnricher_Options(bool appName, bool envName, bool buildVer, bool depRing, string? buildVersion, string? deploymentRing)
public void ApplicationLogEnricher_Options(bool appName, bool envName, bool buildVer, bool depRing, string? buildVersion, string? deploymentRing)
{
// Arrange
var options = new ApplicationLogEnricherOptions
Expand All @@ -63,15 +63,15 @@ public void ServiceLogEnricher_Options(bool appName, bool envName, bool buildVer
DeploymentRing = depRing,
};

var serviceOptions = new ApplicationMetadata
var metadata = new ApplicationMetadata
{
BuildVersion = buildVersion,
DeploymentRing = deploymentRing,
ApplicationName = _hostMock.Object.ApplicationName,
EnvironmentName = _hostMock.Object.EnvironmentName
};

var enricher = new ApplicationLogEnricher(options.ToOptions(), serviceOptions.ToOptions());
var enricher = new ApplicationLogEnricher(options.ToOptions(), metadata.ToOptions());
var enrichedProperties = new TestLogEnrichmentTagCollector();

// Act
Expand Down
Loading
Loading