From 4cdcb05acd79d4fb971e148a58964ebadbeb91e0 Mon Sep 17 00:00:00 2001 From: Stuart McCulloch Date: Tue, 28 May 2024 14:29:36 +0100 Subject: [PATCH] Move the OpenTelemetry shim to its own module so we can re-use it for drop-in support (#7072) * Move the OpenTelemetry shim to its own module so we can re-use it for drop-in support. We now embed a shaded copy of the OpenTelemetry API which has been pre-instrumented at build time with our shim. This shaded API will be on the bootstrap class-path so it can be used by drop-in advice without having to continually inject it everywhere the drop-in advice is injected. The same shim is used at runtime when instrumenting use of the OpenTelemetry API on the application class-path. * Ensure shared plugin class-loader is rebuilt when processing different instrument setups --- .../src/main/groovy/InstrumentPlugin.groovy | 15 +- .../agent-otel/otel-bootstrap/build.gradle | 66 +++++++++ .../src/main/java/package-info.java | 1 + .../agent-otel/otel-shim/build.gradle | 11 ++ .../shim}/context/OtelContext.java | 39 +++++- .../shim}/context/OtelScope.java | 2 +- .../propagation/AgentTextMapPropagator.java | 10 +- .../propagation/OtelContextPropagators.java | 2 +- .../context/propagation/TraceStateHelper.java | 2 +- .../shim}/trace/OtelConventions.java | 2 +- .../shim}/trace/OtelExtractedContext.java | 2 +- .../opentelemetry/shim}/trace/OtelSpan.java | 6 +- .../shim}/trace/OtelSpanBuilder.java | 10 +- .../shim}/trace/OtelSpanContext.java | 2 +- .../shim}/trace/OtelSpanLink.java | 4 +- .../opentelemetry/shim}/trace/OtelTracer.java | 4 +- .../shim}/trace/OtelTracerBuilder.java | 2 +- .../shim}/trace/OtelTracerProvider.java | 2 +- .../agent-otel/otel-tooling/build.gradle | 9 ++ .../tooling/OtelShimGradlePlugin.java | 43 ++++++ .../tooling/OtelShimInjector.java | 130 ++++++++++++++++++ dd-java-agent/build.gradle | 1 + .../opentelemetry-1.4/build.gradle | 2 + .../OpenTelemetryInstrumentation.java | 47 +++---- .../OpenTelemetryContextInstrumentation.java | 36 ++--- ...elemetryContextStorageInstrumentation.java | 72 +++------- .../OpenTelemetry14ConventionsTest.groovy | 6 +- .../test/groovy/OpenTelemetry14Test.groovy | 2 +- .../context/ContextTest.groovy | 6 +- settings.gradle | 6 +- 30 files changed, 407 insertions(+), 135 deletions(-) create mode 100644 dd-java-agent/agent-otel/otel-bootstrap/build.gradle create mode 100644 dd-java-agent/agent-otel/otel-bootstrap/src/main/java/package-info.java create mode 100644 dd-java-agent/agent-otel/otel-shim/build.gradle rename dd-java-agent/{instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14 => agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim}/context/OtelContext.java (59%) rename dd-java-agent/{instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14 => agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim}/context/OtelScope.java (90%) rename dd-java-agent/{instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14 => agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim}/context/propagation/AgentTextMapPropagator.java (90%) rename dd-java-agent/{instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14 => agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim}/context/propagation/OtelContextPropagators.java (85%) rename dd-java-agent/{instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14 => agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim}/context/propagation/TraceStateHelper.java (96%) rename dd-java-agent/{instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14 => agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim}/trace/OtelConventions.java (99%) rename dd-java-agent/{instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14 => agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim}/trace/OtelExtractedContext.java (97%) rename dd-java-agent/{instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14 => agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim}/trace/OtelSpan.java (95%) rename dd-java-agent/{instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14 => agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim}/trace/OtelSpanBuilder.java (91%) rename dd-java-agent/{instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14 => agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim}/trace/OtelSpanContext.java (97%) rename dd-java-agent/{instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14 => agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim}/trace/OtelSpanLink.java (93%) rename dd-java-agent/{instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14 => agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim}/trace/OtelTracer.java (83%) rename dd-java-agent/{instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14 => agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim}/trace/OtelTracerBuilder.java (92%) rename dd-java-agent/{instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14 => agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim}/trace/OtelTracerProvider.java (96%) create mode 100644 dd-java-agent/agent-otel/otel-tooling/build.gradle create mode 100644 dd-java-agent/agent-otel/otel-tooling/src/main/java/datadog/opentelemetry/tooling/OtelShimGradlePlugin.java create mode 100644 dd-java-agent/agent-otel/otel-tooling/src/main/java/datadog/opentelemetry/tooling/OtelShimInjector.java diff --git a/buildSrc/src/main/groovy/InstrumentPlugin.groovy b/buildSrc/src/main/groovy/InstrumentPlugin.groovy index 7f301e26f8e..f7f18e467d6 100644 --- a/buildSrc/src/main/groovy/InstrumentPlugin.groovy +++ b/buildSrc/src/main/groovy/InstrumentPlugin.groovy @@ -178,17 +178,20 @@ interface InstrumentWorkParameters extends WorkParameters { abstract class InstrumentAction implements WorkAction { private static final Object lock = new Object() private static ClassLoader pluginCL - private static volatile long lastBuildStamp + private static String cachedPluginPath + private static volatile long cachedBuildStamp @Override void execute() { // reset shared class-loaders each time a new build starts long buildStamp = parameters.buildStartedTime.get() - if (lastBuildStamp < buildStamp || !pluginCL) { + String pluginPath = parameters.pluginClassPath.join(':') + if (rebuildSharedClassLoader(buildStamp, pluginPath)) { synchronized (lock) { - if (lastBuildStamp < buildStamp || !pluginCL) { + if (rebuildSharedClassLoader(buildStamp, pluginPath)) { pluginCL = createClassLoader(parameters.pluginClassPath) - lastBuildStamp = buildStamp + cachedPluginPath = pluginPath + cachedBuildStamp = buildStamp } } } @@ -199,6 +202,10 @@ abstract class InstrumentAction implements WorkAction InstrumentingPlugin.instrumentClasses(plugins, instrumentingCL, sourceDirectory, targetDirectory) } + static boolean rebuildSharedClassLoader(long buildStamp, String pluginPath) { + return cachedBuildStamp < buildStamp || cachedPluginPath != pluginPath + } + static ClassLoader createClassLoader(cp, parent = InstrumentAction.classLoader) { return new URLClassLoader(cp*.toURI()*.toURL() as URL[], parent as ClassLoader) } diff --git a/dd-java-agent/agent-otel/otel-bootstrap/build.gradle b/dd-java-agent/agent-otel/otel-bootstrap/build.gradle new file mode 100644 index 00000000000..ae5a4aed26a --- /dev/null +++ b/dd-java-agent/agent-otel/otel-bootstrap/build.gradle @@ -0,0 +1,66 @@ +plugins { + id "com.github.johnrengelman.shadow" +} + +apply from: "$rootDir/gradle/java.gradle" +apply plugin: 'instrument' + +configurations { + embeddedClasspath { + visible = false + canBeConsumed = false + canBeResolved = true + } + instrumentPluginClasspath { + visible = false + canBeConsumed = false + canBeResolved = true + } +} + +instrument.plugins = ['datadog.opentelemetry.tooling.OtelShimGradlePlugin'] + +minimumInstructionCoverage = 0.0 +minimumBranchCoverage = 0.0 + +forbiddenApis { + ignoreFailures = true +} +spotbugs { + onlyAnalyze = ['none'] +} + +dependencies { + // latest OpenTelemetry API for drop-in support; instrumented at build-time with our shim + embeddedClasspath group: 'io.opentelemetry', name: 'opentelemetry-api', version: '1.38.0' + + implementation project(':dd-java-agent:agent-otel:otel-shim') + + instrumentPluginClasspath project(':dd-java-agent:agent-otel:otel-tooling') +} + +// unpack embeddedClasspath to same path as compiled classes so it can get instrumented +tasks.register('unpackJars', Copy) { + dependsOn configurations.embeddedClasspath + exclude 'META-INF/' + from { + configurations.embeddedClasspath.collect { zipTree(it) } + } + into compileJava.destinationDirectory +} +tasks.named('compileJava') { + dependsOn 'unpackJars' +} + +shadowJar { + dependencies deps.excludeShared + + exclude 'io/opentelemetry/context/internal/shaded/**' + + relocate 'io.opentelemetry', 'datadog.trace.bootstrap.otel' + relocate 'datadog.opentelemetry.shim', 'datadog.trace.bootstrap.otel.shim' +} + +jar { + archiveClassifier = 'unbundled' +} diff --git a/dd-java-agent/agent-otel/otel-bootstrap/src/main/java/package-info.java b/dd-java-agent/agent-otel/otel-bootstrap/src/main/java/package-info.java new file mode 100644 index 00000000000..3f00de3c82c --- /dev/null +++ b/dd-java-agent/agent-otel/otel-bootstrap/src/main/java/package-info.java @@ -0,0 +1 @@ +// placeholder to activate the compiler task diff --git a/dd-java-agent/agent-otel/otel-shim/build.gradle b/dd-java-agent/agent-otel/otel-shim/build.gradle new file mode 100644 index 00000000000..d622712f484 --- /dev/null +++ b/dd-java-agent/agent-otel/otel-shim/build.gradle @@ -0,0 +1,11 @@ +apply from: "$rootDir/gradle/java.gradle" + +minimumInstructionCoverage = 0.0 +minimumBranchCoverage = 0.0 + +dependencies { + // minimum OpenTelemetry API version this shim is compatible with + compileOnly group: 'io.opentelemetry', name: 'opentelemetry-api', version: '1.4.0' + + implementation project(':internal-api') +} diff --git a/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/context/OtelContext.java b/dd-java-agent/agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim/context/OtelContext.java similarity index 59% rename from dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/context/OtelContext.java rename to dd-java-agent/agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim/context/OtelContext.java index 1779a85e788..bea0f7a8b5c 100644 --- a/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/context/OtelContext.java +++ b/dd-java-agent/agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim/context/OtelContext.java @@ -1,7 +1,10 @@ -package datadog.trace.instrumentation.opentelemetry14.context; +package datadog.opentelemetry.shim.context; +import datadog.opentelemetry.shim.trace.OtelSpan; import datadog.trace.bootstrap.instrumentation.api.AgentScope; -import datadog.trace.instrumentation.opentelemetry14.trace.OtelSpan; +import datadog.trace.bootstrap.instrumentation.api.AgentSpan; +import datadog.trace.bootstrap.instrumentation.api.AgentTracer; +import datadog.trace.bootstrap.instrumentation.api.AttachableWrapper; import io.opentelemetry.api.trace.Span; import io.opentelemetry.context.Context; import io.opentelemetry.context.ContextKey; @@ -56,6 +59,38 @@ public Scope makeCurrent() { return scope; } + public static Context current() { + // Check empty context + AgentSpan agentCurrentSpan = AgentTracer.activeSpan(); + if (null == agentCurrentSpan) { + return OtelContext.ROOT; + } + // Get OTel current span + Span otelCurrentSpan = null; + if (agentCurrentSpan instanceof AttachableWrapper) { + Object wrapper = ((AttachableWrapper) agentCurrentSpan).getWrapper(); + if (wrapper instanceof OtelSpan) { + otelCurrentSpan = (OtelSpan) wrapper; + } + } + if (otelCurrentSpan == null) { + otelCurrentSpan = new OtelSpan(agentCurrentSpan); + } + // Get OTel root span + Span otelRootSpan = null; + AgentSpan agentRootSpan = agentCurrentSpan.getLocalRootSpan(); + if (agentRootSpan instanceof AttachableWrapper) { + Object wrapper = ((AttachableWrapper) agentRootSpan).getWrapper(); + if (wrapper instanceof OtelSpan) { + otelRootSpan = (OtelSpan) wrapper; + } + } + if (otelRootSpan == null) { + otelRootSpan = new OtelSpan(agentRootSpan); + } + return new OtelContext(otelCurrentSpan, otelRootSpan); + } + @Override public String toString() { return "OtelContext{" diff --git a/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/context/OtelScope.java b/dd-java-agent/agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim/context/OtelScope.java similarity index 90% rename from dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/context/OtelScope.java rename to dd-java-agent/agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim/context/OtelScope.java index 6eb0ffdfc4a..7ff94ca0f77 100644 --- a/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/context/OtelScope.java +++ b/dd-java-agent/agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim/context/OtelScope.java @@ -1,4 +1,4 @@ -package datadog.trace.instrumentation.opentelemetry14.context; +package datadog.opentelemetry.shim.context; import datadog.trace.bootstrap.instrumentation.api.AgentScope; import datadog.trace.bootstrap.instrumentation.api.AttachableWrapper; diff --git a/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/context/propagation/AgentTextMapPropagator.java b/dd-java-agent/agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim/context/propagation/AgentTextMapPropagator.java similarity index 90% rename from dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/context/propagation/AgentTextMapPropagator.java rename to dd-java-agent/agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim/context/propagation/AgentTextMapPropagator.java index 906fc77e99c..c12eace4d65 100644 --- a/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/context/propagation/AgentTextMapPropagator.java +++ b/dd-java-agent/agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim/context/propagation/AgentTextMapPropagator.java @@ -1,16 +1,16 @@ -package datadog.trace.instrumentation.opentelemetry14.context.propagation; +package datadog.opentelemetry.shim.context.propagation; +import static datadog.opentelemetry.shim.trace.OtelSpanContext.fromRemote; import static datadog.trace.api.TracePropagationStyle.TRACECONTEXT; -import static datadog.trace.instrumentation.opentelemetry14.trace.OtelSpanContext.fromRemote; +import datadog.opentelemetry.shim.context.OtelContext; +import datadog.opentelemetry.shim.trace.OtelExtractedContext; +import datadog.opentelemetry.shim.trace.OtelSpan; import datadog.trace.api.TracePropagationStyle; import datadog.trace.bootstrap.instrumentation.api.AgentSpan; import datadog.trace.bootstrap.instrumentation.api.AgentSpan.Context.Extracted; import datadog.trace.bootstrap.instrumentation.api.AgentTracer; import datadog.trace.bootstrap.instrumentation.api.TagContext; -import datadog.trace.instrumentation.opentelemetry14.context.OtelContext; -import datadog.trace.instrumentation.opentelemetry14.trace.OtelExtractedContext; -import datadog.trace.instrumentation.opentelemetry14.trace.OtelSpan; import io.opentelemetry.api.trace.Span; import io.opentelemetry.api.trace.SpanContext; import io.opentelemetry.api.trace.TraceState; diff --git a/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/context/propagation/OtelContextPropagators.java b/dd-java-agent/agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim/context/propagation/OtelContextPropagators.java similarity index 85% rename from dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/context/propagation/OtelContextPropagators.java rename to dd-java-agent/agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim/context/propagation/OtelContextPropagators.java index 7d7f2ab10fc..682ebd9ce20 100644 --- a/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/context/propagation/OtelContextPropagators.java +++ b/dd-java-agent/agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim/context/propagation/OtelContextPropagators.java @@ -1,4 +1,4 @@ -package datadog.trace.instrumentation.opentelemetry14.context.propagation; +package datadog.opentelemetry.shim.context.propagation; import io.opentelemetry.context.propagation.ContextPropagators; import io.opentelemetry.context.propagation.TextMapPropagator; diff --git a/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/context/propagation/TraceStateHelper.java b/dd-java-agent/agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim/context/propagation/TraceStateHelper.java similarity index 96% rename from dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/context/propagation/TraceStateHelper.java rename to dd-java-agent/agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim/context/propagation/TraceStateHelper.java index 39751232ac3..b0e2c135936 100644 --- a/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/context/propagation/TraceStateHelper.java +++ b/dd-java-agent/agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim/context/propagation/TraceStateHelper.java @@ -1,4 +1,4 @@ -package datadog.trace.instrumentation.opentelemetry14.context.propagation; +package datadog.opentelemetry.shim.context.propagation; import io.opentelemetry.api.trace.TraceState; import io.opentelemetry.api.trace.TraceStateBuilder; diff --git a/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/trace/OtelConventions.java b/dd-java-agent/agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim/trace/OtelConventions.java similarity index 99% rename from dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/trace/OtelConventions.java rename to dd-java-agent/agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim/trace/OtelConventions.java index 306763cf49e..1c741ed99ae 100644 --- a/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/trace/OtelConventions.java +++ b/dd-java-agent/agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim/trace/OtelConventions.java @@ -1,4 +1,4 @@ -package datadog.trace.instrumentation.opentelemetry14.trace; +package datadog.opentelemetry.shim.trace; import static datadog.trace.api.DDTags.ANALYTICS_SAMPLE_RATE; import static datadog.trace.bootstrap.instrumentation.api.Tags.SPAN_KIND; diff --git a/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/trace/OtelExtractedContext.java b/dd-java-agent/agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim/trace/OtelExtractedContext.java similarity index 97% rename from dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/trace/OtelExtractedContext.java rename to dd-java-agent/agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim/trace/OtelExtractedContext.java index 0823fa48f5d..fa387bf635f 100644 --- a/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/trace/OtelExtractedContext.java +++ b/dd-java-agent/agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim/trace/OtelExtractedContext.java @@ -1,4 +1,4 @@ -package datadog.trace.instrumentation.opentelemetry14.trace; +package datadog.opentelemetry.shim.trace; import datadog.trace.api.DDSpanId; import datadog.trace.api.DDTraceId; diff --git a/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/trace/OtelSpan.java b/dd-java-agent/agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim/trace/OtelSpan.java similarity index 95% rename from dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/trace/OtelSpan.java rename to dd-java-agent/agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim/trace/OtelSpan.java index 5615cf01d7e..64fb9f9a2cb 100644 --- a/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/trace/OtelSpan.java +++ b/dd-java-agent/agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim/trace/OtelSpan.java @@ -1,8 +1,8 @@ -package datadog.trace.instrumentation.opentelemetry14.trace; +package datadog.opentelemetry.shim.trace; +import static datadog.opentelemetry.shim.trace.OtelConventions.applyNamingConvention; +import static datadog.opentelemetry.shim.trace.OtelConventions.applyReservedAttribute; import static datadog.trace.bootstrap.instrumentation.api.AgentTracer.activateSpan; -import static datadog.trace.instrumentation.opentelemetry14.trace.OtelConventions.applyNamingConvention; -import static datadog.trace.instrumentation.opentelemetry14.trace.OtelConventions.applyReservedAttribute; import static io.opentelemetry.api.trace.StatusCode.ERROR; import static io.opentelemetry.api.trace.StatusCode.OK; import static io.opentelemetry.api.trace.StatusCode.UNSET; diff --git a/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/trace/OtelSpanBuilder.java b/dd-java-agent/agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim/trace/OtelSpanBuilder.java similarity index 91% rename from dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/trace/OtelSpanBuilder.java rename to dd-java-agent/agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim/trace/OtelSpanBuilder.java index 6ab7f81f0ed..45a55f02ad9 100644 --- a/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/trace/OtelSpanBuilder.java +++ b/dd-java-agent/agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim/trace/OtelSpanBuilder.java @@ -1,11 +1,11 @@ -package datadog.trace.instrumentation.opentelemetry14.trace; +package datadog.opentelemetry.shim.trace; +import static datadog.opentelemetry.shim.trace.OtelConventions.ANALYTICS_EVENT_SPECIFIC_ATTRIBUTES; +import static datadog.opentelemetry.shim.trace.OtelConventions.OPERATION_NAME_SPECIFIC_ATTRIBUTE; +import static datadog.opentelemetry.shim.trace.OtelConventions.toSpanKindTagValue; +import static datadog.opentelemetry.shim.trace.OtelExtractedContext.extract; import static datadog.trace.api.DDTags.ANALYTICS_SAMPLE_RATE; import static datadog.trace.bootstrap.instrumentation.api.Tags.SPAN_KIND; -import static datadog.trace.instrumentation.opentelemetry14.trace.OtelConventions.ANALYTICS_EVENT_SPECIFIC_ATTRIBUTES; -import static datadog.trace.instrumentation.opentelemetry14.trace.OtelConventions.OPERATION_NAME_SPECIFIC_ATTRIBUTE; -import static datadog.trace.instrumentation.opentelemetry14.trace.OtelConventions.toSpanKindTagValue; -import static datadog.trace.instrumentation.opentelemetry14.trace.OtelExtractedContext.extract; import static io.opentelemetry.api.trace.SpanKind.INTERNAL; import static java.lang.Boolean.parseBoolean; import static java.util.Locale.ROOT; diff --git a/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/trace/OtelSpanContext.java b/dd-java-agent/agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim/trace/OtelSpanContext.java similarity index 97% rename from dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/trace/OtelSpanContext.java rename to dd-java-agent/agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim/trace/OtelSpanContext.java index 0eacf3b19cb..5b18f1931a5 100644 --- a/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/trace/OtelSpanContext.java +++ b/dd-java-agent/agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim/trace/OtelSpanContext.java @@ -1,4 +1,4 @@ -package datadog.trace.instrumentation.opentelemetry14.trace; +package datadog.opentelemetry.shim.trace; import datadog.trace.api.DDSpanId; import datadog.trace.bootstrap.instrumentation.api.AgentSpan; diff --git a/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/trace/OtelSpanLink.java b/dd-java-agent/agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim/trace/OtelSpanLink.java similarity index 93% rename from dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/trace/OtelSpanLink.java rename to dd-java-agent/agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim/trace/OtelSpanLink.java index c410d2349e4..3384dd09c90 100644 --- a/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/trace/OtelSpanLink.java +++ b/dd-java-agent/agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim/trace/OtelSpanLink.java @@ -1,10 +1,10 @@ -package datadog.trace.instrumentation.opentelemetry14.trace; +package datadog.opentelemetry.shim.trace; +import datadog.opentelemetry.shim.context.propagation.TraceStateHelper; import datadog.trace.api.DDSpanId; import datadog.trace.api.DDTraceId; import datadog.trace.bootstrap.instrumentation.api.SpanLink; import datadog.trace.bootstrap.instrumentation.api.SpanLinkAttributes; -import datadog.trace.instrumentation.opentelemetry14.context.propagation.TraceStateHelper; import io.opentelemetry.api.trace.SpanContext; import java.util.List; diff --git a/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/trace/OtelTracer.java b/dd-java-agent/agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim/trace/OtelTracer.java similarity index 83% rename from dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/trace/OtelTracer.java rename to dd-java-agent/agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim/trace/OtelTracer.java index 65980b38a9d..57d33654968 100644 --- a/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/trace/OtelTracer.java +++ b/dd-java-agent/agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim/trace/OtelTracer.java @@ -1,6 +1,6 @@ -package datadog.trace.instrumentation.opentelemetry14.trace; +package datadog.opentelemetry.shim.trace; -import static datadog.trace.instrumentation.opentelemetry14.trace.OtelConventions.SPAN_KIND_INTERNAL; +import static datadog.opentelemetry.shim.trace.OtelConventions.SPAN_KIND_INTERNAL; import datadog.trace.bootstrap.instrumentation.api.AgentTracer; import io.opentelemetry.api.trace.SpanBuilder; diff --git a/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/trace/OtelTracerBuilder.java b/dd-java-agent/agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim/trace/OtelTracerBuilder.java similarity index 92% rename from dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/trace/OtelTracerBuilder.java rename to dd-java-agent/agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim/trace/OtelTracerBuilder.java index 4db53bde598..055745b6ab2 100644 --- a/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/trace/OtelTracerBuilder.java +++ b/dd-java-agent/agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim/trace/OtelTracerBuilder.java @@ -1,4 +1,4 @@ -package datadog.trace.instrumentation.opentelemetry14.trace; +package datadog.opentelemetry.shim.trace; import io.opentelemetry.api.trace.Tracer; import io.opentelemetry.api.trace.TracerBuilder; diff --git a/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/trace/OtelTracerProvider.java b/dd-java-agent/agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim/trace/OtelTracerProvider.java similarity index 96% rename from dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/trace/OtelTracerProvider.java rename to dd-java-agent/agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim/trace/OtelTracerProvider.java index 57aee97d61b..97a05fb3afd 100644 --- a/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/trace/OtelTracerProvider.java +++ b/dd-java-agent/agent-otel/otel-shim/src/main/java/datadog/opentelemetry/shim/trace/OtelTracerProvider.java @@ -1,4 +1,4 @@ -package datadog.trace.instrumentation.opentelemetry14.trace; +package datadog.opentelemetry.shim.trace; import io.opentelemetry.api.trace.Tracer; import io.opentelemetry.api.trace.TracerBuilder; diff --git a/dd-java-agent/agent-otel/otel-tooling/build.gradle b/dd-java-agent/agent-otel/otel-tooling/build.gradle new file mode 100644 index 00000000000..e3511f9f60c --- /dev/null +++ b/dd-java-agent/agent-otel/otel-tooling/build.gradle @@ -0,0 +1,9 @@ +apply from: "$rootDir/gradle/java.gradle" + +minimumInstructionCoverage = 0.0 +minimumBranchCoverage = 0.0 + +dependencies { + api deps.bytebuddy + api deps.bytebuddyagent +} diff --git a/dd-java-agent/agent-otel/otel-tooling/src/main/java/datadog/opentelemetry/tooling/OtelShimGradlePlugin.java b/dd-java-agent/agent-otel/otel-tooling/src/main/java/datadog/opentelemetry/tooling/OtelShimGradlePlugin.java new file mode 100644 index 00000000000..ca891d25992 --- /dev/null +++ b/dd-java-agent/agent-otel/otel-tooling/src/main/java/datadog/opentelemetry/tooling/OtelShimGradlePlugin.java @@ -0,0 +1,43 @@ +package datadog.opentelemetry.tooling; + +import static datadog.opentelemetry.tooling.OtelShimInjector.OTEL_CONTEXT_CLASSES; +import static datadog.opentelemetry.tooling.OtelShimInjector.OTEL_CONTEXT_STORAGE_CLASSES; +import static datadog.opentelemetry.tooling.OtelShimInjector.OTEL_ENTRYPOINT_CLASSES; +import static net.bytebuddy.matcher.ElementMatchers.namedOneOf; + +import de.thetaphi.forbiddenapis.SuppressForbidden; +import java.io.File; +import java.io.IOException; +import net.bytebuddy.build.Plugin; +import net.bytebuddy.description.type.TypeDescription; +import net.bytebuddy.dynamic.ClassFileLocator; +import net.bytebuddy.dynamic.DynamicType; + +/** + * Bytebuddy gradle plugin which injects our OpenTelemetry shim into the target API. + * + * @see "buildSrc/src/main/groovy/InstrumentPlugin.groovy" + */ +public class OtelShimGradlePlugin extends Plugin.ForElementMatcher { + private final File targetDir; + + @SuppressForbidden + public OtelShimGradlePlugin(File targetDir) { + super( + namedOneOf(OTEL_ENTRYPOINT_CLASSES) + .or(namedOneOf(OTEL_CONTEXT_STORAGE_CLASSES)) + .or(namedOneOf(OTEL_CONTEXT_CLASSES))); + this.targetDir = targetDir; + } + + @Override + public DynamicType.Builder apply( + final DynamicType.Builder builder, + final TypeDescription typeDescription, + final ClassFileLocator classFileLocator) { + return builder.visit(OtelShimInjector.INSTANCE); + } + + @Override + public void close() throws IOException {} +} diff --git a/dd-java-agent/agent-otel/otel-tooling/src/main/java/datadog/opentelemetry/tooling/OtelShimInjector.java b/dd-java-agent/agent-otel/otel-tooling/src/main/java/datadog/opentelemetry/tooling/OtelShimInjector.java new file mode 100644 index 00000000000..9d4c63ed0af --- /dev/null +++ b/dd-java-agent/agent-otel/otel-tooling/src/main/java/datadog/opentelemetry/tooling/OtelShimInjector.java @@ -0,0 +1,130 @@ +package datadog.opentelemetry.tooling; + +import net.bytebuddy.asm.AsmVisitorWrapper; +import net.bytebuddy.description.field.FieldDescription; +import net.bytebuddy.description.field.FieldList; +import net.bytebuddy.description.method.MethodList; +import net.bytebuddy.description.type.TypeDescription; +import net.bytebuddy.implementation.Implementation; +import net.bytebuddy.jar.asm.ClassVisitor; +import net.bytebuddy.jar.asm.ClassWriter; +import net.bytebuddy.jar.asm.MethodVisitor; +import net.bytebuddy.jar.asm.Opcodes; +import net.bytebuddy.pool.TypePool; + +/** ASM visitor which injects our OpenTelemetry shim into the target API. */ +public final class OtelShimInjector implements AsmVisitorWrapper { + static final OtelShimInjector INSTANCE = new OtelShimInjector(); + + static final String[] OTEL_ENTRYPOINT_CLASSES = { + "io.opentelemetry.api.DefaultOpenTelemetry", + "io.opentelemetry.api.GlobalOpenTelemetry$ObfuscatedOpenTelemetry", + }; + + static final String[] OTEL_CONTEXT_STORAGE_CLASSES = { + "io.opentelemetry.context.ThreadLocalContextStorage", + "io.opentelemetry.context.StrictContextStorage", + }; + + static final String[] OTEL_CONTEXT_CLASSES = { + "io.opentelemetry.context.ArrayBasedContext", + }; + + static final String TRACER_PROVIDER_DESCRIPTOR = "Lio/opentelemetry/api/trace/TracerProvider;"; + + static final String CONTEXT_PROPAGATORS_DESCRIPTOR = + "Lio/opentelemetry/context/propagation/ContextPropagators;"; + + static final String CONTEXT_DESCRIPTOR = "Lio/opentelemetry/context/Context;"; + + static final String GET_TRACER_PROVIDER_METHOD_DESCRIPTOR = "()" + TRACER_PROVIDER_DESCRIPTOR; + + static final String GET_PROPAGATORS_METHOD_DESCRIPTOR = "()" + CONTEXT_PROPAGATORS_DESCRIPTOR; + + static final String CURRENT_CONTEXT_METHOD_DESCRIPTOR = "()" + CONTEXT_DESCRIPTOR; + + static final String ROOT_CONTEXT_METHOD_DESCRIPTOR = "()" + CONTEXT_DESCRIPTOR; + + static final String SHIM_PACKAGE_PREFIX = "datadog/opentelemetry/shim/"; + + @Override + public int mergeWriter(final int flags) { + return flags | ClassWriter.COMPUTE_MAXS; + } + + @Override + public int mergeReader(final int flags) { + return flags; + } + + @Override + public ClassVisitor wrap( + final TypeDescription instrumentedType, + final ClassVisitor classVisitor, + final Implementation.Context implementationContext, + final TypePool typePool, + final FieldList fields, + final MethodList methods, + final int writerFlags, + final int readerFlags) { + // for convenience use the same bytecode injector for each class of interest + // this is safe because the shim-injected methods don't overlap between them + return new ClassVisitor(Opcodes.ASM7, classVisitor) { + @Override + public MethodVisitor visitMethod( + final int access, + final String name, + final String descriptor, + final String signature, + final String[] exceptions) { + MethodVisitor mv = super.visitMethod(access, name, descriptor, signature, exceptions); + if ("getTracerProvider".equals(name) + && GET_TRACER_PROVIDER_METHOD_DESCRIPTOR.equals(descriptor)) { + mv.visitCode(); + mv.visitFieldInsn( + Opcodes.GETSTATIC, + SHIM_PACKAGE_PREFIX + "trace/OtelTracerProvider", + "INSTANCE", + TRACER_PROVIDER_DESCRIPTOR); + mv.visitInsn(Opcodes.ARETURN); + mv.visitEnd(); + return null; + } else if ("getPropagators".equals(name) + && GET_PROPAGATORS_METHOD_DESCRIPTOR.equals(descriptor)) { + mv.visitCode(); + mv.visitFieldInsn( + Opcodes.GETSTATIC, + SHIM_PACKAGE_PREFIX + "context/propagation/OtelContextPropagators", + "INSTANCE", + CONTEXT_PROPAGATORS_DESCRIPTOR); + mv.visitInsn(Opcodes.ARETURN); + mv.visitEnd(); + return null; + } else if ("current".equals(name) && CURRENT_CONTEXT_METHOD_DESCRIPTOR.equals(descriptor)) { + mv.visitCode(); + mv.visitMethodInsn( + Opcodes.INVOKESTATIC, + SHIM_PACKAGE_PREFIX + "context/OtelContext", + "current", + CURRENT_CONTEXT_METHOD_DESCRIPTOR, + false); + mv.visitInsn(Opcodes.ARETURN); + mv.visitEnd(); + return null; + } else if ("root".equals(name) && ROOT_CONTEXT_METHOD_DESCRIPTOR.equals(descriptor)) { + mv.visitCode(); + mv.visitFieldInsn( + Opcodes.GETSTATIC, + SHIM_PACKAGE_PREFIX + "context/OtelContext", + "ROOT", + CONTEXT_DESCRIPTOR); + mv.visitInsn(Opcodes.ARETURN); + mv.visitEnd(); + return null; + } else { + return mv; + } + } + }; + } +} diff --git a/dd-java-agent/build.gradle b/dd-java-agent/build.gradle index ff10b4d3ce0..1b37a418990 100644 --- a/dd-java-agent/build.gradle +++ b/dd-java-agent/build.gradle @@ -219,6 +219,7 @@ dependencies { // Includes for the top level shadow jar shadowInclude project(path: ':dd-java-agent:agent-bootstrap') shadowInclude project(path: ':dd-java-agent:agent-debugger:debugger-bootstrap') + shadowInclude project(path: ':dd-java-agent:agent-otel:otel-bootstrap', configuration: 'shadow') // Includes for the shared internal shadow jar sharedShadowInclude deps.shared diff --git a/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/build.gradle b/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/build.gradle index 3c689b66333..976cd0970f1 100644 --- a/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/build.gradle +++ b/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/build.gradle @@ -16,6 +16,8 @@ dependencies { compileOnly group: 'io.opentelemetry', name: 'opentelemetry-api', version: openTelemetryVersion compileOnly group: 'com.google.auto.value', name: 'auto-value-annotations', version: '1.6.6' + implementation project(':dd-java-agent:agent-otel:otel-shim') + testImplementation group: 'io.opentelemetry', name: 'opentelemetry-api', version: openTelemetryVersion testImplementation group: 'org.skyscreamer', name: 'jsonassert', version: '1.5.1' latestDepTestImplementation group: 'io.opentelemetry', name: 'opentelemetry-api', version: '1+' diff --git a/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/OpenTelemetryInstrumentation.java b/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/OpenTelemetryInstrumentation.java index fd64a367fa4..23a6b92b488 100644 --- a/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/OpenTelemetryInstrumentation.java +++ b/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/OpenTelemetryInstrumentation.java @@ -7,12 +7,11 @@ import static net.bytebuddy.matcher.ElementMatchers.takesNoArguments; import com.google.auto.service.AutoService; +import datadog.opentelemetry.shim.context.propagation.OtelContextPropagators; +import datadog.opentelemetry.shim.trace.OtelTracerProvider; import datadog.trace.agent.tooling.Instrumenter; import datadog.trace.agent.tooling.InstrumenterModule; import datadog.trace.api.InstrumenterConfig; -import datadog.trace.instrumentation.opentelemetry14.context.propagation.OtelContextPropagators; -import datadog.trace.instrumentation.opentelemetry14.trace.OtelTracerProvider; -import datadog.trace.util.Strings; import io.opentelemetry.api.trace.TracerProvider; import io.opentelemetry.context.propagation.ContextPropagators; import net.bytebuddy.asm.Advice; @@ -22,8 +21,6 @@ @AutoService(InstrumenterModule.class) public class OpenTelemetryInstrumentation extends InstrumenterModule.Tracing implements Instrumenter.CanShortcutTypeMatching { - public static final String ROOT_PACKAGE_NAME = - Strings.getPackageName(OpenTelemetryInstrumentation.class.getName()); public OpenTelemetryInstrumentation() { super("opentelemetry.experimental", "opentelemetry-1"); @@ -60,26 +57,26 @@ public boolean onlyMatchKnownTypes() { @Override public String[] helperClassNames() { return new String[] { - packageName + ".context.OtelContext", - packageName + ".context.OtelScope", - packageName + ".context.propagation.AgentTextMapPropagator", - packageName + ".context.propagation.OtelContextPropagators", - packageName + ".context.propagation.TraceStateHelper", - packageName + ".trace.OtelExtractedContext", - packageName + ".trace.OtelConventions", - packageName + ".trace.OtelConventions$1", - packageName + ".trace.OtelSpan", - packageName + ".trace.OtelSpan$1", - packageName + ".trace.OtelSpan$NoopSpan", - packageName + ".trace.OtelSpan$NoopSpanContext", - packageName + ".trace.OtelSpanBuilder", - packageName + ".trace.OtelSpanBuilder$1", - packageName + ".trace.OtelSpanContext", - packageName + ".trace.OtelSpanLink", - packageName + ".trace.OtelSpanLink$1", - packageName + ".trace.OtelTracer", - packageName + ".trace.OtelTracerBuilder", - packageName + ".trace.OtelTracerProvider", + "datadog.opentelemetry.shim.context.OtelContext", + "datadog.opentelemetry.shim.context.OtelScope", + "datadog.opentelemetry.shim.context.propagation.AgentTextMapPropagator", + "datadog.opentelemetry.shim.context.propagation.OtelContextPropagators", + "datadog.opentelemetry.shim.context.propagation.TraceStateHelper", + "datadog.opentelemetry.shim.trace.OtelExtractedContext", + "datadog.opentelemetry.shim.trace.OtelConventions", + "datadog.opentelemetry.shim.trace.OtelConventions$1", + "datadog.opentelemetry.shim.trace.OtelSpan", + "datadog.opentelemetry.shim.trace.OtelSpan$1", + "datadog.opentelemetry.shim.trace.OtelSpan$NoopSpan", + "datadog.opentelemetry.shim.trace.OtelSpan$NoopSpanContext", + "datadog.opentelemetry.shim.trace.OtelSpanBuilder", + "datadog.opentelemetry.shim.trace.OtelSpanBuilder$1", + "datadog.opentelemetry.shim.trace.OtelSpanContext", + "datadog.opentelemetry.shim.trace.OtelSpanLink", + "datadog.opentelemetry.shim.trace.OtelSpanLink$1", + "datadog.opentelemetry.shim.trace.OtelTracer", + "datadog.opentelemetry.shim.trace.OtelTracerBuilder", + "datadog.opentelemetry.shim.trace.OtelTracerProvider", }; } diff --git a/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/context/OpenTelemetryContextInstrumentation.java b/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/context/OpenTelemetryContextInstrumentation.java index a9c1fc262c2..16bf739da0b 100644 --- a/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/context/OpenTelemetryContextInstrumentation.java +++ b/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/context/OpenTelemetryContextInstrumentation.java @@ -2,12 +2,12 @@ import static datadog.trace.agent.tooling.bytebuddy.matcher.HierarchyMatchers.implementsInterface; import static datadog.trace.agent.tooling.bytebuddy.matcher.NameMatchers.named; -import static datadog.trace.instrumentation.opentelemetry14.OpenTelemetryInstrumentation.ROOT_PACKAGE_NAME; import static net.bytebuddy.matcher.ElementMatchers.isMethod; import static net.bytebuddy.matcher.ElementMatchers.returns; import static net.bytebuddy.matcher.ElementMatchers.takesNoArguments; import com.google.auto.service.AutoService; +import datadog.opentelemetry.shim.context.OtelContext; import datadog.trace.agent.tooling.Instrumenter; import datadog.trace.agent.tooling.InstrumenterModule; import datadog.trace.api.InstrumenterConfig; @@ -54,23 +54,23 @@ public boolean onlyMatchKnownTypes() { @Override public String[] helperClassNames() { return new String[] { - packageName + ".OtelContext", - packageName + ".OtelScope", - ROOT_PACKAGE_NAME + ".trace.OtelExtractedContext", - ROOT_PACKAGE_NAME + ".trace.OtelConventions", - ROOT_PACKAGE_NAME + ".trace.OtelConventions$1", - ROOT_PACKAGE_NAME + ".trace.OtelSpan", - ROOT_PACKAGE_NAME + ".trace.OtelSpan$1", - ROOT_PACKAGE_NAME + ".trace.OtelSpan$NoopSpan", - ROOT_PACKAGE_NAME + ".trace.OtelSpan$NoopSpanContext", - ROOT_PACKAGE_NAME + ".trace.OtelSpanBuilder", - ROOT_PACKAGE_NAME + ".trace.OtelSpanBuilder$1", - ROOT_PACKAGE_NAME + ".trace.OtelSpanContext", - ROOT_PACKAGE_NAME + ".trace.OtelSpanLink", - ROOT_PACKAGE_NAME + ".trace.OtelSpanLink$1", - ROOT_PACKAGE_NAME + ".trace.OtelTracer", - ROOT_PACKAGE_NAME + ".trace.OtelTracerBuilder", - ROOT_PACKAGE_NAME + ".trace.OtelTracerProvider", + "datadog.opentelemetry.shim.context.OtelContext", + "datadog.opentelemetry.shim.context.OtelScope", + "datadog.opentelemetry.shim.trace.OtelExtractedContext", + "datadog.opentelemetry.shim.trace.OtelConventions", + "datadog.opentelemetry.shim.trace.OtelConventions$1", + "datadog.opentelemetry.shim.trace.OtelSpan", + "datadog.opentelemetry.shim.trace.OtelSpan$1", + "datadog.opentelemetry.shim.trace.OtelSpan$NoopSpan", + "datadog.opentelemetry.shim.trace.OtelSpan$NoopSpanContext", + "datadog.opentelemetry.shim.trace.OtelSpanBuilder", + "datadog.opentelemetry.shim.trace.OtelSpanBuilder$1", + "datadog.opentelemetry.shim.trace.OtelSpanContext", + "datadog.opentelemetry.shim.trace.OtelSpanLink", + "datadog.opentelemetry.shim.trace.OtelSpanLink$1", + "datadog.opentelemetry.shim.trace.OtelTracer", + "datadog.opentelemetry.shim.trace.OtelTracerBuilder", + "datadog.opentelemetry.shim.trace.OtelTracerProvider", }; } diff --git a/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/context/OpenTelemetryContextStorageInstrumentation.java b/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/context/OpenTelemetryContextStorageInstrumentation.java index 6d8b7424c9b..c84213266d2 100644 --- a/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/context/OpenTelemetryContextStorageInstrumentation.java +++ b/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/main/java/datadog/trace/instrumentation/opentelemetry14/context/OpenTelemetryContextStorageInstrumentation.java @@ -2,20 +2,15 @@ import static datadog.trace.agent.tooling.bytebuddy.matcher.HierarchyMatchers.implementsInterface; import static datadog.trace.agent.tooling.bytebuddy.matcher.NameMatchers.named; -import static datadog.trace.instrumentation.opentelemetry14.OpenTelemetryInstrumentation.ROOT_PACKAGE_NAME; import static net.bytebuddy.matcher.ElementMatchers.isMethod; import static net.bytebuddy.matcher.ElementMatchers.returns; import static net.bytebuddy.matcher.ElementMatchers.takesNoArguments; import com.google.auto.service.AutoService; +import datadog.opentelemetry.shim.context.OtelContext; import datadog.trace.agent.tooling.Instrumenter; import datadog.trace.agent.tooling.InstrumenterModule; import datadog.trace.api.InstrumenterConfig; -import datadog.trace.bootstrap.instrumentation.api.AgentSpan; -import datadog.trace.bootstrap.instrumentation.api.AgentTracer; -import datadog.trace.bootstrap.instrumentation.api.AttachableWrapper; -import datadog.trace.instrumentation.opentelemetry14.trace.OtelSpan; -import io.opentelemetry.api.trace.Span; import io.opentelemetry.context.Context; import net.bytebuddy.asm.Advice; import net.bytebuddy.description.type.TypeDescription; @@ -60,23 +55,23 @@ public boolean onlyMatchKnownTypes() { @Override public String[] helperClassNames() { return new String[] { - packageName + ".OtelContext", - packageName + ".OtelScope", - ROOT_PACKAGE_NAME + ".trace.OtelExtractedContext", - ROOT_PACKAGE_NAME + ".trace.OtelConventions", - ROOT_PACKAGE_NAME + ".trace.OtelConventions$1", - ROOT_PACKAGE_NAME + ".trace.OtelSpan", - ROOT_PACKAGE_NAME + ".trace.OtelSpan$1", - ROOT_PACKAGE_NAME + ".trace.OtelSpan$NoopSpan", - ROOT_PACKAGE_NAME + ".trace.OtelSpan$NoopSpanContext", - ROOT_PACKAGE_NAME + ".trace.OtelSpanBuilder", - ROOT_PACKAGE_NAME + ".trace.OtelSpanBuilder$1", - ROOT_PACKAGE_NAME + ".trace.OtelSpanContext", - ROOT_PACKAGE_NAME + ".trace.OtelSpanLink", - ROOT_PACKAGE_NAME + ".trace.OtelSpanLink$1", - ROOT_PACKAGE_NAME + ".trace.OtelTracer", - ROOT_PACKAGE_NAME + ".trace.OtelTracerBuilder", - ROOT_PACKAGE_NAME + ".trace.OtelTracerProvider", + "datadog.opentelemetry.shim.context.OtelContext", + "datadog.opentelemetry.shim.context.OtelScope", + "datadog.opentelemetry.shim.trace.OtelExtractedContext", + "datadog.opentelemetry.shim.trace.OtelConventions", + "datadog.opentelemetry.shim.trace.OtelConventions$1", + "datadog.opentelemetry.shim.trace.OtelSpan", + "datadog.opentelemetry.shim.trace.OtelSpan$1", + "datadog.opentelemetry.shim.trace.OtelSpan$NoopSpan", + "datadog.opentelemetry.shim.trace.OtelSpan$NoopSpanContext", + "datadog.opentelemetry.shim.trace.OtelSpanBuilder", + "datadog.opentelemetry.shim.trace.OtelSpanBuilder$1", + "datadog.opentelemetry.shim.trace.OtelSpanContext", + "datadog.opentelemetry.shim.trace.OtelSpanLink", + "datadog.opentelemetry.shim.trace.OtelSpanLink$1", + "datadog.opentelemetry.shim.trace.OtelTracer", + "datadog.opentelemetry.shim.trace.OtelTracerBuilder", + "datadog.opentelemetry.shim.trace.OtelTracerProvider", }; } @@ -95,36 +90,7 @@ public void methodAdvice(MethodTransformer transformer) { public static class ContextStorageCurrentAdvice { @Advice.OnMethodExit(suppress = Throwable.class) public static void current(@Advice.Return(readOnly = false) Context result) { - // Check empty context - AgentSpan agentCurrentSpan = AgentTracer.activeSpan(); - if (null == agentCurrentSpan) { - result = OtelContext.ROOT; - return; - } - // Get OTel current span - Span otelCurrentSpan = null; - if (agentCurrentSpan instanceof AttachableWrapper) { - Object wrapper = ((AttachableWrapper) agentCurrentSpan).getWrapper(); - if (wrapper instanceof OtelSpan) { - otelCurrentSpan = (OtelSpan) wrapper; - } - } - if (otelCurrentSpan == null) { - otelCurrentSpan = new OtelSpan(agentCurrentSpan); - } - // Get OTel root span - Span otelRootSpan = null; - AgentSpan agentRootSpan = agentCurrentSpan.getLocalRootSpan(); - if (agentRootSpan instanceof AttachableWrapper) { - Object wrapper = ((AttachableWrapper) agentRootSpan).getWrapper(); - if (wrapper instanceof OtelSpan) { - otelRootSpan = (OtelSpan) wrapper; - } - } - if (otelRootSpan == null) { - otelRootSpan = new OtelSpan(agentRootSpan); - } - result = new OtelContext(otelCurrentSpan, otelRootSpan); + result = OtelContext.current(); } } } diff --git a/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/test/groovy/OpenTelemetry14ConventionsTest.groovy b/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/test/groovy/OpenTelemetry14ConventionsTest.groovy index 7f865d19a1b..d7d73f80726 100644 --- a/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/test/groovy/OpenTelemetry14ConventionsTest.groovy +++ b/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/test/groovy/OpenTelemetry14ConventionsTest.groovy @@ -6,9 +6,9 @@ import io.opentelemetry.context.ThreadLocalContextStorage import spock.lang.Subject import static datadog.trace.bootstrap.instrumentation.api.Tags.SPAN_KIND -import static datadog.trace.instrumentation.opentelemetry14.trace.OtelConventions.OPERATION_NAME_SPECIFIC_ATTRIBUTE -import static datadog.trace.instrumentation.opentelemetry14.trace.OtelConventions.SPAN_KIND_INTERNAL -import static datadog.trace.instrumentation.opentelemetry14.trace.OtelConventions.toSpanKindTagValue +import static datadog.opentelemetry.shim.trace.OtelConventions.OPERATION_NAME_SPECIFIC_ATTRIBUTE +import static datadog.opentelemetry.shim.trace.OtelConventions.SPAN_KIND_INTERNAL +import static datadog.opentelemetry.shim.trace.OtelConventions.toSpanKindTagValue import static io.opentelemetry.api.trace.SpanKind.CLIENT import static io.opentelemetry.api.trace.SpanKind.CONSUMER import static io.opentelemetry.api.trace.SpanKind.INTERNAL diff --git a/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/test/groovy/OpenTelemetry14Test.groovy b/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/test/groovy/OpenTelemetry14Test.groovy index 32f9ff4c683..322ad5a1b62 100644 --- a/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/test/groovy/OpenTelemetry14Test.groovy +++ b/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/test/groovy/OpenTelemetry14Test.groovy @@ -23,7 +23,7 @@ import static datadog.trace.bootstrap.instrumentation.api.Tags.SPAN_KIND_CLIENT import static datadog.trace.bootstrap.instrumentation.api.Tags.SPAN_KIND_CONSUMER import static datadog.trace.bootstrap.instrumentation.api.Tags.SPAN_KIND_PRODUCER import static datadog.trace.bootstrap.instrumentation.api.Tags.SPAN_KIND_SERVER -import static datadog.trace.instrumentation.opentelemetry14.trace.OtelConventions.SPAN_KIND_INTERNAL +import static datadog.opentelemetry.shim.trace.OtelConventions.SPAN_KIND_INTERNAL import static io.opentelemetry.api.trace.SpanKind.CLIENT import static io.opentelemetry.api.trace.SpanKind.CONSUMER import static io.opentelemetry.api.trace.SpanKind.INTERNAL diff --git a/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/test/groovy/opentelemetry14/context/ContextTest.groovy b/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/test/groovy/opentelemetry14/context/ContextTest.groovy index 64831e4ecd4..ab386e4b7e2 100644 --- a/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/test/groovy/opentelemetry14/context/ContextTest.groovy +++ b/dd-java-agent/instrumentation/opentelemetry/opentelemetry-1.4/src/test/groovy/opentelemetry14/context/ContextTest.groovy @@ -12,9 +12,9 @@ import spock.lang.Ignore import spock.lang.Subject import static datadog.trace.bootstrap.instrumentation.api.ScopeSource.MANUAL -import static datadog.trace.instrumentation.opentelemetry14.context.OtelContext.OTEL_CONTEXT_ROOT_SPAN_KEY -import static datadog.trace.instrumentation.opentelemetry14.context.OtelContext.OTEL_CONTEXT_SPAN_KEY -import static datadog.trace.instrumentation.opentelemetry14.trace.OtelConventions.SPAN_KIND_INTERNAL +import static datadog.opentelemetry.shim.context.OtelContext.OTEL_CONTEXT_ROOT_SPAN_KEY +import static datadog.opentelemetry.shim.context.OtelContext.OTEL_CONTEXT_SPAN_KEY +import static datadog.opentelemetry.shim.trace.OtelConventions.SPAN_KIND_INTERNAL class ContextTest extends AgentTestRunner { @Subject diff --git a/settings.gradle b/settings.gradle index e43ec454e67..928f116602d 100644 --- a/settings.gradle +++ b/settings.gradle @@ -60,6 +60,10 @@ include ':dd-java-agent:agent-debugger:debugger-el' include ':dd-java-agent:agent-crashtracking' +include ':dd-java-agent:agent-otel:otel-bootstrap' +include ':dd-java-agent:agent-otel:otel-shim' +include ':dd-java-agent:agent-otel:otel-tooling' + include ':communication' include ':telemetry' include ':remote-config' @@ -421,7 +425,7 @@ include ':dd-java-agent:instrumentation:testng' include ':dd-java-agent:instrumentation:testng:testng-6' include ':dd-java-agent:instrumentation:testng:testng-7' include ':dd-java-agent:instrumentation:thymeleaf' -include 'dd-java-agent:instrumentation:tinylog-2' +include ':dd-java-agent:instrumentation:tinylog-2' include ':dd-java-agent:instrumentation:tomcat-5.5' include ':dd-java-agent:instrumentation:tomcat-5.5-common' include ':dd-java-agent:instrumentation:tomcat-appsec-5.5'