From 6dc0417817995b33ede6f9ae6a70deaf1bcc6a3c Mon Sep 17 00:00:00 2001 From: Mikel Blanchard Date: Fri, 3 Mar 2023 08:06:57 -0800 Subject: [PATCH] [OneCollector] Add RegisterPayloadTransmittedCallback API (#1058) Co-authored-by: Cijo Thomas --- .../.publicApi/net462/PublicAPI.Unshipped.txt | 27 ++- .../.publicApi/net6.0/PublicAPI.Unshipped.txt | 27 ++- .../.publicApi/net7.0/PublicAPI.Unshipped.txt | 27 ++- .../netstandard2.0/PublicAPI.Unshipped.txt | 27 ++- .../netstandard2.1/PublicAPI.Unshipped.txt | 27 ++- .../CHANGELOG.md | 3 + .../Internal/CallbackManager.cs | 78 ++++++ .../OneCollectorExporterEventSource.cs | 15 ++ .../CommonSchemaJsonSerializer.cs | 2 + .../Internal/Serialization/ISerializer.cs | 2 + .../Internal/Sinks/ISink.cs | 2 + .../Sinks/WriteDirectlyToTransportSink.cs | 13 +- .../Transports/HttpJsonPostTransport.cs | 72 +++++- .../Internal/Transports/ITransport.cs | 2 + .../Transports/TransportSendRequest.cs | 10 +- .../OneCollectorLogExportProcessorBuilder.cs | 225 ++++++++++++++++++ .../Logs/OneCollectorLogExporter.cs | 35 --- .../Logs/OneCollectorLogExporterBuilder.cs | 118 --------- .../Logs/OneCollectorLogExporterOptions.cs | 31 +-- ...torOpenTelemetryLoggerOptionsExtensions.cs | 68 +++--- .../OneCollectorExporter.cs | 23 +- .../OneCollectorExporterOptions.cs | 6 + ...rterPayloadTransmittedCallbackArguments.cs | 93 ++++++++ ...llectorExporterSerializationFormatType.cs} | 13 +- .../OneCollectorExporterTransportOptions.cs | 23 -- .../HttpJsonPostTransportTests.cs | 136 ++++++++++- ...enTelemetryLoggerOptionsExtensionsTests.cs | 24 ++ .../WriteDirectlyToTransportSinkTests.cs | 5 + 28 files changed, 797 insertions(+), 337 deletions(-) create mode 100644 src/OpenTelemetry.Exporter.OneCollector/Internal/CallbackManager.cs create mode 100644 src/OpenTelemetry.Exporter.OneCollector/Logs/OneCollectorLogExportProcessorBuilder.cs delete mode 100644 src/OpenTelemetry.Exporter.OneCollector/Logs/OneCollectorLogExporter.cs delete mode 100644 src/OpenTelemetry.Exporter.OneCollector/Logs/OneCollectorLogExporterBuilder.cs create mode 100644 src/OpenTelemetry.Exporter.OneCollector/OneCollectorExporterPayloadTransmittedCallbackArguments.cs rename src/OpenTelemetry.Exporter.OneCollector/{Internal/Sinks/ISinkFactory.cs => OneCollectorExporterSerializationFormatType.cs} (62%) diff --git a/src/OpenTelemetry.Exporter.OneCollector/.publicApi/net462/PublicAPI.Unshipped.txt b/src/OpenTelemetry.Exporter.OneCollector/.publicApi/net462/PublicAPI.Unshipped.txt index 438e9e6c3d..baf438cdc1 100644 --- a/src/OpenTelemetry.Exporter.OneCollector/.publicApi/net462/PublicAPI.Unshipped.txt +++ b/src/OpenTelemetry.Exporter.OneCollector/.publicApi/net462/PublicAPI.Unshipped.txt @@ -1,8 +1,15 @@ OpenTelemetry.Exporter.OneCollector.OneCollectorExporter +OpenTelemetry.Exporter.OneCollector.OneCollectorExporter.RegisterPayloadTransmittedCallback(OpenTelemetry.Exporter.OneCollector.OneCollectorExporterPayloadTransmittedCallbackAction! callback) -> System.IDisposable? OpenTelemetry.Exporter.OneCollector.OneCollectorExporterOptions OpenTelemetry.Exporter.OneCollector.OneCollectorExporterOptions.ConnectionString.get -> string? OpenTelemetry.Exporter.OneCollector.OneCollectorExporterOptions.ConnectionString.set -> void OpenTelemetry.Exporter.OneCollector.OneCollectorExporterOptions.TransportOptions.get -> OpenTelemetry.Exporter.OneCollector.OneCollectorExporterTransportOptions! +OpenTelemetry.Exporter.OneCollector.OneCollectorExporterPayloadTransmittedCallbackAction +OpenTelemetry.Exporter.OneCollector.OneCollectorExporterPayloadTransmittedCallbackArguments +OpenTelemetry.Exporter.OneCollector.OneCollectorExporterPayloadTransmittedCallbackArguments.CopyPayloadToStream(System.IO.Stream! destination) -> void +OpenTelemetry.Exporter.OneCollector.OneCollectorExporterPayloadTransmittedCallbackArguments.OneCollectorExporterPayloadTransmittedCallbackArguments() -> void +OpenTelemetry.Exporter.OneCollector.OneCollectorExporterPayloadTransmittedCallbackArguments.PayloadSizeInBytes.get -> long +OpenTelemetry.Exporter.OneCollector.OneCollectorExporterPayloadTransmittedCallbackArguments.TransportEndpoint.get -> System.Uri! OpenTelemetry.Exporter.OneCollector.OneCollectorExporterTransportOptions OpenTelemetry.Exporter.OneCollector.OneCollectorExporterTransportOptions.Endpoint.get -> System.Uri! OpenTelemetry.Exporter.OneCollector.OneCollectorExporterTransportOptions.Endpoint.set -> void @@ -10,22 +17,20 @@ OpenTelemetry.Exporter.OneCollector.OneCollectorExporterValidationException OpenTelemetry.Exporter.OneCollector.OneCollectorExporterValidationException.OneCollectorExporterValidationException() -> void OpenTelemetry.Exporter.OneCollector.OneCollectorExporterValidationException.OneCollectorExporterValidationException(string! message) -> void OpenTelemetry.Exporter.OneCollector.OneCollectorExporterValidationException.OneCollectorExporterValidationException(string! message, System.Exception? innerException) -> void -OpenTelemetry.Exporter.OneCollector.OneCollectorLogExporter -OpenTelemetry.Exporter.OneCollector.OneCollectorLogExporter.OneCollectorLogExporter(OpenTelemetry.Exporter.OneCollector.OneCollectorLogExporterOptions! options) -> void OpenTelemetry.Exporter.OneCollector.OneCollectorLogExporterOptions -OpenTelemetry.Exporter.OneCollector.OneCollectorLogExporterOptions.BatchOptions.get -> OpenTelemetry.BatchExportProcessorOptions! OpenTelemetry.Exporter.OneCollector.OneCollectorLogExporterOptions.DefaultEventName.get -> string! OpenTelemetry.Exporter.OneCollector.OneCollectorLogExporterOptions.DefaultEventName.set -> void OpenTelemetry.Exporter.OneCollector.OneCollectorLogExporterOptions.OneCollectorLogExporterOptions() -> void -OpenTelemetry.Logs.OneCollectorLogExporterBuilder -OpenTelemetry.Logs.OneCollectorLogExporterBuilder.ConfigureBatchOptions(System.Action!>! configure) -> OpenTelemetry.Logs.OneCollectorLogExporterBuilder! -OpenTelemetry.Logs.OneCollectorLogExporterBuilder.ConfigureTransportOptions(System.Action! configure) -> OpenTelemetry.Logs.OneCollectorLogExporterBuilder! -OpenTelemetry.Logs.OneCollectorLogExporterBuilder.SetConnectionString(string! connectionString) -> OpenTelemetry.Logs.OneCollectorLogExporterBuilder! -OpenTelemetry.Logs.OneCollectorLogExporterBuilder.SetDefaultEventName(string! defaultEventName) -> OpenTelemetry.Logs.OneCollectorLogExporterBuilder! +OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder +OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder.ConfigureBatchOptions(System.Action!>! configure) -> OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder! +OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder.ConfigureExporter(System.Action!>! configure) -> OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder! +OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder.ConfigureTransportOptions(System.Action! configure) -> OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder! +OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder.SetConnectionString(string! connectionString) -> OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder! +OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder.SetDefaultEventName(string! defaultEventName) -> OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder! OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions override sealed OpenTelemetry.Exporter.OneCollector.OneCollectorExporter.Export(in OpenTelemetry.Batch batch) -> OpenTelemetry.ExportResult static OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions.AddOneCollectorExporter(this OpenTelemetry.Logs.OpenTelemetryLoggerOptions! options, Microsoft.Extensions.Configuration.IConfiguration! configuration) -> OpenTelemetry.Logs.OpenTelemetryLoggerOptions! -static OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions.AddOneCollectorExporter(this OpenTelemetry.Logs.OpenTelemetryLoggerOptions! options, Microsoft.Extensions.Configuration.IConfiguration! configuration, System.Action! configure) -> OpenTelemetry.Logs.OpenTelemetryLoggerOptions! +static OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions.AddOneCollectorExporter(this OpenTelemetry.Logs.OpenTelemetryLoggerOptions! options, Microsoft.Extensions.Configuration.IConfiguration! configuration, System.Action! configure) -> OpenTelemetry.Logs.OpenTelemetryLoggerOptions! static OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions.AddOneCollectorExporter(this OpenTelemetry.Logs.OpenTelemetryLoggerOptions! options, string! connectionString) -> OpenTelemetry.Logs.OpenTelemetryLoggerOptions! -static OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions.AddOneCollectorExporter(this OpenTelemetry.Logs.OpenTelemetryLoggerOptions! options, string! connectionString, System.Action! configure) -> OpenTelemetry.Logs.OpenTelemetryLoggerOptions! -static OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions.AddOneCollectorExporter(this OpenTelemetry.Logs.OpenTelemetryLoggerOptions! options, System.Action! configure) -> OpenTelemetry.Logs.OpenTelemetryLoggerOptions! +static OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions.AddOneCollectorExporter(this OpenTelemetry.Logs.OpenTelemetryLoggerOptions! options, string! connectionString, System.Action! configure) -> OpenTelemetry.Logs.OpenTelemetryLoggerOptions! +static OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions.AddOneCollectorExporter(this OpenTelemetry.Logs.OpenTelemetryLoggerOptions! options, System.Action! configure) -> OpenTelemetry.Logs.OpenTelemetryLoggerOptions! diff --git a/src/OpenTelemetry.Exporter.OneCollector/.publicApi/net6.0/PublicAPI.Unshipped.txt b/src/OpenTelemetry.Exporter.OneCollector/.publicApi/net6.0/PublicAPI.Unshipped.txt index 438e9e6c3d..baf438cdc1 100644 --- a/src/OpenTelemetry.Exporter.OneCollector/.publicApi/net6.0/PublicAPI.Unshipped.txt +++ b/src/OpenTelemetry.Exporter.OneCollector/.publicApi/net6.0/PublicAPI.Unshipped.txt @@ -1,8 +1,15 @@ OpenTelemetry.Exporter.OneCollector.OneCollectorExporter +OpenTelemetry.Exporter.OneCollector.OneCollectorExporter.RegisterPayloadTransmittedCallback(OpenTelemetry.Exporter.OneCollector.OneCollectorExporterPayloadTransmittedCallbackAction! callback) -> System.IDisposable? OpenTelemetry.Exporter.OneCollector.OneCollectorExporterOptions OpenTelemetry.Exporter.OneCollector.OneCollectorExporterOptions.ConnectionString.get -> string? OpenTelemetry.Exporter.OneCollector.OneCollectorExporterOptions.ConnectionString.set -> void OpenTelemetry.Exporter.OneCollector.OneCollectorExporterOptions.TransportOptions.get -> OpenTelemetry.Exporter.OneCollector.OneCollectorExporterTransportOptions! +OpenTelemetry.Exporter.OneCollector.OneCollectorExporterPayloadTransmittedCallbackAction +OpenTelemetry.Exporter.OneCollector.OneCollectorExporterPayloadTransmittedCallbackArguments +OpenTelemetry.Exporter.OneCollector.OneCollectorExporterPayloadTransmittedCallbackArguments.CopyPayloadToStream(System.IO.Stream! destination) -> void +OpenTelemetry.Exporter.OneCollector.OneCollectorExporterPayloadTransmittedCallbackArguments.OneCollectorExporterPayloadTransmittedCallbackArguments() -> void +OpenTelemetry.Exporter.OneCollector.OneCollectorExporterPayloadTransmittedCallbackArguments.PayloadSizeInBytes.get -> long +OpenTelemetry.Exporter.OneCollector.OneCollectorExporterPayloadTransmittedCallbackArguments.TransportEndpoint.get -> System.Uri! OpenTelemetry.Exporter.OneCollector.OneCollectorExporterTransportOptions OpenTelemetry.Exporter.OneCollector.OneCollectorExporterTransportOptions.Endpoint.get -> System.Uri! OpenTelemetry.Exporter.OneCollector.OneCollectorExporterTransportOptions.Endpoint.set -> void @@ -10,22 +17,20 @@ OpenTelemetry.Exporter.OneCollector.OneCollectorExporterValidationException OpenTelemetry.Exporter.OneCollector.OneCollectorExporterValidationException.OneCollectorExporterValidationException() -> void OpenTelemetry.Exporter.OneCollector.OneCollectorExporterValidationException.OneCollectorExporterValidationException(string! message) -> void OpenTelemetry.Exporter.OneCollector.OneCollectorExporterValidationException.OneCollectorExporterValidationException(string! message, System.Exception? innerException) -> void -OpenTelemetry.Exporter.OneCollector.OneCollectorLogExporter -OpenTelemetry.Exporter.OneCollector.OneCollectorLogExporter.OneCollectorLogExporter(OpenTelemetry.Exporter.OneCollector.OneCollectorLogExporterOptions! options) -> void OpenTelemetry.Exporter.OneCollector.OneCollectorLogExporterOptions -OpenTelemetry.Exporter.OneCollector.OneCollectorLogExporterOptions.BatchOptions.get -> OpenTelemetry.BatchExportProcessorOptions! OpenTelemetry.Exporter.OneCollector.OneCollectorLogExporterOptions.DefaultEventName.get -> string! OpenTelemetry.Exporter.OneCollector.OneCollectorLogExporterOptions.DefaultEventName.set -> void OpenTelemetry.Exporter.OneCollector.OneCollectorLogExporterOptions.OneCollectorLogExporterOptions() -> void -OpenTelemetry.Logs.OneCollectorLogExporterBuilder -OpenTelemetry.Logs.OneCollectorLogExporterBuilder.ConfigureBatchOptions(System.Action!>! configure) -> OpenTelemetry.Logs.OneCollectorLogExporterBuilder! -OpenTelemetry.Logs.OneCollectorLogExporterBuilder.ConfigureTransportOptions(System.Action! configure) -> OpenTelemetry.Logs.OneCollectorLogExporterBuilder! -OpenTelemetry.Logs.OneCollectorLogExporterBuilder.SetConnectionString(string! connectionString) -> OpenTelemetry.Logs.OneCollectorLogExporterBuilder! -OpenTelemetry.Logs.OneCollectorLogExporterBuilder.SetDefaultEventName(string! defaultEventName) -> OpenTelemetry.Logs.OneCollectorLogExporterBuilder! +OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder +OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder.ConfigureBatchOptions(System.Action!>! configure) -> OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder! +OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder.ConfigureExporter(System.Action!>! configure) -> OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder! +OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder.ConfigureTransportOptions(System.Action! configure) -> OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder! +OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder.SetConnectionString(string! connectionString) -> OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder! +OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder.SetDefaultEventName(string! defaultEventName) -> OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder! OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions override sealed OpenTelemetry.Exporter.OneCollector.OneCollectorExporter.Export(in OpenTelemetry.Batch batch) -> OpenTelemetry.ExportResult static OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions.AddOneCollectorExporter(this OpenTelemetry.Logs.OpenTelemetryLoggerOptions! options, Microsoft.Extensions.Configuration.IConfiguration! configuration) -> OpenTelemetry.Logs.OpenTelemetryLoggerOptions! -static OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions.AddOneCollectorExporter(this OpenTelemetry.Logs.OpenTelemetryLoggerOptions! options, Microsoft.Extensions.Configuration.IConfiguration! configuration, System.Action! configure) -> OpenTelemetry.Logs.OpenTelemetryLoggerOptions! +static OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions.AddOneCollectorExporter(this OpenTelemetry.Logs.OpenTelemetryLoggerOptions! options, Microsoft.Extensions.Configuration.IConfiguration! configuration, System.Action! configure) -> OpenTelemetry.Logs.OpenTelemetryLoggerOptions! static OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions.AddOneCollectorExporter(this OpenTelemetry.Logs.OpenTelemetryLoggerOptions! options, string! connectionString) -> OpenTelemetry.Logs.OpenTelemetryLoggerOptions! -static OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions.AddOneCollectorExporter(this OpenTelemetry.Logs.OpenTelemetryLoggerOptions! options, string! connectionString, System.Action! configure) -> OpenTelemetry.Logs.OpenTelemetryLoggerOptions! -static OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions.AddOneCollectorExporter(this OpenTelemetry.Logs.OpenTelemetryLoggerOptions! options, System.Action! configure) -> OpenTelemetry.Logs.OpenTelemetryLoggerOptions! +static OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions.AddOneCollectorExporter(this OpenTelemetry.Logs.OpenTelemetryLoggerOptions! options, string! connectionString, System.Action! configure) -> OpenTelemetry.Logs.OpenTelemetryLoggerOptions! +static OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions.AddOneCollectorExporter(this OpenTelemetry.Logs.OpenTelemetryLoggerOptions! options, System.Action! configure) -> OpenTelemetry.Logs.OpenTelemetryLoggerOptions! diff --git a/src/OpenTelemetry.Exporter.OneCollector/.publicApi/net7.0/PublicAPI.Unshipped.txt b/src/OpenTelemetry.Exporter.OneCollector/.publicApi/net7.0/PublicAPI.Unshipped.txt index 438e9e6c3d..baf438cdc1 100644 --- a/src/OpenTelemetry.Exporter.OneCollector/.publicApi/net7.0/PublicAPI.Unshipped.txt +++ b/src/OpenTelemetry.Exporter.OneCollector/.publicApi/net7.0/PublicAPI.Unshipped.txt @@ -1,8 +1,15 @@ OpenTelemetry.Exporter.OneCollector.OneCollectorExporter +OpenTelemetry.Exporter.OneCollector.OneCollectorExporter.RegisterPayloadTransmittedCallback(OpenTelemetry.Exporter.OneCollector.OneCollectorExporterPayloadTransmittedCallbackAction! callback) -> System.IDisposable? OpenTelemetry.Exporter.OneCollector.OneCollectorExporterOptions OpenTelemetry.Exporter.OneCollector.OneCollectorExporterOptions.ConnectionString.get -> string? OpenTelemetry.Exporter.OneCollector.OneCollectorExporterOptions.ConnectionString.set -> void OpenTelemetry.Exporter.OneCollector.OneCollectorExporterOptions.TransportOptions.get -> OpenTelemetry.Exporter.OneCollector.OneCollectorExporterTransportOptions! +OpenTelemetry.Exporter.OneCollector.OneCollectorExporterPayloadTransmittedCallbackAction +OpenTelemetry.Exporter.OneCollector.OneCollectorExporterPayloadTransmittedCallbackArguments +OpenTelemetry.Exporter.OneCollector.OneCollectorExporterPayloadTransmittedCallbackArguments.CopyPayloadToStream(System.IO.Stream! destination) -> void +OpenTelemetry.Exporter.OneCollector.OneCollectorExporterPayloadTransmittedCallbackArguments.OneCollectorExporterPayloadTransmittedCallbackArguments() -> void +OpenTelemetry.Exporter.OneCollector.OneCollectorExporterPayloadTransmittedCallbackArguments.PayloadSizeInBytes.get -> long +OpenTelemetry.Exporter.OneCollector.OneCollectorExporterPayloadTransmittedCallbackArguments.TransportEndpoint.get -> System.Uri! OpenTelemetry.Exporter.OneCollector.OneCollectorExporterTransportOptions OpenTelemetry.Exporter.OneCollector.OneCollectorExporterTransportOptions.Endpoint.get -> System.Uri! OpenTelemetry.Exporter.OneCollector.OneCollectorExporterTransportOptions.Endpoint.set -> void @@ -10,22 +17,20 @@ OpenTelemetry.Exporter.OneCollector.OneCollectorExporterValidationException OpenTelemetry.Exporter.OneCollector.OneCollectorExporterValidationException.OneCollectorExporterValidationException() -> void OpenTelemetry.Exporter.OneCollector.OneCollectorExporterValidationException.OneCollectorExporterValidationException(string! message) -> void OpenTelemetry.Exporter.OneCollector.OneCollectorExporterValidationException.OneCollectorExporterValidationException(string! message, System.Exception? innerException) -> void -OpenTelemetry.Exporter.OneCollector.OneCollectorLogExporter -OpenTelemetry.Exporter.OneCollector.OneCollectorLogExporter.OneCollectorLogExporter(OpenTelemetry.Exporter.OneCollector.OneCollectorLogExporterOptions! options) -> void OpenTelemetry.Exporter.OneCollector.OneCollectorLogExporterOptions -OpenTelemetry.Exporter.OneCollector.OneCollectorLogExporterOptions.BatchOptions.get -> OpenTelemetry.BatchExportProcessorOptions! OpenTelemetry.Exporter.OneCollector.OneCollectorLogExporterOptions.DefaultEventName.get -> string! OpenTelemetry.Exporter.OneCollector.OneCollectorLogExporterOptions.DefaultEventName.set -> void OpenTelemetry.Exporter.OneCollector.OneCollectorLogExporterOptions.OneCollectorLogExporterOptions() -> void -OpenTelemetry.Logs.OneCollectorLogExporterBuilder -OpenTelemetry.Logs.OneCollectorLogExporterBuilder.ConfigureBatchOptions(System.Action!>! configure) -> OpenTelemetry.Logs.OneCollectorLogExporterBuilder! -OpenTelemetry.Logs.OneCollectorLogExporterBuilder.ConfigureTransportOptions(System.Action! configure) -> OpenTelemetry.Logs.OneCollectorLogExporterBuilder! -OpenTelemetry.Logs.OneCollectorLogExporterBuilder.SetConnectionString(string! connectionString) -> OpenTelemetry.Logs.OneCollectorLogExporterBuilder! -OpenTelemetry.Logs.OneCollectorLogExporterBuilder.SetDefaultEventName(string! defaultEventName) -> OpenTelemetry.Logs.OneCollectorLogExporterBuilder! +OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder +OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder.ConfigureBatchOptions(System.Action!>! configure) -> OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder! +OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder.ConfigureExporter(System.Action!>! configure) -> OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder! +OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder.ConfigureTransportOptions(System.Action! configure) -> OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder! +OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder.SetConnectionString(string! connectionString) -> OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder! +OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder.SetDefaultEventName(string! defaultEventName) -> OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder! OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions override sealed OpenTelemetry.Exporter.OneCollector.OneCollectorExporter.Export(in OpenTelemetry.Batch batch) -> OpenTelemetry.ExportResult static OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions.AddOneCollectorExporter(this OpenTelemetry.Logs.OpenTelemetryLoggerOptions! options, Microsoft.Extensions.Configuration.IConfiguration! configuration) -> OpenTelemetry.Logs.OpenTelemetryLoggerOptions! -static OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions.AddOneCollectorExporter(this OpenTelemetry.Logs.OpenTelemetryLoggerOptions! options, Microsoft.Extensions.Configuration.IConfiguration! configuration, System.Action! configure) -> OpenTelemetry.Logs.OpenTelemetryLoggerOptions! +static OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions.AddOneCollectorExporter(this OpenTelemetry.Logs.OpenTelemetryLoggerOptions! options, Microsoft.Extensions.Configuration.IConfiguration! configuration, System.Action! configure) -> OpenTelemetry.Logs.OpenTelemetryLoggerOptions! static OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions.AddOneCollectorExporter(this OpenTelemetry.Logs.OpenTelemetryLoggerOptions! options, string! connectionString) -> OpenTelemetry.Logs.OpenTelemetryLoggerOptions! -static OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions.AddOneCollectorExporter(this OpenTelemetry.Logs.OpenTelemetryLoggerOptions! options, string! connectionString, System.Action! configure) -> OpenTelemetry.Logs.OpenTelemetryLoggerOptions! -static OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions.AddOneCollectorExporter(this OpenTelemetry.Logs.OpenTelemetryLoggerOptions! options, System.Action! configure) -> OpenTelemetry.Logs.OpenTelemetryLoggerOptions! +static OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions.AddOneCollectorExporter(this OpenTelemetry.Logs.OpenTelemetryLoggerOptions! options, string! connectionString, System.Action! configure) -> OpenTelemetry.Logs.OpenTelemetryLoggerOptions! +static OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions.AddOneCollectorExporter(this OpenTelemetry.Logs.OpenTelemetryLoggerOptions! options, System.Action! configure) -> OpenTelemetry.Logs.OpenTelemetryLoggerOptions! diff --git a/src/OpenTelemetry.Exporter.OneCollector/.publicApi/netstandard2.0/PublicAPI.Unshipped.txt b/src/OpenTelemetry.Exporter.OneCollector/.publicApi/netstandard2.0/PublicAPI.Unshipped.txt index 438e9e6c3d..baf438cdc1 100644 --- a/src/OpenTelemetry.Exporter.OneCollector/.publicApi/netstandard2.0/PublicAPI.Unshipped.txt +++ b/src/OpenTelemetry.Exporter.OneCollector/.publicApi/netstandard2.0/PublicAPI.Unshipped.txt @@ -1,8 +1,15 @@ OpenTelemetry.Exporter.OneCollector.OneCollectorExporter +OpenTelemetry.Exporter.OneCollector.OneCollectorExporter.RegisterPayloadTransmittedCallback(OpenTelemetry.Exporter.OneCollector.OneCollectorExporterPayloadTransmittedCallbackAction! callback) -> System.IDisposable? OpenTelemetry.Exporter.OneCollector.OneCollectorExporterOptions OpenTelemetry.Exporter.OneCollector.OneCollectorExporterOptions.ConnectionString.get -> string? OpenTelemetry.Exporter.OneCollector.OneCollectorExporterOptions.ConnectionString.set -> void OpenTelemetry.Exporter.OneCollector.OneCollectorExporterOptions.TransportOptions.get -> OpenTelemetry.Exporter.OneCollector.OneCollectorExporterTransportOptions! +OpenTelemetry.Exporter.OneCollector.OneCollectorExporterPayloadTransmittedCallbackAction +OpenTelemetry.Exporter.OneCollector.OneCollectorExporterPayloadTransmittedCallbackArguments +OpenTelemetry.Exporter.OneCollector.OneCollectorExporterPayloadTransmittedCallbackArguments.CopyPayloadToStream(System.IO.Stream! destination) -> void +OpenTelemetry.Exporter.OneCollector.OneCollectorExporterPayloadTransmittedCallbackArguments.OneCollectorExporterPayloadTransmittedCallbackArguments() -> void +OpenTelemetry.Exporter.OneCollector.OneCollectorExporterPayloadTransmittedCallbackArguments.PayloadSizeInBytes.get -> long +OpenTelemetry.Exporter.OneCollector.OneCollectorExporterPayloadTransmittedCallbackArguments.TransportEndpoint.get -> System.Uri! OpenTelemetry.Exporter.OneCollector.OneCollectorExporterTransportOptions OpenTelemetry.Exporter.OneCollector.OneCollectorExporterTransportOptions.Endpoint.get -> System.Uri! OpenTelemetry.Exporter.OneCollector.OneCollectorExporterTransportOptions.Endpoint.set -> void @@ -10,22 +17,20 @@ OpenTelemetry.Exporter.OneCollector.OneCollectorExporterValidationException OpenTelemetry.Exporter.OneCollector.OneCollectorExporterValidationException.OneCollectorExporterValidationException() -> void OpenTelemetry.Exporter.OneCollector.OneCollectorExporterValidationException.OneCollectorExporterValidationException(string! message) -> void OpenTelemetry.Exporter.OneCollector.OneCollectorExporterValidationException.OneCollectorExporterValidationException(string! message, System.Exception? innerException) -> void -OpenTelemetry.Exporter.OneCollector.OneCollectorLogExporter -OpenTelemetry.Exporter.OneCollector.OneCollectorLogExporter.OneCollectorLogExporter(OpenTelemetry.Exporter.OneCollector.OneCollectorLogExporterOptions! options) -> void OpenTelemetry.Exporter.OneCollector.OneCollectorLogExporterOptions -OpenTelemetry.Exporter.OneCollector.OneCollectorLogExporterOptions.BatchOptions.get -> OpenTelemetry.BatchExportProcessorOptions! OpenTelemetry.Exporter.OneCollector.OneCollectorLogExporterOptions.DefaultEventName.get -> string! OpenTelemetry.Exporter.OneCollector.OneCollectorLogExporterOptions.DefaultEventName.set -> void OpenTelemetry.Exporter.OneCollector.OneCollectorLogExporterOptions.OneCollectorLogExporterOptions() -> void -OpenTelemetry.Logs.OneCollectorLogExporterBuilder -OpenTelemetry.Logs.OneCollectorLogExporterBuilder.ConfigureBatchOptions(System.Action!>! configure) -> OpenTelemetry.Logs.OneCollectorLogExporterBuilder! -OpenTelemetry.Logs.OneCollectorLogExporterBuilder.ConfigureTransportOptions(System.Action! configure) -> OpenTelemetry.Logs.OneCollectorLogExporterBuilder! -OpenTelemetry.Logs.OneCollectorLogExporterBuilder.SetConnectionString(string! connectionString) -> OpenTelemetry.Logs.OneCollectorLogExporterBuilder! -OpenTelemetry.Logs.OneCollectorLogExporterBuilder.SetDefaultEventName(string! defaultEventName) -> OpenTelemetry.Logs.OneCollectorLogExporterBuilder! +OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder +OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder.ConfigureBatchOptions(System.Action!>! configure) -> OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder! +OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder.ConfigureExporter(System.Action!>! configure) -> OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder! +OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder.ConfigureTransportOptions(System.Action! configure) -> OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder! +OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder.SetConnectionString(string! connectionString) -> OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder! +OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder.SetDefaultEventName(string! defaultEventName) -> OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder! OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions override sealed OpenTelemetry.Exporter.OneCollector.OneCollectorExporter.Export(in OpenTelemetry.Batch batch) -> OpenTelemetry.ExportResult static OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions.AddOneCollectorExporter(this OpenTelemetry.Logs.OpenTelemetryLoggerOptions! options, Microsoft.Extensions.Configuration.IConfiguration! configuration) -> OpenTelemetry.Logs.OpenTelemetryLoggerOptions! -static OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions.AddOneCollectorExporter(this OpenTelemetry.Logs.OpenTelemetryLoggerOptions! options, Microsoft.Extensions.Configuration.IConfiguration! configuration, System.Action! configure) -> OpenTelemetry.Logs.OpenTelemetryLoggerOptions! +static OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions.AddOneCollectorExporter(this OpenTelemetry.Logs.OpenTelemetryLoggerOptions! options, Microsoft.Extensions.Configuration.IConfiguration! configuration, System.Action! configure) -> OpenTelemetry.Logs.OpenTelemetryLoggerOptions! static OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions.AddOneCollectorExporter(this OpenTelemetry.Logs.OpenTelemetryLoggerOptions! options, string! connectionString) -> OpenTelemetry.Logs.OpenTelemetryLoggerOptions! -static OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions.AddOneCollectorExporter(this OpenTelemetry.Logs.OpenTelemetryLoggerOptions! options, string! connectionString, System.Action! configure) -> OpenTelemetry.Logs.OpenTelemetryLoggerOptions! -static OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions.AddOneCollectorExporter(this OpenTelemetry.Logs.OpenTelemetryLoggerOptions! options, System.Action! configure) -> OpenTelemetry.Logs.OpenTelemetryLoggerOptions! +static OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions.AddOneCollectorExporter(this OpenTelemetry.Logs.OpenTelemetryLoggerOptions! options, string! connectionString, System.Action! configure) -> OpenTelemetry.Logs.OpenTelemetryLoggerOptions! +static OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions.AddOneCollectorExporter(this OpenTelemetry.Logs.OpenTelemetryLoggerOptions! options, System.Action! configure) -> OpenTelemetry.Logs.OpenTelemetryLoggerOptions! diff --git a/src/OpenTelemetry.Exporter.OneCollector/.publicApi/netstandard2.1/PublicAPI.Unshipped.txt b/src/OpenTelemetry.Exporter.OneCollector/.publicApi/netstandard2.1/PublicAPI.Unshipped.txt index 9087227582..baf438cdc1 100644 --- a/src/OpenTelemetry.Exporter.OneCollector/.publicApi/netstandard2.1/PublicAPI.Unshipped.txt +++ b/src/OpenTelemetry.Exporter.OneCollector/.publicApi/netstandard2.1/PublicAPI.Unshipped.txt @@ -1,8 +1,15 @@ OpenTelemetry.Exporter.OneCollector.OneCollectorExporter +OpenTelemetry.Exporter.OneCollector.OneCollectorExporter.RegisterPayloadTransmittedCallback(OpenTelemetry.Exporter.OneCollector.OneCollectorExporterPayloadTransmittedCallbackAction! callback) -> System.IDisposable? OpenTelemetry.Exporter.OneCollector.OneCollectorExporterOptions OpenTelemetry.Exporter.OneCollector.OneCollectorExporterOptions.ConnectionString.get -> string? OpenTelemetry.Exporter.OneCollector.OneCollectorExporterOptions.ConnectionString.set -> void OpenTelemetry.Exporter.OneCollector.OneCollectorExporterOptions.TransportOptions.get -> OpenTelemetry.Exporter.OneCollector.OneCollectorExporterTransportOptions! +OpenTelemetry.Exporter.OneCollector.OneCollectorExporterPayloadTransmittedCallbackAction +OpenTelemetry.Exporter.OneCollector.OneCollectorExporterPayloadTransmittedCallbackArguments +OpenTelemetry.Exporter.OneCollector.OneCollectorExporterPayloadTransmittedCallbackArguments.CopyPayloadToStream(System.IO.Stream! destination) -> void +OpenTelemetry.Exporter.OneCollector.OneCollectorExporterPayloadTransmittedCallbackArguments.OneCollectorExporterPayloadTransmittedCallbackArguments() -> void +OpenTelemetry.Exporter.OneCollector.OneCollectorExporterPayloadTransmittedCallbackArguments.PayloadSizeInBytes.get -> long +OpenTelemetry.Exporter.OneCollector.OneCollectorExporterPayloadTransmittedCallbackArguments.TransportEndpoint.get -> System.Uri! OpenTelemetry.Exporter.OneCollector.OneCollectorExporterTransportOptions OpenTelemetry.Exporter.OneCollector.OneCollectorExporterTransportOptions.Endpoint.get -> System.Uri! OpenTelemetry.Exporter.OneCollector.OneCollectorExporterTransportOptions.Endpoint.set -> void @@ -10,22 +17,20 @@ OpenTelemetry.Exporter.OneCollector.OneCollectorExporterValidationException OpenTelemetry.Exporter.OneCollector.OneCollectorExporterValidationException.OneCollectorExporterValidationException() -> void OpenTelemetry.Exporter.OneCollector.OneCollectorExporterValidationException.OneCollectorExporterValidationException(string! message) -> void OpenTelemetry.Exporter.OneCollector.OneCollectorExporterValidationException.OneCollectorExporterValidationException(string! message, System.Exception? innerException) -> void -OpenTelemetry.Exporter.OneCollector.OneCollectorLogExporter -OpenTelemetry.Exporter.OneCollector.OneCollectorLogExporter.OneCollectorLogExporter(OpenTelemetry.Exporter.OneCollector.OneCollectorLogExporterOptions! options) -> void OpenTelemetry.Exporter.OneCollector.OneCollectorLogExporterOptions -OpenTelemetry.Exporter.OneCollector.OneCollectorLogExporterOptions.BatchOptions.get -> OpenTelemetry.BatchExportProcessorOptions! OpenTelemetry.Exporter.OneCollector.OneCollectorLogExporterOptions.DefaultEventName.get -> string! OpenTelemetry.Exporter.OneCollector.OneCollectorLogExporterOptions.DefaultEventName.set -> void OpenTelemetry.Exporter.OneCollector.OneCollectorLogExporterOptions.OneCollectorLogExporterOptions() -> void -OpenTelemetry.Logs.OneCollectorLogExporterBuilder -OpenTelemetry.Logs.OneCollectorLogExporterBuilder.ConfigureBatchOptions(System.Action!>! configure) -> OpenTelemetry.Logs.OneCollectorLogExporterBuilder! -OpenTelemetry.Logs.OneCollectorLogExporterBuilder.ConfigureTransportOptions(System.Action! configure) -> OpenTelemetry.Logs.OneCollectorLogExporterBuilder! -OpenTelemetry.Logs.OneCollectorLogExporterBuilder.SetConnectionString(string! connectionString) -> OpenTelemetry.Logs.OneCollectorLogExporterBuilder! -OpenTelemetry.Logs.OneCollectorLogExporterBuilder.SetDefaultEventName(string! defaultEventName) -> OpenTelemetry.Logs.OneCollectorLogExporterBuilder! +OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder +OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder.ConfigureBatchOptions(System.Action!>! configure) -> OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder! +OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder.ConfigureExporter(System.Action!>! configure) -> OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder! +OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder.ConfigureTransportOptions(System.Action! configure) -> OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder! +OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder.SetConnectionString(string! connectionString) -> OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder! +OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder.SetDefaultEventName(string! defaultEventName) -> OpenTelemetry.Logs.OneCollectorLogExportProcessorBuilder! OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions override sealed OpenTelemetry.Exporter.OneCollector.OneCollectorExporter.Export(in OpenTelemetry.Batch batch) -> OpenTelemetry.ExportResult static OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions.AddOneCollectorExporter(this OpenTelemetry.Logs.OpenTelemetryLoggerOptions! options, Microsoft.Extensions.Configuration.IConfiguration! configuration) -> OpenTelemetry.Logs.OpenTelemetryLoggerOptions! -static OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions.AddOneCollectorExporter(this OpenTelemetry.Logs.OpenTelemetryLoggerOptions! options, Microsoft.Extensions.Configuration.IConfiguration! configuration, System.Action! configure) -> OpenTelemetry.Logs.OpenTelemetryLoggerOptions! +static OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions.AddOneCollectorExporter(this OpenTelemetry.Logs.OpenTelemetryLoggerOptions! options, Microsoft.Extensions.Configuration.IConfiguration! configuration, System.Action! configure) -> OpenTelemetry.Logs.OpenTelemetryLoggerOptions! static OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions.AddOneCollectorExporter(this OpenTelemetry.Logs.OpenTelemetryLoggerOptions! options, string! connectionString) -> OpenTelemetry.Logs.OpenTelemetryLoggerOptions! -static OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions.AddOneCollectorExporter(this OpenTelemetry.Logs.OpenTelemetryLoggerOptions! options, string! connectionString, System.Action! configure) -> OpenTelemetry.Logs.OpenTelemetryLoggerOptions! -static OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions.AddOneCollectorExporter(this OpenTelemetry.Logs.OpenTelemetryLoggerOptions! options, System.Action! configure) -> OpenTelemetry.Logs.OpenTelemetryLoggerOptions! \ No newline at end of file +static OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions.AddOneCollectorExporter(this OpenTelemetry.Logs.OpenTelemetryLoggerOptions! options, string! connectionString, System.Action! configure) -> OpenTelemetry.Logs.OpenTelemetryLoggerOptions! +static OpenTelemetry.Logs.OneCollectorOpenTelemetryLoggerOptionsExtensions.AddOneCollectorExporter(this OpenTelemetry.Logs.OpenTelemetryLoggerOptions! options, System.Action! configure) -> OpenTelemetry.Logs.OpenTelemetryLoggerOptions! diff --git a/src/OpenTelemetry.Exporter.OneCollector/CHANGELOG.md b/src/OpenTelemetry.Exporter.OneCollector/CHANGELOG.md index 16a028098e..a3b6cab3dd 100644 --- a/src/OpenTelemetry.Exporter.OneCollector/CHANGELOG.md +++ b/src/OpenTelemetry.Exporter.OneCollector/CHANGELOG.md @@ -14,6 +14,9 @@ instrumentation key directly. ([#1037](https://github.com/open-telemetry/opentelemetry-dotnet-contrib/pull/1037)) +* Added `RegisterPayloadTransmittedCallback` API on `OneCollectorExporter`. + ([#1058](https://github.com/open-telemetry/opentelemetry-dotnet-contrib/pull/1058)) + ## 0.1.0-alpha.1 Released 2023-Feb-16 diff --git a/src/OpenTelemetry.Exporter.OneCollector/Internal/CallbackManager.cs b/src/OpenTelemetry.Exporter.OneCollector/Internal/CallbackManager.cs new file mode 100644 index 0000000000..a545bce80a --- /dev/null +++ b/src/OpenTelemetry.Exporter.OneCollector/Internal/CallbackManager.cs @@ -0,0 +1,78 @@ +// +// Copyright The OpenTelemetry Authors +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// + +using System.Diagnostics; + +namespace OpenTelemetry.Exporter.OneCollector; + +internal sealed class CallbackManager : IDisposable + where T : Delegate +{ + private readonly object lockObject = new(); + private T? root; + private bool disposed; + + public T? Root { get => this.root; } + + public IDisposable Add(T callback) + { + Debug.Assert(callback != null, "callback was null"); + + lock (this.lockObject) + { + if (this.disposed) + { + throw new ObjectDisposedException(nameof(CallbackManager)); + } + + this.root = (T)Delegate.Combine(this.root, callback); + } + + return new CallbackManagerRegistration(() => + { + lock (this.lockObject) + { + this.root = (T?)Delegate.Remove(this.root, callback); + } + }); + } + + public void Dispose() + { + lock (this.lockObject) + { + this.root = null; + this.disposed = true; + } + } + + private sealed class CallbackManagerRegistration : IDisposable + { + private readonly Action disposeAction; + + public CallbackManagerRegistration(Action disposeAction) + { + Debug.Assert(disposeAction != null, "disposeAction was null"); + + this.disposeAction = disposeAction!; + } + + public void Dispose() + { + this.disposeAction(); + } + } +} diff --git a/src/OpenTelemetry.Exporter.OneCollector/Internal/OneCollectorExporterEventSource.cs b/src/OpenTelemetry.Exporter.OneCollector/Internal/OneCollectorExporterEventSource.cs index aa5f21c7be..0ab1a1eb0c 100644 --- a/src/OpenTelemetry.Exporter.OneCollector/Internal/OneCollectorExporterEventSource.cs +++ b/src/OpenTelemetry.Exporter.OneCollector/Internal/OneCollectorExporterEventSource.cs @@ -73,6 +73,15 @@ public void WriteHttpTransportErrorResponseReceivedEventIfEnabled(string transpo } } + [NonEvent] + public void WriteExceptionThrownFromUserCodeEventIfEnabled(string userCodeType, Exception exception) + { + if (this.IsEnabled(EventLevel.Error, EventKeywords.All)) + { + this.ExceptionThrownFromUserCode(userCodeType, ExceptionToInvariantString(exception)); + } + } + [Event(1, Message = "Exception thrown exporting '{0}' batch: {1}.", Level = EventLevel.Error)] public void ExportExceptionThrown(string itemType, string exception) { @@ -127,6 +136,12 @@ public void EventNameInvalid(string eventName) this.WriteEvent(9, eventName); } + [Event(10, Message = "Exception thrown by '{0}' user code: {1}", Level = EventLevel.Error)] + public void ExceptionThrownFromUserCode(string userCodeType, string exception) + { + this.WriteEvent(10, userCodeType, exception); + } + /// /// Returns a culture-independent string representation of the given object, /// appropriate for diagnostics tracing. diff --git a/src/OpenTelemetry.Exporter.OneCollector/Internal/Serialization/CommonSchemaJsonSerializer.cs b/src/OpenTelemetry.Exporter.OneCollector/Internal/Serialization/CommonSchemaJsonSerializer.cs index a6cf0d7a64..bd9793ca70 100644 --- a/src/OpenTelemetry.Exporter.OneCollector/Internal/Serialization/CommonSchemaJsonSerializer.cs +++ b/src/OpenTelemetry.Exporter.OneCollector/Internal/Serialization/CommonSchemaJsonSerializer.cs @@ -53,6 +53,8 @@ protected CommonSchemaJsonSerializer( public abstract string Description { get; } + public OneCollectorExporterSerializationFormatType SerializationFormat => OneCollectorExporterSerializationFormatType.CommonSchemaV4JsonStream; + protected JsonEncodedText TenantTokenWithTenancySystemSymbol { get; } public void SerializeBatchOfItemsToStream(Resource resource, in Batch batch, Stream stream, int initialSizeOfPayloadInBytes, out BatchSerializationResult result) diff --git a/src/OpenTelemetry.Exporter.OneCollector/Internal/Serialization/ISerializer.cs b/src/OpenTelemetry.Exporter.OneCollector/Internal/Serialization/ISerializer.cs index bcd607f084..1b2669aeeb 100644 --- a/src/OpenTelemetry.Exporter.OneCollector/Internal/Serialization/ISerializer.cs +++ b/src/OpenTelemetry.Exporter.OneCollector/Internal/Serialization/ISerializer.cs @@ -23,6 +23,8 @@ internal interface ISerializer { string Description { get; } + OneCollectorExporterSerializationFormatType SerializationFormat { get; } + void SerializeBatchOfItemsToStream( Resource resource, in Batch batch, diff --git a/src/OpenTelemetry.Exporter.OneCollector/Internal/Sinks/ISink.cs b/src/OpenTelemetry.Exporter.OneCollector/Internal/Sinks/ISink.cs index ba914c1e10..e404f1f548 100644 --- a/src/OpenTelemetry.Exporter.OneCollector/Internal/Sinks/ISink.cs +++ b/src/OpenTelemetry.Exporter.OneCollector/Internal/Sinks/ISink.cs @@ -23,5 +23,7 @@ internal interface ISink { string Description { get; } + ITransport? Transport { get; } + int Write(Resource resource, in Batch batch); } diff --git a/src/OpenTelemetry.Exporter.OneCollector/Internal/Sinks/WriteDirectlyToTransportSink.cs b/src/OpenTelemetry.Exporter.OneCollector/Internal/Sinks/WriteDirectlyToTransportSink.cs index b6f49c6866..3f228dba0b 100644 --- a/src/OpenTelemetry.Exporter.OneCollector/Internal/Sinks/WriteDirectlyToTransportSink.cs +++ b/src/OpenTelemetry.Exporter.OneCollector/Internal/Sinks/WriteDirectlyToTransportSink.cs @@ -28,7 +28,6 @@ internal sealed class WriteDirectlyToTransportSink : ISink, IDisposable { private readonly string typeName; private readonly ISerializer serializer; - private readonly ITransport transport; private readonly MemoryStream buffer; public WriteDirectlyToTransportSink( @@ -42,12 +41,14 @@ public WriteDirectlyToTransportSink( this.typeName = typeof(T).Name; this.serializer = serializer; - this.transport = transport; + this.Transport = transport; this.buffer = new(initialBufferCapacity); } public string Description => "WriteDirectlyToTransportSink"; + public ITransport Transport { get; } + internal MemoryStream Buffer => this.buffer; public void Dispose() @@ -55,7 +56,7 @@ public void Dispose() this.TrySendRemainingData(); (this.serializer as IDisposable)?.Dispose(); - (this.transport as IDisposable)?.Dispose(); + (this.Transport as IDisposable)?.Dispose(); } public int Write(Resource resource, in Batch batch) @@ -97,10 +98,11 @@ public int Write(Resource resource, in Batch batch) buffer.Position = 0; - if (!this.transport.Send( + if (!this.Transport.Send( new TransportSendRequest { ItemType = this.typeName, + ItemSerializationFormat = this.serializer.SerializationFormat, ItemStream = buffer, NumberOfItems = numberOfItemsToSend, })) @@ -147,10 +149,11 @@ private void TrySendRemainingData() try { - if (!this.transport.Send( + if (!this.Transport.Send( new TransportSendRequest { ItemType = this.typeName, + ItemSerializationFormat = this.serializer.SerializationFormat, ItemStream = buffer, NumberOfItems = 1, })) diff --git a/src/OpenTelemetry.Exporter.OneCollector/Internal/Transports/HttpJsonPostTransport.cs b/src/OpenTelemetry.Exporter.OneCollector/Internal/Transports/HttpJsonPostTransport.cs index f2b6d78af3..2324ef4a97 100644 --- a/src/OpenTelemetry.Exporter.OneCollector/Internal/Transports/HttpJsonPostTransport.cs +++ b/src/OpenTelemetry.Exporter.OneCollector/Internal/Transports/HttpJsonPostTransport.cs @@ -18,6 +18,7 @@ using System.IO.Compression; using System.Net; using System.Net.Http.Headers; +using OpenTelemetry.Internal; namespace OpenTelemetry.Exporter.OneCollector; @@ -26,6 +27,7 @@ internal sealed class HttpJsonPostTransport : ITransport, IDisposable private static readonly string SdkVersion = $"OTel-{Environment.OSVersion.Platform}-.net-{typeof(OneCollectorExporter<>).Assembly.GetName()?.Version?.ToString() ?? "0.0.0"}"; private static readonly string UserAgent = $".NET/{Environment.Version} HttpClient"; + private readonly CallbackManager payloadTransmittedCallbacks = new(); private readonly Uri endpoint; private readonly string instrumentationKey; private readonly OneCollectorExporterHttpTransportCompressionType compressionType; @@ -54,11 +56,26 @@ public HttpJsonPostTransport( public void Dispose() { + this.payloadTransmittedCallbacks.Dispose(); this.buffer?.Dispose(); } + public IDisposable RegisterPayloadTransmittedCallback(OneCollectorExporterPayloadTransmittedCallbackAction callback) + { + Guard.ThrowIfNull(callback); + + return this.payloadTransmittedCallbacks.Add(callback); + } + public bool Send(in TransportSendRequest sendRequest) { + Debug.Assert(sendRequest.ItemStream.CanSeek, "ItemStream was not seekable."); + Debug.Assert( + sendRequest.ItemSerializationFormat == OneCollectorExporterSerializationFormatType.CommonSchemaV4JsonStream, + "sendRequest.ItemSerializationFormat was not CommonSchemaV4JsonStream"); + + var streamStartingPosition = sendRequest.ItemStream.Position; + // Prevent OneCollector's HTTP operations from being instrumented. using var scope = SuppressInstrumentationScope.Begin(); @@ -98,6 +115,17 @@ public bool Send(in TransportSendRequest sendRequest) response.EnsureSuccessStatusCode(); OneCollectorExporterEventSource.Log.WriteTransportDataSentEventIfEnabled(sendRequest.ItemType, sendRequest.NumberOfItems, this.Description); + + var root = this.payloadTransmittedCallbacks.Root; + if (root != null) + { + this.InvokePayloadTransmittedCallbacks( + root, + streamStartingPosition, + in sendRequest); + } + + return true; } catch { @@ -120,8 +148,6 @@ public bool Send(in TransportSendRequest sendRequest) return false; } - - return true; } private HttpContent BuildRequestContent(Stream stream) @@ -160,6 +186,36 @@ private HttpContent BuildRequestContent(Stream stream) } } + private void InvokePayloadTransmittedCallbacks( + OneCollectorExporterPayloadTransmittedCallbackAction callback, + long streamStartingPosition, + in TransportSendRequest sendRequest) + { + var stream = sendRequest.ItemStream; + + var currentPosition = stream.Position; + + try + { + stream.Position = streamStartingPosition; + + callback( + new OneCollectorExporterPayloadTransmittedCallbackArguments( + sendRequest.ItemSerializationFormat, + stream, + OneCollectorExporterTransportProtocolType.HttpJsonPost, + this.endpoint)); + } + catch (Exception ex) + { + OneCollectorExporterEventSource.Log.WriteExceptionThrownFromUserCodeEventIfEnabled("PayloadTransmittedCallback", ex); + } + finally + { + stream.Position = currentPosition; + } + } + private sealed class NonDisposingStreamContent : HttpContent { #pragma warning disable CA2213 // Disposable fields should be disposed @@ -176,16 +232,8 @@ public NonDisposingStreamContent(Stream stream) protected override bool TryComputeLength(out long length) { var stream = this.stream; - if (stream.CanSeek) - { - length = stream.Length - stream.Position; - return true; - } - else - { - length = 0; - return false; - } + length = stream.Length - stream.Position; + return true; } #if NET6_0_OR_GREATER diff --git a/src/OpenTelemetry.Exporter.OneCollector/Internal/Transports/ITransport.cs b/src/OpenTelemetry.Exporter.OneCollector/Internal/Transports/ITransport.cs index 9edc4a601e..4abed07d5b 100644 --- a/src/OpenTelemetry.Exporter.OneCollector/Internal/Transports/ITransport.cs +++ b/src/OpenTelemetry.Exporter.OneCollector/Internal/Transports/ITransport.cs @@ -21,4 +21,6 @@ internal interface ITransport string Description { get; } bool Send(in TransportSendRequest sendRequest); + + IDisposable RegisterPayloadTransmittedCallback(OneCollectorExporterPayloadTransmittedCallbackAction callback); } diff --git a/src/OpenTelemetry.Exporter.OneCollector/Internal/Transports/TransportSendRequest.cs b/src/OpenTelemetry.Exporter.OneCollector/Internal/Transports/TransportSendRequest.cs index 90505bfa41..7490be62a2 100644 --- a/src/OpenTelemetry.Exporter.OneCollector/Internal/Transports/TransportSendRequest.cs +++ b/src/OpenTelemetry.Exporter.OneCollector/Internal/Transports/TransportSendRequest.cs @@ -36,12 +36,18 @@ public TransportSendRequest() #if NET7_0_OR_GREATER public required string ItemType { get; init; } + public required OneCollectorExporterSerializationFormatType ItemSerializationFormat { get; init; } + public required Stream ItemStream { get; init; } + + public required int NumberOfItems { get; init; } #else public string ItemType { get; init; } + public OneCollectorExporterSerializationFormatType ItemSerializationFormat { get; init; } + public Stream ItemStream { get; init; } -#endif - public int? NumberOfItems { get; init; } + public int NumberOfItems { get; init; } +#endif } diff --git a/src/OpenTelemetry.Exporter.OneCollector/Logs/OneCollectorLogExportProcessorBuilder.cs b/src/OpenTelemetry.Exporter.OneCollector/Logs/OneCollectorLogExportProcessorBuilder.cs new file mode 100644 index 0000000000..69e47a6734 --- /dev/null +++ b/src/OpenTelemetry.Exporter.OneCollector/Logs/OneCollectorLogExportProcessorBuilder.cs @@ -0,0 +1,225 @@ +// +// Copyright The OpenTelemetry Authors +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// + +using Microsoft.Extensions.Configuration; +using OpenTelemetry.Exporter.OneCollector; +using OpenTelemetry.Internal; + +namespace OpenTelemetry.Logs; + +/// +/// Contains methods for building and instances for exporting telemetry data. +/// +public sealed class OneCollectorLogExportProcessorBuilder +{ + private static readonly Func DefaultHttpClientFactory = () => new HttpClient(); + private readonly OneCollectorLogExporterOptions exporterOptions = new(); + private readonly BatchExportProcessorOptions batchOptions = new(); + private readonly List>> configureExporterActions = new(); + private Func? httpClientFactory; + + internal OneCollectorLogExportProcessorBuilder( + IConfiguration? configuration) + { + if (configuration != null) + { + configuration.Bind(this.exporterOptions); + configuration.GetSection("BatchOptions").Bind(this.batchOptions); + } + } + + /// + /// Register a callback action for configuring the batch options of the + /// processor used to invoke the . + /// + /// Callback action for configuring . + /// The supplied for call + /// chaining. + public OneCollectorLogExportProcessorBuilder ConfigureBatchOptions( + Action> configure) + { + Guard.ThrowIfNull(configure); + + configure(this.batchOptions); + + return this; + } + + /// + /// Register a callback action for configuring the created by the builder. + /// + /// Callback action for configuring . + /// The supplied for call + /// chaining. + public OneCollectorLogExportProcessorBuilder ConfigureExporter( + Action> configure) + { + Guard.ThrowIfNull(configure); + + this.configureExporterActions.Add(configure); + + return this; + } + + /// + /// Register a callback action for configuring the transport options used by + /// the created by the builder. + /// + /// Callback action for configuring . + /// The supplied for call + /// chaining. + public OneCollectorLogExportProcessorBuilder ConfigureTransportOptions( + Action configure) + { + Guard.ThrowIfNull(configure); + + configure(this.exporterOptions.TransportOptions); + + return this; + } + + /// + /// Sets the connection string used by the created by the builder. + /// + /// + /// Connection string. + /// The supplied for call + /// chaining. + public OneCollectorLogExportProcessorBuilder SetConnectionString( + string connectionString) + { + Guard.ThrowIfNullOrWhitespace(connectionString); + + this.exporterOptions.ConnectionString = connectionString; + + return this; + } + + /// + /// Sets the default event name used by the created by the builder. Default value: + /// Log. + /// + /// + /// Default event name. + /// The supplied for call + /// chaining. + public OneCollectorLogExportProcessorBuilder SetDefaultEventName( + string defaultEventName) + { + Guard.ThrowIfNullOrWhitespace(defaultEventName); + + this.exporterOptions.DefaultEventName = defaultEventName; + + return this; + } + + /// + /// Sets the factory function called to create the + /// instance that will be used at runtime to transmit telemetry over HTTP + /// transports. The returned instance will be reused for all export + /// invocations. + /// + /// + /// Note: The default behavior is an will be + /// instantiated directly. + /// + /// Factory function which returns the instance to use. + /// The supplied for call + /// chaining. + internal OneCollectorLogExportProcessorBuilder SetHttpClientFactory( + Func httpClientFactory) + { + Guard.ThrowIfNull(httpClientFactory); + + this.httpClientFactory = httpClientFactory; + + return this; + } + + internal BaseProcessor BuildProcessor() + { +#pragma warning disable CA2000 // Dispose objects before losing scope + return new BatchLogRecordExportProcessor( + this.BuildExporter(), + this.batchOptions.MaxQueueSize, + this.batchOptions.ScheduledDelayMilliseconds, + this.batchOptions.ExporterTimeoutMilliseconds, + this.batchOptions.MaxExportBatchSize); +#pragma warning restore CA2000 // Dispose objects before losing scope + } + + private OneCollectorExporter BuildExporter() + { + var exporter = new OneCollectorExporter(this.CreateSink()); + + try + { + int index = 0; + while (index < this.configureExporterActions.Count) + { + var action = this.configureExporterActions[index++]; + action(exporter); + } + } + catch + { + exporter.Dispose(); + throw; + } + + return exporter; + } + + private ISink CreateSink() + { + this.exporterOptions.Validate(); + + var transportOptions = this.exporterOptions.TransportOptions; + +#pragma warning disable CA2000 // Dispose objects before losing scope + return new WriteDirectlyToTransportSink( + new LogRecordCommonSchemaJsonSerializer( + new EventNameManager(this.exporterOptions.DefaultEventNamespace, this.exporterOptions.DefaultEventName), + this.exporterOptions.TenantToken!, + transportOptions.MaxPayloadSizeInBytes == -1 ? int.MaxValue : transportOptions.MaxPayloadSizeInBytes, + transportOptions.MaxNumberOfItemsPerPayload == -1 ? int.MaxValue : transportOptions.MaxNumberOfItemsPerPayload), + new HttpJsonPostTransport( + this.exporterOptions.InstrumentationKey!, + transportOptions.Endpoint, + transportOptions.HttpCompression, + (this.httpClientFactory ?? DefaultHttpClientFactory)() ?? throw new NotSupportedException("HttpClientFactory cannot return a null instance."))); +#pragma warning restore CA2000 // Dispose objects before losing scope + } +} diff --git a/src/OpenTelemetry.Exporter.OneCollector/Logs/OneCollectorLogExporter.cs b/src/OpenTelemetry.Exporter.OneCollector/Logs/OneCollectorLogExporter.cs deleted file mode 100644 index 85d86f3ba2..0000000000 --- a/src/OpenTelemetry.Exporter.OneCollector/Logs/OneCollectorLogExporter.cs +++ /dev/null @@ -1,35 +0,0 @@ -// -// Copyright The OpenTelemetry Authors -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. -// - -using OpenTelemetry.Logs; - -namespace OpenTelemetry.Exporter.OneCollector; - -/// -/// OpenTelemetry exporter implementation for sending -/// telemetry data to Microsoft OneCollector. -/// -public sealed class OneCollectorLogExporter : OneCollectorExporter -{ - /// - /// Initializes a new instance of the class. - /// - /// . - public OneCollectorLogExporter(OneCollectorLogExporterOptions options) - : base(options) - { - } -} diff --git a/src/OpenTelemetry.Exporter.OneCollector/Logs/OneCollectorLogExporterBuilder.cs b/src/OpenTelemetry.Exporter.OneCollector/Logs/OneCollectorLogExporterBuilder.cs deleted file mode 100644 index 52aa8a807e..0000000000 --- a/src/OpenTelemetry.Exporter.OneCollector/Logs/OneCollectorLogExporterBuilder.cs +++ /dev/null @@ -1,118 +0,0 @@ -// -// Copyright The OpenTelemetry Authors -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. -// - -using System.Diagnostics; -using Microsoft.Extensions.Configuration; -using OpenTelemetry.Exporter.OneCollector; -using OpenTelemetry.Internal; - -namespace OpenTelemetry.Logs; - -/// -/// Contains methods for building instances. -/// -public sealed class OneCollectorLogExporterBuilder -{ - internal OneCollectorLogExporterBuilder(string? connectionString) - { - this.Options = new() - { - ConnectionString = connectionString, - }; - } - - internal OneCollectorLogExporterBuilder(IConfiguration configuration) - : this(connectionString: null) - { - Debug.Assert(configuration != null, "configuration was null"); - - configuration.Bind(this.Options); - } - - internal OneCollectorLogExporterOptions Options { get; } - - /// - /// Register a callback action for configuring the batch options of . - /// - /// Callback action for configuring . - /// The supplied for - /// call chaining. - public OneCollectorLogExporterBuilder ConfigureBatchOptions(Action> configure) - { - Guard.ThrowIfNull(configure); - - configure(this.Options.BatchOptions); - - return this; - } - - /// - /// Register a callback action for configuring the transport options of . - /// - /// Callback action for configuring . - /// The supplied for - /// call chaining. - public OneCollectorLogExporterBuilder ConfigureTransportOptions(Action configure) - { - Guard.ThrowIfNull(configure); - - configure(this.Options.TransportOptions); - - return this; - } - - /// - /// Sets the - /// property. - /// - /// - /// Connection string. - /// The supplied for - /// call chaining. - public OneCollectorLogExporterBuilder SetConnectionString(string connectionString) - { - Guard.ThrowIfNullOrWhitespace(connectionString); - - this.Options.ConnectionString = connectionString; - - return this; - } - - /// - /// Sets the - /// property. Default value: Log. - /// - /// - /// Default event name. - /// The supplied for - /// call chaining. - public OneCollectorLogExporterBuilder SetDefaultEventName(string defaultEventName) - { - Guard.ThrowIfNullOrWhitespace(defaultEventName); - - this.Options.DefaultEventName = defaultEventName; - - return this; - } -} diff --git a/src/OpenTelemetry.Exporter.OneCollector/Logs/OneCollectorLogExporterOptions.cs b/src/OpenTelemetry.Exporter.OneCollector/Logs/OneCollectorLogExporterOptions.cs index 2c036105e3..f6018e1f26 100644 --- a/src/OpenTelemetry.Exporter.OneCollector/Logs/OneCollectorLogExporterOptions.cs +++ b/src/OpenTelemetry.Exporter.OneCollector/Logs/OneCollectorLogExporterOptions.cs @@ -20,9 +20,10 @@ namespace OpenTelemetry.Exporter.OneCollector; /// -/// Contains options for the class. +/// Contains options used to build a +/// instance for exporting telemetry data. /// -public sealed class OneCollectorLogExporterOptions : OneCollectorExporterOptions, ISinkFactory +public sealed class OneCollectorLogExporterOptions : OneCollectorExporterOptions { /// /// Gets or sets the default event name. Default value: Log. @@ -34,11 +35,6 @@ public sealed class OneCollectorLogExporterOptions : OneCollectorExporterOptions /// public string DefaultEventName { get; set; } = "Log"; - /// - /// Gets the options. - /// - public BatchExportProcessorOptions BatchOptions { get; } = new(); - /// /// Gets or sets the default event namespace. Default value: /// OpenTelemetry.Logs. @@ -51,27 +47,6 @@ public sealed class OneCollectorLogExporterOptions : OneCollectorExporterOptions /// internal string DefaultEventNamespace { get; set; } = "OpenTelemetry.Logs"; - ISink ISinkFactory.CreateSink() - { - this.Validate(); - - var transportOptions = this.TransportOptions; - -#pragma warning disable CA2000 // Dispose objects before losing scope - return new WriteDirectlyToTransportSink( - new LogRecordCommonSchemaJsonSerializer( - new EventNameManager(this.DefaultEventNamespace, this.DefaultEventName), - this.TenantToken!, - transportOptions.MaxPayloadSizeInBytes == -1 ? int.MaxValue : transportOptions.MaxPayloadSizeInBytes, - transportOptions.MaxNumberOfItemsPerPayload == -1 ? int.MaxValue : transportOptions.MaxNumberOfItemsPerPayload), - new HttpJsonPostTransport( - this.InstrumentationKey!, - transportOptions.Endpoint, - transportOptions.HttpCompression, - transportOptions.HttpClientFactory() ?? throw new OneCollectorExporterValidationException($"{nameof(OneCollectorLogExporterOptions)} was missing HttpClientFactory or it returned null."))); -#pragma warning restore CA2000 // Dispose objects before losing scope - } - internal override void Validate() { if (string.IsNullOrWhiteSpace(this.DefaultEventNamespace)) diff --git a/src/OpenTelemetry.Exporter.OneCollector/Logs/OneCollectorOpenTelemetryLoggerOptionsExtensions.cs b/src/OpenTelemetry.Exporter.OneCollector/Logs/OneCollectorOpenTelemetryLoggerOptionsExtensions.cs index c3ab41f770..120c1b2739 100644 --- a/src/OpenTelemetry.Exporter.OneCollector/Logs/OneCollectorOpenTelemetryLoggerOptionsExtensions.cs +++ b/src/OpenTelemetry.Exporter.OneCollector/Logs/OneCollectorOpenTelemetryLoggerOptionsExtensions.cs @@ -25,31 +25,18 @@ namespace OpenTelemetry.Logs; /// public static class OneCollectorOpenTelemetryLoggerOptionsExtensions { - /* - TODO: Enable this once logging supports DI/options binding. /// /// Add OneCollector exporter to the . /// /// . - /// The supplied for call - /// chaining. - public static OpenTelemetryLoggerOptions AddOneCollectorExporter( - this OpenTelemetryLoggerOptions options) - => AddOneCollectorExporter(options, _ => { }); - */ - - /// - /// Add OneCollector exporter to the . - /// - /// . - /// Callback action for configuring . + /// Callback action for configuring . /// The supplied for call /// chaining. public static OpenTelemetryLoggerOptions AddOneCollectorExporter( this OpenTelemetryLoggerOptions options, - Action configure) + Action configure) { Guard.ThrowIfNull(configure); @@ -79,13 +66,14 @@ public static OpenTelemetryLoggerOptions AddOneCollectorExporter( /// /// . /// OneCollector connection string. - /// Callback action for configuring . + /// Callback action for configuring . /// The supplied for call /// chaining. public static OpenTelemetryLoggerOptions AddOneCollectorExporter( this OpenTelemetryLoggerOptions options, string connectionString, - Action configure) + Action configure) { Guard.ThrowIfNullOrWhitespace(connectionString); @@ -96,8 +84,14 @@ public static OpenTelemetryLoggerOptions AddOneCollectorExporter( /// Add OneCollector exporter to the . /// + /// Note: Batch options () are bound to the "BatchOptions" + /// sub-section of the supplied in the + /// parameter. /// . - /// Configuration used to build . + /// Configuration used to build and . /// The supplied for call /// chaining. public static OpenTelemetryLoggerOptions AddOneCollectorExporter( @@ -113,47 +107,47 @@ public static OpenTelemetryLoggerOptions AddOneCollectorExporter( /// Add OneCollector exporter to the . /// + /// /// . - /// Configuration used to build . - /// Callback action for configuring . + /// + /// Callback action for configuring . /// The supplied for call /// chaining. public static OpenTelemetryLoggerOptions AddOneCollectorExporter( this OpenTelemetryLoggerOptions options, IConfiguration configuration, - Action configure) + Action configure) { Guard.ThrowIfNull(configuration); return AddOneCollectorExporter(options, connectionString: null, configuration, configure); } - internal static OpenTelemetryLoggerOptions AddOneCollectorExporter( + private static OpenTelemetryLoggerOptions AddOneCollectorExporter( this OpenTelemetryLoggerOptions options, string? connectionString, IConfiguration? configuration, - Action? configure) + Action? configure) { Guard.ThrowIfNull(options); - var builder = configuration == null - ? new OneCollectorLogExporterBuilder(connectionString) - : new OneCollectorLogExporterBuilder(configuration); + var builder = new OneCollectorLogExportProcessorBuilder(configuration); - configure?.Invoke(builder); - - var exporterOptions = builder.Options; + if (!string.IsNullOrWhiteSpace(connectionString)) + { + builder.SetConnectionString(connectionString!); + } - var batchOptions = exporterOptions.BatchOptions; + configure?.Invoke(builder); #pragma warning disable CA2000 // Dispose objects before losing scope options.AddProcessor( - new BatchLogRecordExportProcessor( - new OneCollectorLogExporter(exporterOptions), - batchOptions.MaxQueueSize, - batchOptions.ScheduledDelayMilliseconds, - batchOptions.ExporterTimeoutMilliseconds, - batchOptions.MaxExportBatchSize)); + builder.BuildProcessor()); #pragma warning restore CA2000 // Dispose objects before losing scope return options; diff --git a/src/OpenTelemetry.Exporter.OneCollector/OneCollectorExporter.cs b/src/OpenTelemetry.Exporter.OneCollector/OneCollectorExporter.cs index 8190c71413..b9c1fff210 100644 --- a/src/OpenTelemetry.Exporter.OneCollector/OneCollectorExporter.cs +++ b/src/OpenTelemetry.Exporter.OneCollector/OneCollectorExporter.cs @@ -24,7 +24,7 @@ namespace OpenTelemetry.Exporter.OneCollector; /// Microsoft OneCollector. /// /// Item type. -public class OneCollectorExporter : BaseExporter +public sealed class OneCollectorExporter : BaseExporter where T : class { private readonly string typeName; @@ -34,13 +34,13 @@ public class OneCollectorExporter : BaseExporter /// /// Initializes a new instance of the class. /// - /// . - internal OneCollectorExporter(ISinkFactory sinkFactory) + /// . + internal OneCollectorExporter(ISink sink) { - Guard.ThrowIfNull(sinkFactory); + Guard.ThrowIfNull(sink); this.typeName = typeof(T).Name; - this.sink = sinkFactory.CreateSink(); + this.sink = sink; } /// @@ -64,6 +64,19 @@ public sealed override ExportResult Export(in Batch batch) } } + /// + /// Register a callback action that will be triggered any time a payload is + /// transmitted by the exporter. + /// + /// . + /// if no transport is tied to the exporter + /// or an representing the registered callback. + /// Call on the returned instance to + /// cancel the registration. + public IDisposable? RegisterPayloadTransmittedCallback(OneCollectorExporterPayloadTransmittedCallbackAction callback) + => this.sink.Transport?.RegisterPayloadTransmittedCallback(callback); + /// protected override void Dispose(bool disposing) { diff --git a/src/OpenTelemetry.Exporter.OneCollector/OneCollectorExporterOptions.cs b/src/OpenTelemetry.Exporter.OneCollector/OneCollectorExporterOptions.cs index 8ea82c4caf..540d9e0e7e 100644 --- a/src/OpenTelemetry.Exporter.OneCollector/OneCollectorExporterOptions.cs +++ b/src/OpenTelemetry.Exporter.OneCollector/OneCollectorExporterOptions.cs @@ -51,6 +51,12 @@ internal OneCollectorExporterOptions() /// internal string? TenantToken { get; private set; } + /// + /// Gets or sets OneCollector serialization format. Default value: . + /// + internal OneCollectorExporterSerializationFormatType SerializationFormat { get; set; } = OneCollectorExporterSerializationFormatType.CommonSchemaV4JsonStream; + internal virtual void Validate() { if (string.IsNullOrWhiteSpace(this.ConnectionString)) diff --git a/src/OpenTelemetry.Exporter.OneCollector/OneCollectorExporterPayloadTransmittedCallbackArguments.cs b/src/OpenTelemetry.Exporter.OneCollector/OneCollectorExporterPayloadTransmittedCallbackArguments.cs new file mode 100644 index 0000000000..2f720c4c5e --- /dev/null +++ b/src/OpenTelemetry.Exporter.OneCollector/OneCollectorExporterPayloadTransmittedCallbackArguments.cs @@ -0,0 +1,93 @@ +// +// Copyright The OpenTelemetry Authors +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// + +using System.Diagnostics; +using OpenTelemetry.Internal; + +namespace OpenTelemetry.Exporter.OneCollector; + +/// +/// Defines a callback delegate for handling payload transmitted events in the +/// class. +/// +/// Arguments. +public delegate void OneCollectorExporterPayloadTransmittedCallbackAction( + in OneCollectorExporterPayloadTransmittedCallbackArguments args); + +/// +/// Contains arguments for the +/// callback delegate. +/// +public readonly ref struct OneCollectorExporterPayloadTransmittedCallbackArguments +{ + private readonly Stream payloadStream; + + internal OneCollectorExporterPayloadTransmittedCallbackArguments( + OneCollectorExporterSerializationFormatType payloadSerializationFormat, + Stream payloadStream, + OneCollectorExporterTransportProtocolType transportProtocol, + Uri transportEndpoint) + { + Debug.Assert(payloadStream != null, "payload stream was null"); + Debug.Assert(payloadStream!.CanSeek, "payload stream was not seekable"); + Debug.Assert(transportEndpoint != null, "transportEndpoint was null"); + + this.PayloadSerializationFormat = payloadSerializationFormat; + this.payloadStream = payloadStream; + this.TransportProtocol = transportProtocol; + this.TransportEndpoint = transportEndpoint!; + } + + /// + /// Gets the payload size in bytes. + /// + public long PayloadSizeInBytes => this.payloadStream!.Length; + + /// + /// Gets the transport endpoint. + /// + public Uri TransportEndpoint { get; } + + /// + /// Gets the payload serialization format. + /// + internal OneCollectorExporterSerializationFormatType PayloadSerializationFormat { get; } + + /// + /// Gets the transport protocol. + /// + internal OneCollectorExporterTransportProtocolType TransportProtocol { get; } + + /// + /// Copy the bytes of the payload to the stream specified by the parameter. + /// + /// Destination . + public void CopyPayloadToStream(Stream destination) + { + Guard.ThrowIfNull(destination); + + var startPosition = this.payloadStream.Position; + try + { + this.payloadStream.CopyTo(destination); + } + finally + { + this.payloadStream.Position = startPosition; + } + } +} diff --git a/src/OpenTelemetry.Exporter.OneCollector/Internal/Sinks/ISinkFactory.cs b/src/OpenTelemetry.Exporter.OneCollector/OneCollectorExporterSerializationFormatType.cs similarity index 62% rename from src/OpenTelemetry.Exporter.OneCollector/Internal/Sinks/ISinkFactory.cs rename to src/OpenTelemetry.Exporter.OneCollector/OneCollectorExporterSerializationFormatType.cs index 46adf69e4f..e9f42365cb 100644 --- a/src/OpenTelemetry.Exporter.OneCollector/Internal/Sinks/ISinkFactory.cs +++ b/src/OpenTelemetry.Exporter.OneCollector/OneCollectorExporterSerializationFormatType.cs @@ -1,4 +1,4 @@ -// +// // Copyright The OpenTelemetry Authors // // Licensed under the Apache License, Version 2.0 (the "License"); @@ -16,8 +16,13 @@ namespace OpenTelemetry.Exporter.OneCollector; -internal interface ISinkFactory - where T : class +/// +/// Describes the OneCollector serialization format to use when writing telemetry. +/// +internal enum OneCollectorExporterSerializationFormatType { - ISink CreateSink(); + /// + /// Common Schema v4.0 UTF-8 JSON stream serialization format. + /// + CommonSchemaV4JsonStream, } diff --git a/src/OpenTelemetry.Exporter.OneCollector/OneCollectorExporterTransportOptions.cs b/src/OpenTelemetry.Exporter.OneCollector/OneCollectorExporterTransportOptions.cs index a65365dbe0..5f1759f3ce 100644 --- a/src/OpenTelemetry.Exporter.OneCollector/OneCollectorExporterTransportOptions.cs +++ b/src/OpenTelemetry.Exporter.OneCollector/OneCollectorExporterTransportOptions.cs @@ -27,8 +27,6 @@ public sealed class OneCollectorExporterTransportOptions internal const int DefaultMaxPayloadSizeInBytes = 1024 * 1024 * 4; internal const int DefaultMaxNumberOfItemsPerPayload = 1500; - internal static readonly Func DefaultHttpClientFactory = () => new HttpClient(); - internal OneCollectorExporterTransportOptions() { } @@ -74,22 +72,6 @@ internal OneCollectorExporterTransportOptions() /// internal OneCollectorExporterHttpTransportCompressionType HttpCompression { get; set; } = OneCollectorExporterHttpTransportCompressionType.Deflate; - /// - /// Gets or sets the factory function called to create the instance that will be used at runtime to transmit - /// telemetry over HTTP. The returned instance will be reused for all export - /// invocations. - /// - /// - /// Notes: - /// - /// The default behavior when using the class is an will be instantiated directly. - /// - /// - internal Func HttpClientFactory { get; set; } = DefaultHttpClientFactory; - internal void Validate() { if (this.Endpoint == null) @@ -97,11 +79,6 @@ internal void Validate() throw new OneCollectorExporterValidationException($"{nameof(this.Endpoint)} was not specified on {this.GetType().Name} options."); } - if (this.HttpClientFactory == null) - { - throw new OneCollectorExporterValidationException($"{nameof(this.HttpClientFactory)} was not specified on {this.GetType().Name} options."); - } - if (this.MaxPayloadSizeInBytes <= 0 && this.MaxPayloadSizeInBytes != -1) { throw new OneCollectorExporterValidationException($"{nameof(this.MaxPayloadSizeInBytes)} was invalid on {this.GetType().Name} options."); diff --git a/test/OpenTelemetry.Exporter.OneCollector.Tests/HttpJsonPostTransportTests.cs b/test/OpenTelemetry.Exporter.OneCollector.Tests/HttpJsonPostTransportTests.cs index 910c5bdd85..140fc7c6a3 100644 --- a/test/OpenTelemetry.Exporter.OneCollector.Tests/HttpJsonPostTransportTests.cs +++ b/test/OpenTelemetry.Exporter.OneCollector.Tests/HttpJsonPostTransportTests.cs @@ -84,6 +84,103 @@ public void RequestUsingDeflateCompressionTest() }); } + [Fact] + public void RegisterPayloadTransmittedCallbackTest() + { + var request = "{\"key1\":\"value1\"}"; + + using var httpClient = new HttpClient(); + + int lastCompletedIteration = -1; + IDisposable? callbackRegistration = null; + bool callbackFired = false; + + /* + * This test runs a few different iterations... + * + * 0) Callback is attached and verified to fire. + * 1) Exisiting callback fires again and is verified. Then we remove the callback. + * 2) Verifies callback is NOT attached and NOT fired. + * 3) Callback is attached again and verified to fire. Then we remove the callback. + */ + + RunHttpServerTest( + request, + requestUri => + { + var transport = new HttpJsonPostTransport( + "instrumentation-key", + requestUri, + OneCollectorExporterHttpTransportCompressionType.None, + httpClient); + + return transport; + }, + (req, body) => + { + AssertStandardHeaders(req); + Assert.True(string.IsNullOrWhiteSpace(req.Headers["Content-Encoding"])); + Assert.Equal(request, Encoding.ASCII.GetString(body.ToArray())); + }, + testStartingAction: (iteration, transport) => + { + switch (iteration) + { + case 0: + case 3: + Assert.Null(callbackRegistration); + callbackRegistration = transport.RegisterPayloadTransmittedCallback(OnPayloadTransmitted); + break; + case 1: + Assert.NotNull(callbackRegistration); + break; + case 2: + Assert.Null(callbackRegistration); + break; + } + }, + testFinishedAction: (iteration, transport) => + { + switch (iteration) + { + case 0: + Assert.NotNull(callbackRegistration); + Assert.True(callbackFired); + break; + case 1: + case 3: + Assert.NotNull(callbackRegistration); + Assert.True(callbackFired); + callbackRegistration.Dispose(); + callbackRegistration = null; + break; + case 2: + Assert.Null(callbackRegistration); + Assert.False(callbackFired); + break; + } + + callbackFired = false; + lastCompletedIteration = iteration; + }, + testIterations: 4); + + Assert.Equal(3, lastCompletedIteration); + + void OnPayloadTransmitted(in OneCollectorExporterPayloadTransmittedCallbackArguments arguments) + { + callbackFired = true; + + using var stream = new MemoryStream(); + arguments.CopyPayloadToStream(stream); + + Assert.Equal(Encoding.ASCII.GetBytes(request), stream.ToArray()); + Assert.Equal(OneCollectorExporterSerializationFormatType.CommonSchemaV4JsonStream, arguments.PayloadSerializationFormat); + Assert.Equal(OneCollectorExporterTransportProtocolType.HttpJsonPost, arguments.TransportProtocol); + Assert.NotNull(arguments.TransportEndpoint); + } + } + private static void AssertStandardHeaders(HttpListenerRequest request) { Assert.Equal("POST", request.HttpMethod); @@ -97,7 +194,11 @@ private static void AssertStandardHeaders(HttpListenerRequest request) private static void RunHttpServerTest( string requestBody, Func createTransportFunc, - Action assertRequestAction) + Action assertRequestAction, + int numberOfItemsInRequestBody = 1, + int testIterations = 1, + Action? testStartingAction = null, + Action? testFinishedAction = null) { bool requestReceivedAndAsserted = false; Exception? testException = null; @@ -138,22 +239,31 @@ private static void RunHttpServerTest( { var requestBodyBytes = Encoding.ASCII.GetBytes(requestBody); - using var requestBodyStream = new MemoryStream(requestBodyBytes); + for (int i = 0; i < testIterations; i++) + { + testStartingAction?.Invoke(i, transport); + + using var requestBodyStream = new MemoryStream(requestBodyBytes); + + var result = transport.Send( + new TransportSendRequest + { + ItemStream = requestBodyStream, + ItemSerializationFormat = OneCollectorExporterSerializationFormatType.CommonSchemaV4JsonStream, + ItemType = "TestRequest", + NumberOfItems = numberOfItemsInRequestBody, + }); - var result = transport.Send( - new TransportSendRequest + if (testException != null) { - ItemStream = requestBodyStream, - ItemType = "TestRequest", - }); + throw testException; + } - if (testException != null) - { - throw testException; - } + Assert.True(result); + Assert.True(requestReceivedAndAsserted); - Assert.True(result); - Assert.True(requestReceivedAndAsserted); + testFinishedAction?.Invoke(i, transport); + } } finally { diff --git a/test/OpenTelemetry.Exporter.OneCollector.Tests/OneCollectorOpenTelemetryLoggerOptionsExtensionsTests.cs b/test/OpenTelemetry.Exporter.OneCollector.Tests/OneCollectorOpenTelemetryLoggerOptionsExtensionsTests.cs index 6f9d4bac94..e157ff08f1 100644 --- a/test/OpenTelemetry.Exporter.OneCollector.Tests/OneCollectorOpenTelemetryLoggerOptionsExtensionsTests.cs +++ b/test/OpenTelemetry.Exporter.OneCollector.Tests/OneCollectorOpenTelemetryLoggerOptionsExtensionsTests.cs @@ -22,6 +22,30 @@ namespace OpenTelemetry.Exporter.OneCollector.Tests; public class OneCollectorOpenTelemetryLoggerOptionsExtensionsTests { + [Fact] + public void ConfigureExporterTest() + { + OneCollectorExporter? exporterInstance = null; + + using var loggerFactory = LoggerFactory.Create(builder => builder + .AddOpenTelemetry(builder => + { + builder.AddOneCollectorExporter( + "InstrumentationKey=token-extrainformation", + configure => configure.ConfigureExporter(exporter => exporterInstance = exporter)); + })); + + Assert.NotNull(exporterInstance); + + using var payloadTransmittedRegistration = exporterInstance.RegisterPayloadTransmittedCallback(OnPayloadTransmitted); + + Assert.NotNull(payloadTransmittedRegistration); + + static void OnPayloadTransmitted(in OneCollectorExporterPayloadTransmittedCallbackArguments args) + { + } + } + [Fact] public void InstrumentationKeyAndTenantTokenValidationTest() { diff --git a/test/OpenTelemetry.Exporter.OneCollector.Tests/WriteDirectlyToTransportSinkTests.cs b/test/OpenTelemetry.Exporter.OneCollector.Tests/WriteDirectlyToTransportSinkTests.cs index f2ac6df9ff..58df6d47df 100644 --- a/test/OpenTelemetry.Exporter.OneCollector.Tests/WriteDirectlyToTransportSinkTests.cs +++ b/test/OpenTelemetry.Exporter.OneCollector.Tests/WriteDirectlyToTransportSinkTests.cs @@ -166,6 +166,11 @@ private sealed class TestTransport : ITransport public List ExportedData { get; } = new(); + public IDisposable RegisterPayloadTransmittedCallback(OneCollectorExporterPayloadTransmittedCallbackAction callback) + { + throw new NotImplementedException(); + } + public bool Send(in TransportSendRequest sendRequest) { var stream = new MemoryStream();