diff --git a/docs-builder.sln.DotSettings b/docs-builder.sln.DotSettings
index 571a4f3ad..7d809a9c7 100644
--- a/docs-builder.sln.DotSettings
+++ b/docs-builder.sln.DotSettings
@@ -4,4 +4,5 @@
True
True
True
+ True
True
\ No newline at end of file
diff --git a/src/Elastic.Documentation.ServiceDefaults/Extensions.cs b/src/Elastic.Documentation.ServiceDefaults/Extensions.cs
index 63d479679..eaa86b9d0 100644
--- a/src/Elastic.Documentation.ServiceDefaults/Extensions.cs
+++ b/src/Elastic.Documentation.ServiceDefaults/Extensions.cs
@@ -37,6 +37,11 @@ public static TBuilder AddServiceDefaults(this TBuilder builder) where
public static TBuilder AddOpenTelemetryDefaults(this TBuilder builder) where TBuilder : IHostApplicationBuilder
{
+
+ var useOtlpExporter = !string.IsNullOrWhiteSpace(builder.Configuration["OTEL_EXPORTER_OTLP_ENDPOINT"]);
+ if (!useOtlpExporter)
+ return builder;
+
_ = builder.Logging.AddOpenTelemetry(logging =>
{
logging.IncludeFormattedMessage = true;
@@ -86,14 +91,6 @@ private static TBuilder AddOpenTelemetryExporters(this TBuilder builde
_ = builder.Services.AddOpenTelemetry().UseOtlpExporter();
}
-
- // Uncomment the following lines to enable the Azure Monitor exporter (requires the Azure.Monitor.OpenTelemetry.AspNetCore package)
- //if (!string.IsNullOrEmpty(builder.Configuration["APPLICATIONINSIGHTS_CONNECTION_STRING"]))
- //{
- // builder.Services.AddOpenTelemetry()
- // .UseAzureMonitor();
- //}
-
return builder;
}
diff --git a/src/api/Elastic.Documentation.Api.Infrastructure/MappingsExtensions.cs b/src/api/Elastic.Documentation.Api.Infrastructure/MappingsExtensions.cs
index 7a69179cb..ef756d7c8 100644
--- a/src/api/Elastic.Documentation.Api.Infrastructure/MappingsExtensions.cs
+++ b/src/api/Elastic.Documentation.Api.Infrastructure/MappingsExtensions.cs
@@ -14,13 +14,15 @@ namespace Elastic.Documentation.Api.Infrastructure;
public static class MappingsExtension
{
- public static void MapElasticDocsApiEndpoints(this IEndpointRouteBuilder group)
+ public static void MapElasticDocsApiEndpoints(this IEndpointRouteBuilder group, bool mapOtlpEndpoints = true)
{
+
_ = group.MapGet("/", () => Results.Empty);
_ = group.MapPost("/", () => Results.Empty);
MapAskAiEndpoint(group);
MapNavigationSearch(group);
- MapOtlpProxyEndpoint(group);
+ if (mapOtlpEndpoints)
+ MapOtlpProxyEndpoint(group);
}
private static void MapAskAiEndpoint(IEndpointRouteBuilder group)
diff --git a/src/api/Elastic.Documentation.Api.Infrastructure/OpenTelemetry/OpenTelemetryExtensions.cs b/src/api/Elastic.Documentation.Api.Infrastructure/OpenTelemetry/OpenTelemetryExtensions.cs
index b7a1cf168..0a839781d 100644
--- a/src/api/Elastic.Documentation.Api.Infrastructure/OpenTelemetry/OpenTelemetryExtensions.cs
+++ b/src/api/Elastic.Documentation.Api.Infrastructure/OpenTelemetry/OpenTelemetryExtensions.cs
@@ -71,10 +71,13 @@ public static TracerProviderBuilder AddDocsApiTracing(this TracerProviderBuilder
///
/// The web application builder
/// The builder for chaining
- public static TBuilder AddDocsApiOpenTelemetry(
- this TBuilder builder)
+ public static TBuilder AddDocsApiOpenTelemetry(this TBuilder builder)
where TBuilder : IHostApplicationBuilder
{
+ var useOtlpExporter = !string.IsNullOrWhiteSpace(builder.Configuration["OTEL_EXPORTER_OTLP_ENDPOINT"]);
+ if (!useOtlpExporter)
+ return builder;
+
var options = new ElasticOpenTelemetryOptions
{
// In AOT mode, assembly scanning is not supported, so we skip it
diff --git a/src/api/Elastic.Documentation.Api.Lambda/Program.cs b/src/api/Elastic.Documentation.Api.Lambda/Program.cs
index a31227d91..abd16dff2 100644
--- a/src/api/Elastic.Documentation.Api.Lambda/Program.cs
+++ b/src/api/Elastic.Documentation.Api.Lambda/Program.cs
@@ -49,7 +49,9 @@
_ = app.UseDeveloperExceptionPage();
var v1 = app.MapGroup("/docs/_api/v1");
- v1.MapElasticDocsApiEndpoints();
+
+ var mapOtlpEndpoints = !string.IsNullOrWhiteSpace(builder.Configuration["OTEL_EXPORTER_OTLP_ENDPOINT"]);
+ v1.MapElasticDocsApiEndpoints(mapOtlpEndpoints);
Console.WriteLine("API endpoints mapped");
Console.WriteLine("Application startup completed successfully");
diff --git a/src/tooling/docs-builder/Http/DocumentationWebHost.cs b/src/tooling/docs-builder/Http/DocumentationWebHost.cs
index 3c8442fba..381c6f584 100644
--- a/src/tooling/docs-builder/Http/DocumentationWebHost.cs
+++ b/src/tooling/docs-builder/Http/DocumentationWebHost.cs
@@ -142,7 +142,8 @@ private void SetUpRoutes()
var apiV1 = _webApplication.MapGroup("/docs/_api/v1");
#if DEBUG
- apiV1.MapElasticDocsApiEndpoints();
+ var mapOtlpEndpoints = !string.IsNullOrWhiteSpace(_webApplication.Configuration["OTEL_EXPORTER_OTLP_ENDPOINT"]);
+ apiV1.MapElasticDocsApiEndpoints(mapOtlpEndpoints);
#endif
_ = _webApplication.MapGet("{**slug}", (string slug, ReloadableGeneratorState holder, Cancel ctx) =>
diff --git a/src/tooling/docs-builder/Http/StaticWebHost.cs b/src/tooling/docs-builder/Http/StaticWebHost.cs
index 131ce3271..f1e85072d 100644
--- a/src/tooling/docs-builder/Http/StaticWebHost.cs
+++ b/src/tooling/docs-builder/Http/StaticWebHost.cs
@@ -85,7 +85,8 @@ private void SetUpRoutes()
var apiV1 = WebApplication.MapGroup("/docs/_api/v1");
#if DEBUG
- apiV1.MapElasticDocsApiEndpoints();
+ var mapOtlpEndpoints = !string.IsNullOrWhiteSpace(WebApplication.Configuration["OTEL_EXPORTER_OTLP_ENDPOINT"]);
+ apiV1.MapElasticDocsApiEndpoints(mapOtlpEndpoints);
#endif
}
diff --git a/tests-integration/Elastic.Documentation.Api.IntegrationTests/EuidEnrichmentIntegrationTests.cs b/tests-integration/Elastic.Documentation.Api.IntegrationTests/EuidEnrichmentIntegrationTests.cs
index df7c446dc..3dfd28bd3 100644
--- a/tests-integration/Elastic.Documentation.Api.IntegrationTests/EuidEnrichmentIntegrationTests.cs
+++ b/tests-integration/Elastic.Documentation.Api.IntegrationTests/EuidEnrichmentIntegrationTests.cs
@@ -17,8 +17,23 @@ namespace Elastic.Documentation.Api.IntegrationTests;
/// Integration tests for euid cookie enrichment in OpenTelemetry traces and logging.
/// Uses WebApplicationFactory to test the real API configuration with mocked AskAi services.
///
-public class EuidEnrichmentIntegrationTests
+public class EuidEnrichmentIntegrationTests : IAsyncLifetime
{
+ private const string OtlpEndpoint = "http://localhost:4318";
+
+ public ValueTask InitializeAsync()
+ {
+ Environment.SetEnvironmentVariable("OTEL_EXPORTER_OTLP_ENDPOINT", OtlpEndpoint);
+ return ValueTask.CompletedTask;
+ }
+
+ public ValueTask DisposeAsync()
+ {
+ GC.SuppressFinalize(this);
+ Environment.SetEnvironmentVariable("OTEL_EXPORTER_OTLP_ENDPOINT", null);
+ return ValueTask.CompletedTask;
+ }
+
///
/// Test that verifies euid cookie is added to both HTTP span and custom AskAi span,
/// and appears in log entries - using the real API configuration.
diff --git a/tests-integration/Elastic.Documentation.Api.IntegrationTests/OtlpProxyIntegrationTests.cs b/tests-integration/Elastic.Documentation.Api.IntegrationTests/OtlpProxyIntegrationTests.cs
index f8fbd177d..7f32fcaf8 100644
--- a/tests-integration/Elastic.Documentation.Api.IntegrationTests/OtlpProxyIntegrationTests.cs
+++ b/tests-integration/Elastic.Documentation.Api.IntegrationTests/OtlpProxyIntegrationTests.cs
@@ -13,8 +13,23 @@
namespace Elastic.Documentation.Api.IntegrationTests;
-public class OtlpProxyIntegrationTests
+public class OtlpProxyIntegrationTests : IAsyncLifetime
{
+ private const string OtlpEndpoint = "http://localhost:4318";
+
+ public ValueTask InitializeAsync()
+ {
+ Environment.SetEnvironmentVariable("OTEL_EXPORTER_OTLP_ENDPOINT", OtlpEndpoint);
+ return ValueTask.CompletedTask;
+ }
+
+ public ValueTask DisposeAsync()
+ {
+ GC.SuppressFinalize(this);
+ Environment.SetEnvironmentVariable("OTEL_EXPORTER_OTLP_ENDPOINT", null);
+ return ValueTask.CompletedTask;
+ }
+
[Fact]
public async Task OtlpProxyTracesEndpointForwardsToCorrectUrl()
{
@@ -71,7 +86,7 @@ public async Task OtlpProxyTracesEndpointForwardsToCorrectUrl()
response.StatusCode.Should().Be(HttpStatusCode.NoContent);
capturedRequest.Should().NotBeNull();
capturedRequest!.RequestUri.Should().NotBeNull();
- capturedRequest.RequestUri!.ToString().Should().Be("http://localhost:4318/v1/traces");
+ capturedRequest.RequestUri!.ToString().Should().Be($"{OtlpEndpoint}/v1/traces");
capturedRequest.Method.Should().Be(HttpMethod.Post);
capturedRequest.Content.Should().NotBeNull();
capturedRequest.Content!.Headers.ContentType!.MediaType.Should().Be("application/json");
@@ -131,7 +146,7 @@ public async Task OtlpProxyLogsEndpointForwardsToCorrectUrl()
// Assert - verify the enum ToStringFast() generates "logs" (lowercase)
response.StatusCode.Should().Be(HttpStatusCode.NoContent);
capturedRequest.Should().NotBeNull();
- capturedRequest!.RequestUri!.ToString().Should().Be("http://localhost:4318/v1/logs");
+ capturedRequest!.RequestUri!.ToString().Should().Be($"{OtlpEndpoint}/v1/logs");
// Cleanup mock response
mockResponse.Dispose();
@@ -184,7 +199,7 @@ public async Task OtlpProxyMetricsEndpointForwardsToCorrectUrl()
// Assert - verify the enum ToStringFast() generates "metrics" (lowercase)
response.StatusCode.Should().Be(HttpStatusCode.NoContent);
capturedRequest.Should().NotBeNull();
- capturedRequest!.RequestUri!.ToString().Should().Be("http://localhost:4318/v1/metrics");
+ capturedRequest!.RequestUri!.ToString().Should().Be($"{OtlpEndpoint}/v1/metrics");
// Cleanup mock response
mockResponse.Dispose();