Skip to content
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

Move LoggerProvider and friends (OTEL1000) to a stable API #5648

Merged
merged 18 commits into from
Jun 5, 2024

Conversation

CodeBlanch
Copy link
Member

@CodeBlanch CodeBlanch commented May 23, 2024

Fixes #5442
Fixes #4014

Changes

  • Expose the experimental APIs covered by OTEL1000 diagnostic

Migration guidance for library authors

Library authors should begin adding extension methods targeting LoggerProviderBuilder. In a future release the ILoggingBuilder.AddOpenTelemetry extension method and the OpenTelemetryLoggerOptions.AddProcessor & OpenTelemetryLoggerOptions.SetResourceBuilder methods will be marked obsolete.

Before:

    public static OpenTelemetryLoggerOptions AddMyExporter(
        this OpenTelemetryLoggerOptions loggerOptions,
        Action<MyExporterOptions> configure) {}

After:

    public static OpenTelemetryLoggerOptions AddMyExporter(
        this OpenTelemetryLoggerOptions loggerOptions,
        Action<MyExporterOptions> configure) {}

    public static LoggerProviderBuilder AddMyExporter(
        this LoggerProviderBuilder builder,
        Action<MyExporterOptions> configure) {}

LoggerProviderBuilder has the same AddProcessor and SetResourceBuilder methods previously available on OpenTelemetryLoggerOptions as well as the full set of methods\features available to MeterProviderBuilder and TracerProviderBuilder.

Migration guidance for users

Note: No migration is currently required for users. All existing code should function as it did before. The following migration paths are purely optional.

When using OpenTelemetry.Extensions.Hosting

Before:

appBuilder.Logging.AddOpenTelemetry(options =>
{
    options.IncludeFormattedMessage = true;
    options.AddOtlpExporter(o => o.Endpoint = new Uri("http://myotlpendpoint:4317/logs"));
});

After:

appBuilder.Services.AddOpenTelemetry()
    .WithLogging(
        logging => logging.AddOtlpExporter(o => o.Endpoint = new Uri("http://myotlpendpoint:4317/logs")),
        options => options.IncludeFormattedMessage = true);

For this to work, your exporter needs to expose an extension which targets LoggerProviderBuilder. Extensions are provided for OtlpExporter, ConsoleExporter, and InMemoryExporter.

If you are using an exporter from the https://github.com/open-telemetry/opentelemetry-dotnet-contrib repository or some other exporter, it may not provide this extension yet. First try to upgrade your exporter package. If there isn't an update available, you may use this pattern and continue to call the existing extension (while waiting for the component to be updated):

appBuilder.Services.AddOpenTelemetry()
    .WithLogging(
	logging => {},
	options =>
    	{
        	options.IncludeFormattedMessage = true;

        	// Note: Existing extensions targeting OpenTelemetryLoggerOptions can still be called.
        	options.AddGenevaLogExporter(o => o.ConnectionString = "...");
    	});

When using LoggerFactory.Create

There is no dedicated API provided yet to migrate from ILoggerBuilder.AddOpenTelemetry (which provides OpenTelemetryLoggerOptions) to something which provides LoggerProviderBuilder. This API will come in a future version.

If for some reason you want to use LoggerProviderBuilder before that API is available, it is possible to use IServiceCollection.ConfigureOpenTelemetryLoggerProvider to configure the LoggerProviderBuilder using ILoggingBuilder.Services:

Before

