Skip to content

Commit

Permalink
Http server builder (#11651)
Browse files Browse the repository at this point in the history
  • Loading branch information
zeitlinger authored Oct 7, 2024
1 parent d1ba858 commit b9f09ca
Show file tree
Hide file tree
Showing 45 changed files with 502 additions and 889 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,7 @@
import io.opentelemetry.instrumentation.api.semconv.http.HttpSpanStatusExtractor;
import java.util.ArrayList;
import java.util.List;
import java.util.Objects;
import java.util.Set;
import java.util.function.Consumer;
import java.util.function.Function;
Expand Down Expand Up @@ -58,21 +59,43 @@ public final class DefaultHttpClientInstrumenterBuilder<REQUEST, RESPONSE> {
private final HttpClientAttributesGetter<REQUEST, RESPONSE> attributesGetter;
private final HttpSpanNameExtractorBuilder<REQUEST> httpSpanNameExtractorBuilder;

@Nullable private TextMapSetter<REQUEST> headerSetter;
@Nullable private final TextMapSetter<REQUEST> headerSetter;
private Function<SpanNameExtractor<? super REQUEST>, ? extends SpanNameExtractor<? super REQUEST>>
spanNameExtractorTransformer = Function.identity();
private boolean emitExperimentalHttpClientMetrics = false;
private Consumer<InstrumenterBuilder<REQUEST, RESPONSE>> builderCustomizer = b -> {};

public DefaultHttpClientInstrumenterBuilder(
private DefaultHttpClientInstrumenterBuilder(
String instrumentationName,
OpenTelemetry openTelemetry,
HttpClientAttributesGetter<REQUEST, RESPONSE> attributesGetter) {
this.instrumentationName = instrumentationName;
this.openTelemetry = openTelemetry;
HttpClientAttributesGetter<REQUEST, RESPONSE> attributesGetter,
TextMapSetter<REQUEST> headerSetter) {
this.instrumentationName = Objects.requireNonNull(instrumentationName, "instrumentationName");
this.openTelemetry = Objects.requireNonNull(openTelemetry, "openTelemetry");
this.attributesGetter = Objects.requireNonNull(attributesGetter, "attributesGetter");
httpSpanNameExtractorBuilder = HttpSpanNameExtractor.builder(attributesGetter);
httpAttributesExtractorBuilder = HttpClientAttributesExtractor.builder(attributesGetter);
this.attributesGetter = attributesGetter;
this.headerSetter = headerSetter;
}

public static <REQUEST, RESPONSE> DefaultHttpClientInstrumenterBuilder<REQUEST, RESPONSE> create(
String instrumentationName,
OpenTelemetry openTelemetry,
HttpClientAttributesGetter<REQUEST, RESPONSE> attributesGetter) {
return new DefaultHttpClientInstrumenterBuilder<REQUEST, RESPONSE>(
instrumentationName, openTelemetry, attributesGetter, null);
}

public static <REQUEST, RESPONSE> DefaultHttpClientInstrumenterBuilder<REQUEST, RESPONSE> create(
String instrumentationName,
OpenTelemetry openTelemetry,
HttpClientAttributesGetter<REQUEST, RESPONSE> attributesGetter,
TextMapSetter<REQUEST> headerSetter) {
return new DefaultHttpClientInstrumenterBuilder<REQUEST, RESPONSE>(
instrumentationName,
openTelemetry,
attributesGetter,
Objects.requireNonNull(headerSetter, "headerSetter"));
}

/**
Expand Down Expand Up @@ -141,13 +164,6 @@ public DefaultHttpClientInstrumenterBuilder<REQUEST, RESPONSE> setKnownMethods(
return this;
}

@CanIgnoreReturnValue
public DefaultHttpClientInstrumenterBuilder<REQUEST, RESPONSE> setHeaderSetter(
@Nullable TextMapSetter<REQUEST> headerSetter) {
this.headerSetter = headerSetter;
return this;
}

/**
* Configures the instrumentation to emit experimental HTTP client metrics.
*
Expand Down Expand Up @@ -193,7 +209,6 @@ public DefaultHttpClientInstrumenterBuilder<REQUEST, RESPONSE> setBuilderCustomi
}

public Instrumenter<REQUEST, RESPONSE> build() {

SpanNameExtractor<? super REQUEST> spanNameExtractor =
spanNameExtractorTransformer.apply(httpSpanNameExtractorBuilder.build());

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,7 @@
import io.opentelemetry.instrumentation.api.semconv.http.HttpSpanStatusExtractor;
import java.util.ArrayList;
import java.util.List;
import java.util.Objects;
import java.util.Set;
import java.util.function.Consumer;
import java.util.function.Function;
Expand Down Expand Up @@ -61,20 +62,40 @@ public final class DefaultHttpServerInstrumenterBuilder<REQUEST, RESPONSE> {
private boolean emitExperimentalHttpServerMetrics = false;
private Consumer<InstrumenterBuilder<REQUEST, RESPONSE>> builderCustomizer = b -> {};

public DefaultHttpServerInstrumenterBuilder(
private DefaultHttpServerInstrumenterBuilder(
String instrumentationName,
OpenTelemetry openTelemetry,
HttpServerAttributesGetter<REQUEST, RESPONSE> attributesGetter,
@Nullable TextMapGetter<REQUEST> headerGetter) {
this.instrumentationName = instrumentationName;
this.openTelemetry = openTelemetry;
TextMapGetter<REQUEST> headerGetter) {
this.instrumentationName = Objects.requireNonNull(instrumentationName, "instrumentationName");
this.openTelemetry = Objects.requireNonNull(openTelemetry, "openTelemetry");
this.attributesGetter = Objects.requireNonNull(attributesGetter, "attributesGetter");
httpAttributesExtractorBuilder = HttpServerAttributesExtractor.builder(attributesGetter);
httpSpanNameExtractorBuilder = HttpSpanNameExtractor.builder(attributesGetter);
httpServerRouteBuilder = HttpServerRoute.builder(attributesGetter);
this.attributesGetter = attributesGetter;
this.headerGetter = headerGetter;
}

public static <REQUEST, RESPONSE> DefaultHttpServerInstrumenterBuilder<REQUEST, RESPONSE> create(
String instrumentationName,
OpenTelemetry openTelemetry,
HttpServerAttributesGetter<REQUEST, RESPONSE> attributesGetter) {
return new DefaultHttpServerInstrumenterBuilder<>(
instrumentationName, openTelemetry, attributesGetter, null);
}

public static <REQUEST, RESPONSE> DefaultHttpServerInstrumenterBuilder<REQUEST, RESPONSE> create(
String instrumentationName,
OpenTelemetry openTelemetry,
HttpServerAttributesGetter<REQUEST, RESPONSE> attributesGetter,
TextMapGetter<REQUEST> headerGetter) {
return new DefaultHttpServerInstrumenterBuilder<>(
instrumentationName,
openTelemetry,
attributesGetter,
Objects.requireNonNull(headerGetter, "headerGetter"));
}

/**
* Adds an additional {@link AttributesExtractor} to invoke to set attributes to instrumented
* items.
Expand Down Expand Up @@ -172,6 +193,15 @@ public DefaultHttpServerInstrumenterBuilder<REQUEST, RESPONSE> setBuilderCustomi
}

public Instrumenter<REQUEST, RESPONSE> build() {
InstrumenterBuilder<REQUEST, RESPONSE> builder = instrumenterBuilder();

if (headerGetter != null) {
return builder.buildServerInstrumenter(headerGetter);
}
return builder.buildInstrumenter(SpanKindExtractor.alwaysServer());
}

public InstrumenterBuilder<REQUEST, RESPONSE> instrumenterBuilder() {
SpanNameExtractor<? super REQUEST> spanNameExtractor =
spanNameExtractorTransformer.apply(httpSpanNameExtractorBuilder.build());

Expand All @@ -190,11 +220,7 @@ public Instrumenter<REQUEST, RESPONSE> build() {
.addOperationMetrics(HttpServerExperimentalMetrics.get());
}
builderCustomizer.accept(builder);

if (headerGetter != null) {
return builder.buildServerInstrumenter(headerGetter);
}
return builder.buildInstrumenter(SpanKindExtractor.alwaysServer());
return builder;
}

@CanIgnoreReturnValue
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -7,50 +7,20 @@

import akka.http.scaladsl.model.HttpRequest;
import akka.http.scaladsl.model.HttpResponse;
import io.opentelemetry.api.GlobalOpenTelemetry;
import io.opentelemetry.instrumentation.api.incubator.semconv.http.HttpExperimentalAttributesExtractor;
import io.opentelemetry.instrumentation.api.incubator.semconv.http.HttpServerExperimentalMetrics;
import io.opentelemetry.instrumentation.api.instrumenter.Instrumenter;
import io.opentelemetry.instrumentation.api.instrumenter.InstrumenterBuilder;
import io.opentelemetry.instrumentation.api.semconv.http.HttpServerAttributesExtractor;
import io.opentelemetry.instrumentation.api.semconv.http.HttpServerMetrics;
import io.opentelemetry.instrumentation.api.semconv.http.HttpServerRoute;
import io.opentelemetry.instrumentation.api.semconv.http.HttpSpanNameExtractor;
import io.opentelemetry.instrumentation.api.semconv.http.HttpSpanStatusExtractor;
import io.opentelemetry.javaagent.bootstrap.internal.AgentCommonConfig;
import io.opentelemetry.javaagent.bootstrap.internal.JavaagentHttpServerInstrumenters;
import io.opentelemetry.javaagent.instrumentation.akkahttp.AkkaHttpUtil;

public final class AkkaHttpServerSingletons {

private static final Instrumenter<HttpRequest, HttpResponse> INSTRUMENTER;

static {
AkkaHttpServerAttributesGetter httpAttributesGetter = new AkkaHttpServerAttributesGetter();
InstrumenterBuilder<HttpRequest, HttpResponse> builder =
Instrumenter.<HttpRequest, HttpResponse>builder(
GlobalOpenTelemetry.get(),
AkkaHttpUtil.instrumentationName(),
HttpSpanNameExtractor.builder(httpAttributesGetter)
.setKnownMethods(AgentCommonConfig.get().getKnownHttpRequestMethods())
.build())
.setSpanStatusExtractor(HttpSpanStatusExtractor.create(httpAttributesGetter))
.addAttributesExtractor(
HttpServerAttributesExtractor.builder(httpAttributesGetter)
.setCapturedRequestHeaders(AgentCommonConfig.get().getServerRequestHeaders())
.setCapturedResponseHeaders(AgentCommonConfig.get().getServerResponseHeaders())
.setKnownMethods(AgentCommonConfig.get().getKnownHttpRequestMethods())
.build())
.addOperationMetrics(HttpServerMetrics.get())
.addContextCustomizer(
HttpServerRoute.builder(httpAttributesGetter)
.setKnownMethods(AgentCommonConfig.get().getKnownHttpRequestMethods())
.build());
if (AgentCommonConfig.get().shouldEmitExperimentalHttpServerTelemetry()) {
builder
.addAttributesExtractor(HttpExperimentalAttributesExtractor.create(httpAttributesGetter))
.addOperationMetrics(HttpServerExperimentalMetrics.get());
}
INSTRUMENTER = builder.buildServerInstrumenter(AkkaHttpServerHeaders.INSTANCE);
INSTRUMENTER =
JavaagentHttpServerInstrumenters.create(
AkkaHttpUtil.instrumentationName(),
new AkkaHttpServerAttributesGetter(),
AkkaHttpServerHeaders.INSTANCE);
}

public static Instrumenter<HttpRequest, HttpResponse> instrumenter() {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,7 @@ public final class ApacheHttpClientTelemetryBuilder {

ApacheHttpClientTelemetryBuilder(OpenTelemetry openTelemetry) {
builder =
new DefaultHttpClientInstrumenterBuilder<>(
DefaultHttpClientInstrumenterBuilder.create(
INSTRUMENTATION_NAME, openTelemetry, ApacheHttpClientHttpAttributesGetter.INSTANCE);
this.openTelemetry = openTelemetry;
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,7 @@ public final class ApacheHttpClient5TelemetryBuilder {

ApacheHttpClient5TelemetryBuilder(OpenTelemetry openTelemetry) {
builder =
new DefaultHttpClientInstrumenterBuilder<>(
DefaultHttpClientInstrumenterBuilder.create(
INSTRUMENTATION_NAME, openTelemetry, ApacheHttpClient5HttpAttributesGetter.INSTANCE);
this.openTelemetry = openTelemetry;
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ private ArmeriaInstrumenterBuilderFactory() {}

public static DefaultHttpServerInstrumenterBuilder<ServiceRequestContext, RequestLog>
getServerBuilder(OpenTelemetry openTelemetry) {
return new DefaultHttpServerInstrumenterBuilder<>(
return DefaultHttpServerInstrumenterBuilder.create(
INSTRUMENTATION_NAME,
openTelemetry,
ArmeriaHttpServerAttributesGetter.INSTANCE,
Expand All @@ -32,8 +32,10 @@ private ArmeriaInstrumenterBuilderFactory() {}

public static DefaultHttpClientInstrumenterBuilder<ClientRequestContext, RequestLog>
getClientBuilder(OpenTelemetry openTelemetry) {
return new DefaultHttpClientInstrumenterBuilder<>(
INSTRUMENTATION_NAME, openTelemetry, ArmeriaHttpClientAttributesGetter.INSTANCE)
.setHeaderSetter(ClientRequestContextSetter.INSTANCE);
return DefaultHttpClientInstrumenterBuilder.create(
INSTRUMENTATION_NAME,
openTelemetry,
ArmeriaHttpClientAttributesGetter.INSTANCE,
ClientRequestContextSetter.INSTANCE);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -5,17 +5,8 @@

package io.opentelemetry.javaagent.instrumentation.grizzly;

import io.opentelemetry.api.GlobalOpenTelemetry;
import io.opentelemetry.instrumentation.api.incubator.semconv.http.HttpExperimentalAttributesExtractor;
import io.opentelemetry.instrumentation.api.incubator.semconv.http.HttpServerExperimentalMetrics;
import io.opentelemetry.instrumentation.api.instrumenter.Instrumenter;
import io.opentelemetry.instrumentation.api.instrumenter.InstrumenterBuilder;
import io.opentelemetry.instrumentation.api.semconv.http.HttpServerAttributesExtractor;
import io.opentelemetry.instrumentation.api.semconv.http.HttpServerMetrics;
import io.opentelemetry.instrumentation.api.semconv.http.HttpServerRoute;
import io.opentelemetry.instrumentation.api.semconv.http.HttpSpanNameExtractor;
import io.opentelemetry.instrumentation.api.semconv.http.HttpSpanStatusExtractor;
import io.opentelemetry.javaagent.bootstrap.internal.AgentCommonConfig;
import io.opentelemetry.javaagent.bootstrap.internal.JavaagentHttpServerInstrumenters;
import io.opentelemetry.javaagent.bootstrap.servlet.AppServerBridge;
import org.glassfish.grizzly.http.HttpRequestPacket;
import org.glassfish.grizzly.http.HttpResponsePacket;
Expand All @@ -25,43 +16,22 @@ public final class GrizzlySingletons {
private static final Instrumenter<HttpRequestPacket, HttpResponsePacket> INSTRUMENTER;

static {
GrizzlyHttpAttributesGetter httpAttributesGetter = new GrizzlyHttpAttributesGetter();

InstrumenterBuilder<HttpRequestPacket, HttpResponsePacket> builder =
Instrumenter.<HttpRequestPacket, HttpResponsePacket>builder(
GlobalOpenTelemetry.get(),
"io.opentelemetry.grizzly-2.3",
HttpSpanNameExtractor.builder(httpAttributesGetter)
.setKnownMethods(AgentCommonConfig.get().getKnownHttpRequestMethods())
.build())
.setSpanStatusExtractor(HttpSpanStatusExtractor.create(httpAttributesGetter))
.addAttributesExtractor(
HttpServerAttributesExtractor.builder(httpAttributesGetter)
.setCapturedRequestHeaders(AgentCommonConfig.get().getServerRequestHeaders())
.setCapturedResponseHeaders(AgentCommonConfig.get().getServerResponseHeaders())
.setKnownMethods(AgentCommonConfig.get().getKnownHttpRequestMethods())
.build())
.addOperationMetrics(HttpServerMetrics.get());
if (AgentCommonConfig.get().shouldEmitExperimentalHttpServerTelemetry()) {
builder
.addAttributesExtractor(HttpExperimentalAttributesExtractor.create(httpAttributesGetter))
.addOperationMetrics(HttpServerExperimentalMetrics.get());
}
INSTRUMENTER =
builder
.addContextCustomizer(
(context, request, attributes) ->
new AppServerBridge.Builder()
.captureServletAttributes()
.recordException()
.init(context))
.addContextCustomizer(
(context, httpRequestPacket, startAttributes) -> GrizzlyErrorHolder.init(context))
.addContextCustomizer(
HttpServerRoute.builder(httpAttributesGetter)
.setKnownMethods(AgentCommonConfig.get().getKnownHttpRequestMethods())
.build())
.buildServerInstrumenter(HttpRequestHeadersGetter.INSTANCE);
JavaagentHttpServerInstrumenters.create(
"io.opentelemetry.grizzly-2.3",
new GrizzlyHttpAttributesGetter(),
HttpRequestHeadersGetter.INSTANCE,
builder ->
builder
.addContextCustomizer(
(context, request, attributes) ->
new AppServerBridge.Builder()
.captureServletAttributes()
.recordException()
.init(context))
.addContextCustomizer(
(context, httpRequestPacket, startAttributes) ->
GrizzlyErrorHolder.init(context)));
}

public static Instrumenter<HttpRequestPacket, HttpResponsePacket> instrumenter() {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ private JavaHttpClientInstrumenterBuilderFactory() {}

public static DefaultHttpClientInstrumenterBuilder<HttpRequest, HttpResponse<?>> create(
OpenTelemetry openTelemetry) {
return new DefaultHttpClientInstrumenterBuilder<>(
return DefaultHttpClientInstrumenterBuilder.create(
INSTRUMENTATION_NAME, openTelemetry, JavaHttpClientAttributesGetter.INSTANCE);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -21,8 +21,10 @@ private JettyHttpClientInstrumenterBuilderFactory() {}

public static DefaultHttpClientInstrumenterBuilder<Request, Response> create(
OpenTelemetry openTelemetry) {
return new DefaultHttpClientInstrumenterBuilder<>(
INSTRUMENTATION_NAME, openTelemetry, JettyClientHttpAttributesGetter.INSTANCE)
.setHeaderSetter(HttpHeaderSetter.INSTANCE);
return DefaultHttpClientInstrumenterBuilder.create(
INSTRUMENTATION_NAME,
openTelemetry,
JettyClientHttpAttributesGetter.INSTANCE,
HttpHeaderSetter.INSTANCE);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -21,8 +21,10 @@ private JettyHttpClientInstrumenterBuilderFactory() {}

public static DefaultHttpClientInstrumenterBuilder<Request, Response> create(
OpenTelemetry openTelemetry) {
return new DefaultHttpClientInstrumenterBuilder<>(
INSTRUMENTATION_NAME, openTelemetry, JettyClientHttpAttributesGetter.INSTANCE)
.setHeaderSetter(HttpHeaderSetter.INSTANCE);
return DefaultHttpClientInstrumenterBuilder.create(
INSTRUMENTATION_NAME,
openTelemetry,
JettyClientHttpAttributesGetter.INSTANCE,
HttpHeaderSetter.INSTANCE);
}
}
Loading

0 comments on commit b9f09ca

Please sign in to comment.