using var loggerFactory = LoggerFactory.Create(builder => builder
    .AddOpenTelemetry(options =>
    {
        options.IncludeFormattedMessage = true;
        options.AddOtlpExporter(o => o.Endpoint = new Uri("http://myotlpendpoint:4317/logs"));
    });

After

using var loggerFactory = LoggerFactory.Create(builder =>
{
    builder.AddOpenTelemetry(options => options.IncludeFormattedMessage = true);

    builder.Services.ConfigureOpenTelemetryLoggerProvider(
        logging => logging.AddConsoleExporter());
});

Merge requirement checklist

  • CONTRIBUTING guidelines followed (license requirements, nullable enabled, static analysis, etc.)
  • Unit tests added/updated
  • Appropriate CHANGELOG.md files updated for non-trivial changes
  • Changes in public API reviewed (if applicable)

@CodeBlanch CodeBlanch added pkg:OpenTelemetry.Api Issues related to OpenTelemetry.Api NuGet package pkg:OpenTelemetry Issues related to OpenTelemetry NuGet package pkg:OpenTelemetry.Extensions.Hosting Issues related to OpenTelemetry.Extensions.Hosting NuGet package pkg:OpenTelemetry.Api.ProviderBuilderExtensions Issues related to OpenTelemetry.Api.ProviderBuilderExtensions NuGet package labels May 23, 2024
Copy link

codecov bot commented May 23, 2024

Codecov Report

All modified and coverable lines are covered by tests ✅

Project coverage is 86.15%. Comparing base (6250307) to head (6611356).
Report is 249 commits behind head on main.

Additional details and impacted files

Impacted file tree graph

@@            Coverage Diff             @@
##             main    #5648      +/-   ##
==========================================
+ Coverage   83.38%   86.15%   +2.77%     
==========================================
  Files         297      254      -43     
  Lines       12531    11054    -1477     
==========================================
- Hits        10449     9524     -925     
+ Misses       2082     1530     -552     
Flag Coverage Δ
unittests ?
unittests-Project-Experimental 86.05% <100.00%> (?)
unittests-Project-Stable 86.00% <100.00%> (?)
unittests-Solution 86.01% <100.00%> (?)
unittests-UnstableCoreLibraries-Experimental 20.19% <0.00%> (?)

Flags with carried forward coverage won't be shown. Click here to find out more.

Files Coverage Δ
...endencyInjectionLoggerProviderBuilderExtensions.cs 100.00% <ø> (ø)
...encyInjectionLoggingServiceCollectionExtensions.cs 100.00% <ø> (ø)
src/OpenTelemetry.Api/Logs/LoggerProvider.cs 100.00% <ø> (ø)
...rc/OpenTelemetry.Api/Logs/LoggerProviderBuilder.cs 100.00% <ø> (ø)
...porter.Console/ConsoleExporterLoggingExtensions.cs 0.00% <ø> (ø)
...rter.InMemory/InMemoryExporterLoggingExtensions.cs 100.00% <ø> (+33.33%) ⬆️
...lemetryProtocol/OtlpLogExporterHelperExtensions.cs 94.26% <ø> (+23.19%) ⬆️
...lemetry.Extensions.Hosting/OpenTelemetryBuilder.cs 100.00% <ø> (ø)
src/OpenTelemetry/BatchExportProcessor.cs 84.11% <100.00%> (+1.86%) ⬆️
...ry/Logs/Builder/LoggerProviderBuilderExtensions.cs 100.00% <ø> (ø)
... and 6 more

... and 117 files with indirect coverage changes

@CodeBlanch
Copy link
Member Author

Some thoughts for anyone taking a look at this...

  • We don't necessarily have to obsolete anything. I put them in initially to see the fallout. I added migration guidance to the PR so we can see what it would look like.

  • There is no Sdk.CreateLoggerProviderBuilder being added here. I moved that to the Log Bridge experimental API (OTEL1001). The only use case I can think of for Sdk.CreateLoggerProviderBuilder is in order to build a LoggerProvider manually to feed into a bridge. For the use cases we have today, LoggerFactory.Create works fine so I didn't feel this API was needed at this time.

@CodeBlanch CodeBlanch marked this pull request as ready for review May 30, 2024 23:08
@CodeBlanch CodeBlanch requested a review from a team May 30, 2024 23:08
@vishweshbankwar
Copy link
Member

Some thoughts for anyone taking a look at this...

  • We don't necessarily have to obsolete anything. I put them in initially to see the fallout. I added migration guidance to the PR so we can see what it would look like.
  • There is no Sdk.CreateLoggerProviderBuilder being added here. I moved that to the Log Bridge experimental API (OTEL1001). The only use case I can think of for Sdk.CreateLoggerProviderBuilder is in order to build a LoggerProvider manually to feed into a bridge. For the use cases we have today, LoggerFactory.Create works fine so I didn't feel this API was needed at this time.

@CodeBlanch - I think we should not mark things obsolete rn.

Regarding the migration guidance:

  1. Migration guidance for case 1:

    appBuilder.Logging.AddOpenTelemetry(options =>
    {
        options.IncludeFormattedMessage = true;
        options.AddOtlpExporter(o => o.Endpoint = new Uri("http://myotlpendpoint:4317/logs"));
    });

    With this change, my understanding was, they should be able to move to following pattern (bringing consistency with other two signals for hosting scenarios and the update you have in the example)

    appBuilder.Services.AddOpenTelemetry().WithLogging()
  2. Migration guidance for case 2:

    using var loggerFactory = LoggerFactory.Create(builder => builder
            .UseOpenTelemetry(
            logging => logging.AddOtlpExporter(o => o.Endpoint = new Uri("http://myotlpendpoint:4317/logs")),
            options => options.IncludeFormattedMessage = true));

    I think we should not include it with this change. As per my understanding, it depends on the final outcome of [sdk] Add OpenTelemetrySdk builder pattern #5325. If we go ahead with the OpenTelemetrySdk pattern then we could just ask users to follow that (Separate discussion).

In short, the only use case we would enable right now is .WithLogging() for hosting scenarios.

For future, we could decide whether we want to have the migration guidance for case 2 or go with OpenTelemetrySdk pattern.

@CodeBlanch
Copy link
Member Author

@vishweshbankwar

@CodeBlanch - I think we should not mark things obsolete rn.

Based on what thinking/reasons? Please elaborate a bit 😄

@vishweshbankwar
Copy link
Member

vishweshbankwar commented Jun 4, 2024

@vishweshbankwar

@CodeBlanch - I think we should not mark things obsolete rn.

Based on what thinking/reasons? Please elaborate a bit 😄

  • Based on my point # 2: Once we have a clear plan/alternate for users on case 2 then we can consider the obsoleting part.
  • Also, following this staged approach would give enough time for library authors also to support the extensions based on LoggerProviderBuilder.

Copy link
Member

@alanwest alanwest left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can't wait to start tell users they can finally use WithLogging!

static OpenTelemetry.Logs.LoggerProviderExtensions.Shutdown(this OpenTelemetry.Logs.LoggerProvider! provider, int timeoutMilliseconds = -1) -> bool
static OpenTelemetry.OpenTelemetryBuilderSdkExtensions.WithLogging(this OpenTelemetry.IOpenTelemetryBuilder! builder) -> OpenTelemetry.IOpenTelemetryBuilder!
static OpenTelemetry.OpenTelemetryBuilderSdkExtensions.WithLogging(this OpenTelemetry.IOpenTelemetryBuilder! builder, System.Action<OpenTelemetry.Logs.LoggerProviderBuilder!>! configure) -> OpenTelemetry.IOpenTelemetryBuilder!
static OpenTelemetry.OpenTelemetryBuilderSdkExtensions.WithLogging(this OpenTelemetry.IOpenTelemetryBuilder! builder, System.Action<OpenTelemetry.Logs.LoggerProviderBuilder!>? configureBuilder, System.Action<OpenTelemetry.Logs.OpenTelemetryLoggerOptions!>? configureOptions) -> OpenTelemetry.IOpenTelemetryBuilder!
static OpenTelemetry.Sdk.CreateLoggerProviderBuilder() -> OpenTelemetry.Logs.LoggerProviderBuilder!
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm ok keeping this experimental for now. Might ultimately be nice simply for consistency, but I see no reason for this discussion to block the introduction of the new APIs, especially WithLogging.

@CodeBlanch
Copy link
Member Author

We decided on the SIG meeting 6/4/2024 that we would:

  • Not obsolete anything for 1.9.0. We will obsolete things in a future release. This was done to give library authors time to add extensions targeting LoggerProviderBuilder which will ease migration for users when things are obsoleted.

  • ILoggingBuilder.UseOpenTelemetry will not be exposed initially. It may be replaced by the design on [sdk] Add OpenTelemetrySdk builder pattern #5325.

@alanwest @vishweshbankwar PR has been updated.

@cijothomas
Copy link
Member

@CodeBlanch Can you update the PR description to include the changes expected to be done by end users as well, even though they are not forced to do it? Also call out that, this should be done only if their exporter supports this new model (and mention that exporters shipped from this repo already supports this model)


var resourceBuilder = ResourceBuilder.CreateDefault();
configureResource(resourceBuilder);
options.SetResourceBuilder(resourceBuilder);
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

❤️ seeing common Resource across all 3!

And also ❤️ fixing the awkwardness of calling methods like AddExporter on a supposedly pure "Options" class!

// In production environment, ConsoleExporter should be replaced with other exporters (e.g. OTLP Exporter).
.AddConsoleExporter();
});
// Add OpenTelemetry logging provider by calling the WithLogging extension.
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

should we add a note here to warn users that this approach only works if their exporter also supports this model?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Might get confusing. I think either a) we leave it as is or b) we show the old style. Let me know which you prefer! I'm hoping the gap is short-lived and we can get these extensions added soon after 1.9.0 is out.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

okay to keep this as-is, assuming the gap is short-lived.

@CodeBlanch
Copy link
Member Author

@cijothomas I added "Migration guidance for users" back on the PR description.

Copy link
Member

@vishweshbankwar vishweshbankwar left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
pkg:OpenTelemetry.Api.ProviderBuilderExtensions Issues related to OpenTelemetry.Api.ProviderBuilderExtensions NuGet package pkg:OpenTelemetry.Api Issues related to OpenTelemetry.Api NuGet package pkg:OpenTelemetry.Extensions.Hosting Issues related to OpenTelemetry.Extensions.Hosting NuGet package pkg:OpenTelemetry Issues related to OpenTelemetry NuGet package
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Promote LoggerProvider from experimental to stable Improve DI friendliness of Logging
4 participants