Refactor Instrumenters into InstrumentationModules - R, S, T, V (#1576)
This commit is contained in:
parent
087a9cbc4e
commit
9d2db827b9
|
@ -22,7 +22,6 @@ import static net.bytebuddy.matcher.ElementMatchers.not;
|
|||
import static net.bytebuddy.matcher.ElementMatchers.takesArgument;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.takesArguments;
|
||||
|
||||
import com.google.auto.service.AutoService;
|
||||
import com.rabbitmq.client.AMQP;
|
||||
import com.rabbitmq.client.Channel;
|
||||
import com.rabbitmq.client.Consumer;
|
||||
|
@ -34,7 +33,7 @@ import io.opentelemetry.context.Context;
|
|||
import io.opentelemetry.context.Scope;
|
||||
import io.opentelemetry.javaagent.instrumentation.api.CallDepthThreadLocalMap;
|
||||
import io.opentelemetry.javaagent.instrumentation.api.Java8BytecodeBridge;
|
||||
import io.opentelemetry.javaagent.tooling.Instrumenter;
|
||||
import io.opentelemetry.javaagent.tooling.TypeInstrumentation;
|
||||
import java.io.IOException;
|
||||
import java.util.HashMap;
|
||||
import java.util.LinkedHashMap;
|
||||
|
@ -44,12 +43,7 @@ import net.bytebuddy.description.method.MethodDescription;
|
|||
import net.bytebuddy.description.type.TypeDescription;
|
||||
import net.bytebuddy.matcher.ElementMatcher;
|
||||
|
||||
@AutoService(Instrumenter.class)
|
||||
public class RabbitChannelInstrumentation extends Instrumenter.Default {
|
||||
|
||||
public RabbitChannelInstrumentation() {
|
||||
super("amqp", "rabbitmq");
|
||||
}
|
||||
final class RabbitChannelInstrumentation implements TypeInstrumentation {
|
||||
|
||||
@Override
|
||||
public ElementMatcher<ClassLoader> classLoaderMatcher() {
|
||||
|
@ -62,17 +56,6 @@ public class RabbitChannelInstrumentation extends Instrumenter.Default {
|
|||
return implementsInterface(named("com.rabbitmq.client.Channel"));
|
||||
}
|
||||
|
||||
@Override
|
||||
public String[] helperClassNames() {
|
||||
return new String[] {
|
||||
packageName + ".RabbitTracer",
|
||||
packageName + ".TextMapInjectAdapter",
|
||||
packageName + ".TextMapExtractAdapter",
|
||||
packageName + ".TracedDelegatingConsumer",
|
||||
RabbitCommandInstrumentation.class.getName() + "$SpanHolder",
|
||||
};
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
// We want the advice applied in a specific order, so use an ordered map.
|
||||
|
|
|
@ -13,22 +13,16 @@ import static java.util.Collections.singletonMap;
|
|||
import static net.bytebuddy.matcher.ElementMatchers.isConstructor;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.named;
|
||||
|
||||
import com.google.auto.service.AutoService;
|
||||
import com.rabbitmq.client.Command;
|
||||
import io.opentelemetry.api.trace.Span;
|
||||
import io.opentelemetry.javaagent.tooling.Instrumenter;
|
||||
import io.opentelemetry.javaagent.tooling.TypeInstrumentation;
|
||||
import java.util.Map;
|
||||
import net.bytebuddy.asm.Advice;
|
||||
import net.bytebuddy.description.method.MethodDescription;
|
||||
import net.bytebuddy.description.type.TypeDescription;
|
||||
import net.bytebuddy.matcher.ElementMatcher;
|
||||
|
||||
@AutoService(Instrumenter.class)
|
||||
public class RabbitCommandInstrumentation extends Instrumenter.Default {
|
||||
|
||||
public RabbitCommandInstrumentation() {
|
||||
super("amqp", "rabbitmq");
|
||||
}
|
||||
final class RabbitCommandInstrumentation implements TypeInstrumentation {
|
||||
|
||||
@Override
|
||||
public ElementMatcher<ClassLoader> classLoaderMatcher() {
|
||||
|
@ -41,17 +35,6 @@ public class RabbitCommandInstrumentation extends Instrumenter.Default {
|
|||
return implementsInterface(named("com.rabbitmq.client.Command"));
|
||||
}
|
||||
|
||||
@Override
|
||||
public String[] helperClassNames() {
|
||||
return new String[] {
|
||||
packageName + ".RabbitTracer",
|
||||
// These are only used by muzzleCheck:
|
||||
packageName + ".TextMapExtractAdapter",
|
||||
packageName + ".TracedDelegatingConsumer",
|
||||
RabbitCommandInstrumentation.class.getName() + "$SpanHolder"
|
||||
};
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
return singletonMap(
|
||||
|
@ -72,14 +55,5 @@ public class RabbitCommandInstrumentation extends Instrumenter.Default {
|
|||
tracer().onCommand(span, command);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* This instrumentation will match with 2.6, but the channel instrumentation only matches with
|
||||
* 2.7 because of TracedDelegatingConsumer. This unused method is added to ensure consistent
|
||||
* muzzle validation by preventing match with 2.6.
|
||||
*/
|
||||
public static void muzzleCheck(TracedDelegatingConsumer consumer) {
|
||||
consumer.handleRecoverOk(null);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -0,0 +1,36 @@
|
|||
/*
|
||||
* Copyright The OpenTelemetry Authors
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
|
||||
package io.opentelemetry.javaagent.instrumentation.rabbitmq.amqp;
|
||||
|
||||
import static java.util.Arrays.asList;
|
||||
|
||||
import com.google.auto.service.AutoService;
|
||||
import io.opentelemetry.javaagent.tooling.InstrumentationModule;
|
||||
import io.opentelemetry.javaagent.tooling.TypeInstrumentation;
|
||||
import java.util.List;
|
||||
|
||||
@AutoService(InstrumentationModule.class)
|
||||
public class RabbitMqInstrumentationModule extends InstrumentationModule {
|
||||
public RabbitMqInstrumentationModule() {
|
||||
super("amqp", "rabbitmq");
|
||||
}
|
||||
|
||||
@Override
|
||||
public String[] helperClassNames() {
|
||||
return new String[] {
|
||||
packageName + ".RabbitTracer",
|
||||
packageName + ".TextMapInjectAdapter",
|
||||
packageName + ".TextMapExtractAdapter",
|
||||
packageName + ".TracedDelegatingConsumer",
|
||||
RabbitCommandInstrumentation.class.getName() + "$SpanHolder",
|
||||
};
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<TypeInstrumentation> typeInstrumentations() {
|
||||
return asList(new RabbitChannelInstrumentation(), new RabbitCommandInstrumentation());
|
||||
}
|
||||
}
|
|
@ -12,22 +12,15 @@ import static net.bytebuddy.matcher.ElementMatchers.nameStartsWith;
|
|||
import static net.bytebuddy.matcher.ElementMatchers.named;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.takesArgument;
|
||||
|
||||
import com.google.auto.service.AutoService;
|
||||
import io.opentelemetry.javaagent.tooling.Instrumenter;
|
||||
import io.opentelemetry.javaagent.tooling.TypeInstrumentation;
|
||||
import java.util.Map;
|
||||
import net.bytebuddy.asm.Advice;
|
||||
import net.bytebuddy.description.method.MethodDescription;
|
||||
import net.bytebuddy.description.type.TypeDescription;
|
||||
import net.bytebuddy.matcher.ElementMatcher;
|
||||
import ratpack.func.Block;
|
||||
import ratpack.path.PathBinding;
|
||||
|
||||
@AutoService(Instrumenter.class)
|
||||
public final class ContinuationInstrumentation extends Instrumenter.Default {
|
||||
|
||||
public ContinuationInstrumentation() {
|
||||
super("ratpack");
|
||||
}
|
||||
final class ContinuationInstrumentation implements TypeInstrumentation {
|
||||
|
||||
@Override
|
||||
public ElementMatcher<ClassLoader> classLoaderMatcher() {
|
||||
|
@ -41,11 +34,6 @@ public final class ContinuationInstrumentation extends Instrumenter.Default {
|
|||
.<TypeDescription>and(implementsInterface(named("ratpack.exec.internal.Continuation")));
|
||||
}
|
||||
|
||||
@Override
|
||||
public String[] helperClassNames() {
|
||||
return new String[] {packageName + ".BlockWrapper"};
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
return singletonMap(
|
||||
|
@ -59,10 +47,5 @@ public final class ContinuationInstrumentation extends Instrumenter.Default {
|
|||
public static void wrap(@Advice.Argument(value = 0, readOnly = false) Block block) {
|
||||
block = BlockWrapper.wrapIfNeeded(block);
|
||||
}
|
||||
|
||||
public void muzzleCheck(PathBinding binding) {
|
||||
// This was added in 1.4. Added here to ensure consistency with other instrumentation.
|
||||
binding.getDescription();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -10,8 +10,7 @@ import static net.bytebuddy.matcher.ElementMatchers.nameStartsWith;
|
|||
import static net.bytebuddy.matcher.ElementMatchers.named;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.takesArgument;
|
||||
|
||||
import com.google.auto.service.AutoService;
|
||||
import io.opentelemetry.javaagent.tooling.Instrumenter;
|
||||
import io.opentelemetry.javaagent.tooling.TypeInstrumentation;
|
||||
import java.util.Map;
|
||||
import net.bytebuddy.asm.Advice;
|
||||
import net.bytebuddy.description.method.MethodDescription;
|
||||
|
@ -19,25 +18,14 @@ import net.bytebuddy.description.type.TypeDescription;
|
|||
import net.bytebuddy.matcher.ElementMatcher;
|
||||
import ratpack.exec.internal.Continuation;
|
||||
import ratpack.func.Action;
|
||||
import ratpack.path.PathBinding;
|
||||
|
||||
@AutoService(Instrumenter.class)
|
||||
public final class DefaultExecutionInstrumentation extends Instrumenter.Default {
|
||||
|
||||
public DefaultExecutionInstrumentation() {
|
||||
super("ratpack");
|
||||
}
|
||||
final class DefaultExecutionInstrumentation implements TypeInstrumentation {
|
||||
|
||||
@Override
|
||||
public ElementMatcher<? super TypeDescription> typeMatcher() {
|
||||
return named("ratpack.exec.internal.DefaultExecution");
|
||||
}
|
||||
|
||||
@Override
|
||||
public String[] helperClassNames() {
|
||||
return new String[] {packageName + ".ActionWrapper"};
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
return singletonMap(
|
||||
|
@ -56,10 +44,5 @@ public final class DefaultExecutionInstrumentation extends Instrumenter.Default
|
|||
onError = ActionWrapper.wrapIfNeeded(onError);
|
||||
segment = ActionWrapper.wrapIfNeeded(segment);
|
||||
}
|
||||
|
||||
public void muzzleCheck(PathBinding binding) {
|
||||
// This was added in 1.4. Added here to ensure consistency with other instrumentation.
|
||||
binding.getDescription();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -0,0 +1,39 @@
|
|||
/*
|
||||
* Copyright The OpenTelemetry Authors
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
|
||||
package io.opentelemetry.javaagent.instrumentation.ratpack;
|
||||
|
||||
import static java.util.Arrays.asList;
|
||||
|
||||
import com.google.auto.service.AutoService;
|
||||
import io.opentelemetry.javaagent.tooling.InstrumentationModule;
|
||||
import io.opentelemetry.javaagent.tooling.TypeInstrumentation;
|
||||
import java.util.List;
|
||||
|
||||
@AutoService(InstrumentationModule.class)
|
||||
public class RatpackInstrumentationModule extends InstrumentationModule {
|
||||
public RatpackInstrumentationModule() {
|
||||
super("ratpack");
|
||||
}
|
||||
|
||||
@Override
|
||||
public String[] helperClassNames() {
|
||||
return new String[] {
|
||||
packageName + ".ActionWrapper",
|
||||
packageName + ".BlockWrapper",
|
||||
packageName + ".RatpackTracer",
|
||||
packageName + ".TracingHandler",
|
||||
};
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<TypeInstrumentation> typeInstrumentations() {
|
||||
return asList(
|
||||
new ContinuationInstrumentation(),
|
||||
new DefaultExecutionInstrumentation(),
|
||||
new ServerErrorHandlerInstrumentation(),
|
||||
new ServerRegistryInstrumentation());
|
||||
}
|
||||
}
|
|
@ -13,19 +13,13 @@ import static net.bytebuddy.matcher.ElementMatchers.named;
|
|||
import static net.bytebuddy.matcher.ElementMatchers.not;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.takesArgument;
|
||||
|
||||
import com.google.auto.service.AutoService;
|
||||
import io.opentelemetry.javaagent.tooling.Instrumenter;
|
||||
import io.opentelemetry.javaagent.tooling.TypeInstrumentation;
|
||||
import java.util.Map;
|
||||
import net.bytebuddy.description.method.MethodDescription;
|
||||
import net.bytebuddy.description.type.TypeDescription;
|
||||
import net.bytebuddy.matcher.ElementMatcher;
|
||||
|
||||
@AutoService(Instrumenter.class)
|
||||
public class ServerErrorHandlerInstrumentation extends Instrumenter.Default {
|
||||
|
||||
public ServerErrorHandlerInstrumentation() {
|
||||
super("ratpack");
|
||||
}
|
||||
final class ServerErrorHandlerInstrumentation implements TypeInstrumentation {
|
||||
|
||||
@Override
|
||||
public ElementMatcher<ClassLoader> classLoaderMatcher() {
|
||||
|
@ -38,19 +32,12 @@ public class ServerErrorHandlerInstrumentation extends Instrumenter.Default {
|
|||
return not(isAbstract()).and(implementsInterface(named("ratpack.error.ServerErrorHandler")));
|
||||
}
|
||||
|
||||
@Override
|
||||
public String[] helperClassNames() {
|
||||
return new String[] {
|
||||
packageName + ".RatpackTracer",
|
||||
};
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
return singletonMap(
|
||||
named("error")
|
||||
.and(takesArgument(0, named("ratpack.handling.Context")))
|
||||
.and(takesArgument(1, Throwable.class)),
|
||||
packageName + ".ErrorHandlerAdvice");
|
||||
ErrorHandlerAdvice.class.getName());
|
||||
}
|
||||
}
|
||||
|
|
|
@ -10,36 +10,23 @@ import static net.bytebuddy.matcher.ElementMatchers.isMethod;
|
|||
import static net.bytebuddy.matcher.ElementMatchers.isStatic;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.named;
|
||||
|
||||
import com.google.auto.service.AutoService;
|
||||
import io.opentelemetry.javaagent.tooling.Instrumenter;
|
||||
import io.opentelemetry.javaagent.tooling.TypeInstrumentation;
|
||||
import java.util.Map;
|
||||
import net.bytebuddy.description.method.MethodDescription;
|
||||
import net.bytebuddy.description.type.TypeDescription;
|
||||
import net.bytebuddy.matcher.ElementMatcher;
|
||||
|
||||
@AutoService(Instrumenter.class)
|
||||
public class ServerRegistryInstrumentation extends Instrumenter.Default {
|
||||
|
||||
public ServerRegistryInstrumentation() {
|
||||
super("ratpack");
|
||||
}
|
||||
final class ServerRegistryInstrumentation implements TypeInstrumentation {
|
||||
|
||||
@Override
|
||||
public ElementMatcher<TypeDescription> typeMatcher() {
|
||||
return named("ratpack.server.internal.ServerRegistry");
|
||||
}
|
||||
|
||||
@Override
|
||||
public String[] helperClassNames() {
|
||||
return new String[] {
|
||||
packageName + ".RatpackTracer", packageName + ".TracingHandler",
|
||||
};
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
return singletonMap(
|
||||
isMethod().and(isStatic()).and(named("buildBaseRegistry")),
|
||||
packageName + ".ServerRegistryAdvice");
|
||||
ServerRegistryAdvice.class.getName());
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,45 +0,0 @@
|
|||
/*
|
||||
* Copyright The OpenTelemetry Authors
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
|
||||
package io.opentelemetry.javaagent.instrumentation.reactor;
|
||||
|
||||
import static java.util.Collections.singletonMap;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.isTypeInitializer;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.named;
|
||||
|
||||
import com.google.auto.service.AutoService;
|
||||
import io.opentelemetry.javaagent.tooling.Instrumenter;
|
||||
import java.util.Map;
|
||||
import net.bytebuddy.description.method.MethodDescription;
|
||||
import net.bytebuddy.description.type.TypeDescription;
|
||||
import net.bytebuddy.matcher.ElementMatcher;
|
||||
|
||||
@AutoService(Instrumenter.class)
|
||||
public final class ReactorHooksInstrumentation extends Instrumenter.Default {
|
||||
|
||||
public ReactorHooksInstrumentation() {
|
||||
super("reactor-core");
|
||||
}
|
||||
|
||||
@Override
|
||||
public String[] helperClassNames() {
|
||||
return new String[] {
|
||||
"io.opentelemetry.instrumentation.reactor.TracingOperator$Lifter",
|
||||
"io.opentelemetry.instrumentation.reactor.TracingOperator",
|
||||
"io.opentelemetry.instrumentation.reactor.TracingSubscriber"
|
||||
};
|
||||
}
|
||||
|
||||
@Override
|
||||
public ElementMatcher<TypeDescription> typeMatcher() {
|
||||
return named("reactor.core.publisher.Hooks");
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
return singletonMap(
|
||||
isTypeInitializer().or(named("resetOnEachOperator")), packageName + ".ReactorHooksAdvice");
|
||||
}
|
||||
}
|
|
@ -0,0 +1,55 @@
|
|||
/*
|
||||
* Copyright The OpenTelemetry Authors
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
|
||||
package io.opentelemetry.javaagent.instrumentation.reactor;
|
||||
|
||||
import static java.util.Collections.singletonList;
|
||||
import static java.util.Collections.singletonMap;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.isTypeInitializer;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.named;
|
||||
|
||||
import com.google.auto.service.AutoService;
|
||||
import io.opentelemetry.javaagent.tooling.InstrumentationModule;
|
||||
import io.opentelemetry.javaagent.tooling.TypeInstrumentation;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import net.bytebuddy.description.method.MethodDescription;
|
||||
import net.bytebuddy.description.type.TypeDescription;
|
||||
import net.bytebuddy.matcher.ElementMatcher;
|
||||
|
||||
@AutoService(InstrumentationModule.class)
|
||||
public final class ReactorInstrumentationModule extends InstrumentationModule {
|
||||
|
||||
public ReactorInstrumentationModule() {
|
||||
super("reactor-core");
|
||||
}
|
||||
|
||||
@Override
|
||||
public String[] helperClassNames() {
|
||||
return new String[] {
|
||||
"io.opentelemetry.instrumentation.reactor.TracingOperator$Lifter",
|
||||
"io.opentelemetry.instrumentation.reactor.TracingOperator",
|
||||
"io.opentelemetry.instrumentation.reactor.TracingSubscriber"
|
||||
};
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<TypeInstrumentation> typeInstrumentations() {
|
||||
return singletonList(new HooksInstrumentation());
|
||||
}
|
||||
|
||||
private static final class HooksInstrumentation implements TypeInstrumentation {
|
||||
@Override
|
||||
public ElementMatcher<TypeDescription> typeMatcher() {
|
||||
return named("reactor.core.publisher.Hooks");
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
return singletonMap(
|
||||
isTypeInitializer().or(named("resetOnEachOperator")), ReactorHooksAdvice.class.getName());
|
||||
}
|
||||
}
|
||||
}
|
|
@ -9,6 +9,7 @@ import static io.opentelemetry.javaagent.instrumentation.rediscala.RediscalaClie
|
|||
import static io.opentelemetry.javaagent.tooling.ClassLoaderMatcher.hasClassesNamed;
|
||||
import static io.opentelemetry.javaagent.tooling.bytebuddy.matcher.AgentElementMatchers.safeHasSuperType;
|
||||
import static io.opentelemetry.javaagent.tooling.matcher.NameMatchers.namedOneOf;
|
||||
import static java.util.Collections.singletonList;
|
||||
import static java.util.Collections.singletonMap;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.isMethod;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.isPublic;
|
||||
|
@ -19,7 +20,9 @@ import static net.bytebuddy.matcher.ElementMatchers.takesArgument;
|
|||
import com.google.auto.service.AutoService;
|
||||
import io.opentelemetry.api.trace.Span;
|
||||
import io.opentelemetry.context.Scope;
|
||||
import io.opentelemetry.javaagent.tooling.Instrumenter;
|
||||
import io.opentelemetry.javaagent.tooling.InstrumentationModule;
|
||||
import io.opentelemetry.javaagent.tooling.TypeInstrumentation;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import net.bytebuddy.asm.Advice;
|
||||
import net.bytebuddy.description.method.MethodDescription;
|
||||
|
@ -31,52 +34,59 @@ import scala.concurrent.Future;
|
|||
import scala.runtime.AbstractFunction1;
|
||||
import scala.util.Try;
|
||||
|
||||
@AutoService(Instrumenter.class)
|
||||
public final class RediscalaInstrumentation extends Instrumenter.Default {
|
||||
@AutoService(InstrumentationModule.class)
|
||||
public final class RediscalaInstrumentationModule extends InstrumentationModule {
|
||||
|
||||
public RediscalaInstrumentation() {
|
||||
public RediscalaInstrumentationModule() {
|
||||
super("rediscala", "redis");
|
||||
}
|
||||
|
||||
@Override
|
||||
public ElementMatcher<ClassLoader> classLoaderMatcher() {
|
||||
return hasClassesNamed("redis.Request");
|
||||
}
|
||||
|
||||
@Override
|
||||
public ElementMatcher<TypeDescription> typeMatcher() {
|
||||
return safeHasSuperType(
|
||||
namedOneOf(
|
||||
"redis.ActorRequest",
|
||||
"redis.Request",
|
||||
"redis.BufferedRequest",
|
||||
"redis.RoundRobinPoolRequest"));
|
||||
}
|
||||
|
||||
@Override
|
||||
public String[] helperClassNames() {
|
||||
return new String[] {
|
||||
RediscalaInstrumentation.class.getName() + "$OnCompleteHandler",
|
||||
RediscalaInstrumentationModule.class.getName() + "$OnCompleteHandler",
|
||||
packageName + ".RediscalaClientTracer",
|
||||
};
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
return singletonMap(
|
||||
isMethod()
|
||||
.and(isPublic())
|
||||
.and(named("send"))
|
||||
.and(takesArgument(0, named("redis.RedisCommand")))
|
||||
.and(returns(named("scala.concurrent.Future"))),
|
||||
RediscalaInstrumentation.class.getName() + "$RediscalaAdvice");
|
||||
public List<TypeInstrumentation> typeInstrumentations() {
|
||||
return singletonList(new RequestInstrumentation());
|
||||
}
|
||||
|
||||
private static final class RequestInstrumentation implements TypeInstrumentation {
|
||||
@Override
|
||||
public ElementMatcher<ClassLoader> classLoaderMatcher() {
|
||||
return hasClassesNamed("redis.Request");
|
||||
}
|
||||
|
||||
@Override
|
||||
public ElementMatcher<TypeDescription> typeMatcher() {
|
||||
return safeHasSuperType(
|
||||
namedOneOf(
|
||||
"redis.ActorRequest",
|
||||
"redis.Request",
|
||||
"redis.BufferedRequest",
|
||||
"redis.RoundRobinPoolRequest"));
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
return singletonMap(
|
||||
isMethod()
|
||||
.and(isPublic())
|
||||
.and(named("send"))
|
||||
.and(takesArgument(0, named("redis.RedisCommand")))
|
||||
.and(returns(named("scala.concurrent.Future"))),
|
||||
RediscalaInstrumentationModule.class.getName() + "$RediscalaAdvice");
|
||||
}
|
||||
}
|
||||
|
||||
public static class RediscalaAdvice {
|
||||
|
||||
@Advice.OnMethodEnter(suppress = Throwable.class)
|
||||
public static void onEnter(
|
||||
@Advice.Argument(0) RedisCommand cmd,
|
||||
@Advice.Argument(0) RedisCommand<?, ?> cmd,
|
||||
@Advice.Local("otelSpan") Span span,
|
||||
@Advice.Local("otelScope") Scope scope) {
|
||||
span = tracer().startSpan(cmd, cmd);
|
|
@ -6,6 +6,7 @@
|
|||
package io.opentelemetry.javaagent.instrumentation.redisson;
|
||||
|
||||
import static io.opentelemetry.javaagent.instrumentation.redisson.RedissonClientTracer.tracer;
|
||||
import static java.util.Collections.singletonList;
|
||||
import static java.util.Collections.singletonMap;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.isMethod;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.named;
|
||||
|
@ -13,7 +14,9 @@ import static net.bytebuddy.matcher.ElementMatchers.named;
|
|||
import com.google.auto.service.AutoService;
|
||||
import io.opentelemetry.api.trace.Span;
|
||||
import io.opentelemetry.context.Scope;
|
||||
import io.opentelemetry.javaagent.tooling.Instrumenter;
|
||||
import io.opentelemetry.javaagent.tooling.InstrumentationModule;
|
||||
import io.opentelemetry.javaagent.tooling.TypeInstrumentation;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import net.bytebuddy.asm.Advice;
|
||||
import net.bytebuddy.description.method.MethodDescription;
|
||||
|
@ -21,27 +24,35 @@ import net.bytebuddy.description.type.TypeDescription;
|
|||
import net.bytebuddy.matcher.ElementMatcher;
|
||||
import org.redisson.client.RedisConnection;
|
||||
|
||||
@AutoService(Instrumenter.class)
|
||||
public final class RedissonInstrumentation extends Instrumenter.Default {
|
||||
@AutoService(InstrumentationModule.class)
|
||||
public final class RedissonInstrumentation extends InstrumentationModule {
|
||||
|
||||
public RedissonInstrumentation() {
|
||||
super("redisson", "redis");
|
||||
}
|
||||
|
||||
@Override
|
||||
public ElementMatcher<TypeDescription> typeMatcher() {
|
||||
return named("org.redisson.client.RedisConnection");
|
||||
}
|
||||
|
||||
@Override
|
||||
public String[] helperClassNames() {
|
||||
return new String[] {packageName + ".RedissonClientTracer"};
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
return singletonMap(
|
||||
isMethod().and(named("send")), RedissonInstrumentation.class.getName() + "$RedissonAdvice");
|
||||
public List<TypeInstrumentation> typeInstrumentations() {
|
||||
return singletonList(new RedisConnectionInstrumentation());
|
||||
}
|
||||
|
||||
private static final class RedisConnectionInstrumentation implements TypeInstrumentation {
|
||||
@Override
|
||||
public ElementMatcher<TypeDescription> typeMatcher() {
|
||||
return named("org.redisson.client.RedisConnection");
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
return singletonMap(
|
||||
isMethod().and(named("send")),
|
||||
RedissonInstrumentation.class.getName() + "$RedissonAdvice");
|
||||
}
|
||||
}
|
||||
|
||||
public static class RedissonAdvice {
|
||||
|
|
|
@ -7,6 +7,7 @@ package io.opentelemetry.javaagent.instrumentation.rmi.client;
|
|||
|
||||
import static io.opentelemetry.javaagent.instrumentation.rmi.client.RmiClientTracer.tracer;
|
||||
import static io.opentelemetry.javaagent.tooling.bytebuddy.matcher.AgentElementMatchers.extendsClass;
|
||||
import static java.util.Collections.singletonList;
|
||||
import static java.util.Collections.singletonMap;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.isMethod;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.named;
|
||||
|
@ -16,39 +17,48 @@ import com.google.auto.service.AutoService;
|
|||
import io.opentelemetry.api.trace.Span;
|
||||
import io.opentelemetry.context.Scope;
|
||||
import io.opentelemetry.javaagent.instrumentation.api.Java8BytecodeBridge;
|
||||
import io.opentelemetry.javaagent.tooling.Instrumenter;
|
||||
import io.opentelemetry.javaagent.tooling.InstrumentationModule;
|
||||
import io.opentelemetry.javaagent.tooling.TypeInstrumentation;
|
||||
import java.lang.reflect.Method;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import net.bytebuddy.asm.Advice;
|
||||
import net.bytebuddy.description.method.MethodDescription;
|
||||
import net.bytebuddy.description.type.TypeDescription;
|
||||
import net.bytebuddy.matcher.ElementMatcher;
|
||||
|
||||
@AutoService(Instrumenter.class)
|
||||
public final class RmiClientInstrumentation extends Instrumenter.Default {
|
||||
@AutoService(InstrumentationModule.class)
|
||||
public final class RmiClientInstrumentationModule extends InstrumentationModule {
|
||||
|
||||
public RmiClientInstrumentation() {
|
||||
public RmiClientInstrumentationModule() {
|
||||
super("rmi", "rmi-client");
|
||||
}
|
||||
|
||||
@Override
|
||||
public ElementMatcher<TypeDescription> typeMatcher() {
|
||||
return extendsClass(named("sun.rmi.server.UnicastRef"));
|
||||
}
|
||||
|
||||
@Override
|
||||
public String[] helperClassNames() {
|
||||
return new String[] {packageName + ".RmiClientTracer"};
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
return singletonMap(
|
||||
isMethod()
|
||||
.and(named("invoke"))
|
||||
.and(takesArgument(0, named("java.rmi.Remote")))
|
||||
.and(takesArgument(1, named("java.lang.reflect.Method"))),
|
||||
getClass().getName() + "$RmiClientAdvice");
|
||||
public List<TypeInstrumentation> typeInstrumentations() {
|
||||
return singletonList(new ClientInstrumentation());
|
||||
}
|
||||
|
||||
private static final class ClientInstrumentation implements TypeInstrumentation {
|
||||
@Override
|
||||
public ElementMatcher<TypeDescription> typeMatcher() {
|
||||
return extendsClass(named("sun.rmi.server.UnicastRef"));
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
return singletonMap(
|
||||
isMethod()
|
||||
.and(named("invoke"))
|
||||
.and(takesArgument(0, named("java.rmi.Remote")))
|
||||
.and(takesArgument(1, named("java.lang.reflect.Method"))),
|
||||
RmiClientInstrumentationModule.class.getName() + "$RmiClientAdvice");
|
||||
}
|
||||
}
|
||||
|
||||
public static class RmiClientAdvice {
|
|
@ -0,0 +1,47 @@
|
|||
/*
|
||||
* Copyright The OpenTelemetry Authors
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
|
||||
package io.opentelemetry.javaagent.instrumentation.rmi.context;
|
||||
|
||||
import static java.util.Arrays.asList;
|
||||
import static java.util.Collections.singletonMap;
|
||||
|
||||
import com.google.auto.service.AutoService;
|
||||
import io.opentelemetry.javaagent.instrumentation.rmi.context.client.RmiClientContextInstrumentation;
|
||||
import io.opentelemetry.javaagent.instrumentation.rmi.context.server.RmiServerContextInstrumentation;
|
||||
import io.opentelemetry.javaagent.tooling.InstrumentationModule;
|
||||
import io.opentelemetry.javaagent.tooling.TypeInstrumentation;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
||||
@AutoService(InstrumentationModule.class)
|
||||
public class RmiContextPropagationInstrumentationModule extends InstrumentationModule {
|
||||
public RmiContextPropagationInstrumentationModule() {
|
||||
super("rmi", "rmi-context-propagator");
|
||||
}
|
||||
|
||||
@Override
|
||||
public String[] helperClassNames() {
|
||||
return new String[] {
|
||||
"io.opentelemetry.javaagent.instrumentation.rmi.context.ContextPayload$InjectAdapter",
|
||||
"io.opentelemetry.javaagent.instrumentation.rmi.context.ContextPayload$ExtractAdapter",
|
||||
"io.opentelemetry.javaagent.instrumentation.rmi.context.ContextPayload",
|
||||
"io.opentelemetry.javaagent.instrumentation.rmi.context.ContextPropagator",
|
||||
"io.opentelemetry.javaagent.instrumentation.rmi.context.server.ContextDispatcher",
|
||||
"io.opentelemetry.javaagent.instrumentation.rmi.context.server.ContextDispatcher$NoopRemote"
|
||||
};
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<TypeInstrumentation> typeInstrumentations() {
|
||||
return asList(new RmiClientContextInstrumentation(), new RmiServerContextInstrumentation());
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<String, String> contextStore() {
|
||||
// caching if a connection can support enhanced format
|
||||
return singletonMap("sun.rmi.transport.Connection", "java.lang.Boolean");
|
||||
}
|
||||
}
|
|
@ -12,12 +12,11 @@ import static net.bytebuddy.matcher.ElementMatchers.isConstructor;
|
|||
import static net.bytebuddy.matcher.ElementMatchers.named;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.takesArgument;
|
||||
|
||||
import com.google.auto.service.AutoService;
|
||||
import io.opentelemetry.api.trace.Span;
|
||||
import io.opentelemetry.javaagent.instrumentation.api.ContextStore;
|
||||
import io.opentelemetry.javaagent.instrumentation.api.InstrumentationContext;
|
||||
import io.opentelemetry.javaagent.instrumentation.api.Java8BytecodeBridge;
|
||||
import io.opentelemetry.javaagent.tooling.Instrumenter;
|
||||
import io.opentelemetry.javaagent.tooling.TypeInstrumentation;
|
||||
import java.rmi.server.ObjID;
|
||||
import java.util.Map;
|
||||
import net.bytebuddy.asm.Advice;
|
||||
|
@ -47,34 +46,13 @@ import sun.rmi.transport.Connection;
|
|||
* that instruction will essentially be garbage data and will cause the parsing loop to throw
|
||||
* exception and shutdown the connection which we do not want
|
||||
*/
|
||||
@AutoService(Instrumenter.class)
|
||||
public class RmiClientContextInstrumentation extends Instrumenter.Default {
|
||||
|
||||
public RmiClientContextInstrumentation() {
|
||||
super("rmi", "rmi-context-propagator", "rmi-client-context-propagator");
|
||||
}
|
||||
public final class RmiClientContextInstrumentation implements TypeInstrumentation {
|
||||
|
||||
@Override
|
||||
public ElementMatcher<? super TypeDescription> typeMatcher() {
|
||||
return extendsClass(named("sun.rmi.transport.StreamRemoteCall"));
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<String, String> contextStore() {
|
||||
// caching if a connection can support enhanced format
|
||||
return singletonMap("sun.rmi.transport.Connection", "java.lang.Boolean");
|
||||
}
|
||||
|
||||
@Override
|
||||
public String[] helperClassNames() {
|
||||
return new String[] {
|
||||
"io.opentelemetry.javaagent.instrumentation.rmi.context.ContextPayload$InjectAdapter",
|
||||
"io.opentelemetry.javaagent.instrumentation.rmi.context.ContextPayload$ExtractAdapter",
|
||||
"io.opentelemetry.javaagent.instrumentation.rmi.context.ContextPayload",
|
||||
"io.opentelemetry.javaagent.instrumentation.rmi.context.ContextPropagator"
|
||||
};
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
return singletonMap(
|
||||
|
|
|
@ -13,8 +13,7 @@ import static net.bytebuddy.matcher.ElementMatchers.isStatic;
|
|||
import static net.bytebuddy.matcher.ElementMatchers.named;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.takesArgument;
|
||||
|
||||
import com.google.auto.service.AutoService;
|
||||
import io.opentelemetry.javaagent.tooling.Instrumenter;
|
||||
import io.opentelemetry.javaagent.tooling.TypeInstrumentation;
|
||||
import java.util.Map;
|
||||
import net.bytebuddy.asm.Advice;
|
||||
import net.bytebuddy.description.method.MethodDescription;
|
||||
|
@ -22,30 +21,13 @@ import net.bytebuddy.description.type.TypeDescription;
|
|||
import net.bytebuddy.matcher.ElementMatcher;
|
||||
import sun.rmi.transport.Target;
|
||||
|
||||
@AutoService(Instrumenter.class)
|
||||
public class RmiServerContextInstrumentation extends Instrumenter.Default {
|
||||
|
||||
public RmiServerContextInstrumentation() {
|
||||
super("rmi", "rmi-context-propagator", "rmi-server-context-propagator");
|
||||
}
|
||||
public final class RmiServerContextInstrumentation implements TypeInstrumentation {
|
||||
|
||||
@Override
|
||||
public ElementMatcher<? super TypeDescription> typeMatcher() {
|
||||
return extendsClass(named("sun.rmi.transport.ObjectTable"));
|
||||
}
|
||||
|
||||
@Override
|
||||
public String[] helperClassNames() {
|
||||
return new String[] {
|
||||
"io.opentelemetry.javaagent.instrumentation.rmi.context.ContextPayload$InjectAdapter",
|
||||
"io.opentelemetry.javaagent.instrumentation.rmi.context.ContextPayload$ExtractAdapter",
|
||||
"io.opentelemetry.javaagent.instrumentation.rmi.context.ContextPayload",
|
||||
"io.opentelemetry.javaagent.instrumentation.rmi.context.ContextPropagator",
|
||||
packageName + ".ContextDispatcher",
|
||||
packageName + ".ContextDispatcher$NoopRemote"
|
||||
};
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
return singletonMap(
|
||||
|
|
|
@ -8,6 +8,7 @@ package io.opentelemetry.javaagent.instrumentation.rmi.server;
|
|||
import static io.opentelemetry.javaagent.instrumentation.api.rmi.ThreadLocalContext.THREAD_LOCAL_CONTEXT;
|
||||
import static io.opentelemetry.javaagent.instrumentation.rmi.server.RmiServerTracer.tracer;
|
||||
import static io.opentelemetry.javaagent.tooling.bytebuddy.matcher.AgentElementMatchers.extendsClass;
|
||||
import static java.util.Collections.singletonList;
|
||||
import static java.util.Collections.singletonMap;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.isMethod;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.isPublic;
|
||||
|
@ -20,17 +21,19 @@ import io.opentelemetry.api.trace.Span;
|
|||
import io.opentelemetry.context.Context;
|
||||
import io.opentelemetry.context.Scope;
|
||||
import io.opentelemetry.javaagent.instrumentation.api.CallDepthThreadLocalMap;
|
||||
import io.opentelemetry.javaagent.tooling.Instrumenter;
|
||||
import io.opentelemetry.javaagent.tooling.InstrumentationModule;
|
||||
import io.opentelemetry.javaagent.tooling.TypeInstrumentation;
|
||||
import java.lang.reflect.Method;
|
||||
import java.rmi.server.RemoteServer;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import net.bytebuddy.asm.Advice;
|
||||
import net.bytebuddy.description.method.MethodDescription;
|
||||
import net.bytebuddy.description.type.TypeDescription;
|
||||
import net.bytebuddy.matcher.ElementMatcher;
|
||||
|
||||
@AutoService(Instrumenter.class)
|
||||
public final class RmiServerInstrumentation extends Instrumenter.Default {
|
||||
@AutoService(InstrumentationModule.class)
|
||||
public final class RmiServerInstrumentation extends InstrumentationModule {
|
||||
|
||||
public RmiServerInstrumentation() {
|
||||
super("rmi", "rmi-server");
|
||||
|
@ -42,14 +45,22 @@ public final class RmiServerInstrumentation extends Instrumenter.Default {
|
|||
}
|
||||
|
||||
@Override
|
||||
public ElementMatcher<TypeDescription> typeMatcher() {
|
||||
return extendsClass(named("java.rmi.server.RemoteServer"));
|
||||
public List<TypeInstrumentation> typeInstrumentations() {
|
||||
return singletonList(new ServerInstrumentation());
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
return singletonMap(
|
||||
isMethod().and(isPublic()).and(not(isStatic())), getClass().getName() + "$ServerAdvice");
|
||||
private static final class ServerInstrumentation implements TypeInstrumentation {
|
||||
@Override
|
||||
public ElementMatcher<TypeDescription> typeMatcher() {
|
||||
return extendsClass(named("java.rmi.server.RemoteServer"));
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
return singletonMap(
|
||||
isMethod().and(isPublic()).and(not(isStatic())),
|
||||
RmiServerInstrumentation.class.getName() + "$ServerAdvice");
|
||||
}
|
||||
}
|
||||
|
||||
public static class ServerAdvice {
|
||||
|
|
|
@ -0,0 +1,40 @@
|
|||
/*
|
||||
* Copyright The OpenTelemetry Authors
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
|
||||
package io.opentelemetry.javaagent.instrumentation.scalaconcurrent;
|
||||
|
||||
import static io.opentelemetry.javaagent.instrumentation.scalaconcurrent.ScalaForkJoinTaskInstrumentation.TASK_CLASS_NAME;
|
||||
import static java.util.Arrays.asList;
|
||||
|
||||
import com.google.auto.service.AutoService;
|
||||
import io.opentelemetry.javaagent.instrumentation.api.concurrent.State;
|
||||
import io.opentelemetry.javaagent.tooling.InstrumentationModule;
|
||||
import io.opentelemetry.javaagent.tooling.TypeInstrumentation;
|
||||
import java.util.Collections;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.concurrent.Callable;
|
||||
|
||||
@AutoService(InstrumentationModule.class)
|
||||
public class ScalaConcurrentInstrumentationModule extends InstrumentationModule {
|
||||
public ScalaConcurrentInstrumentationModule() {
|
||||
super("java_concurrent", "scala_concurrent");
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<TypeInstrumentation> typeInstrumentations() {
|
||||
return asList(new ScalaForkJoinPoolInstrumentation(), new ScalaForkJoinTaskInstrumentation());
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<String, String> contextStore() {
|
||||
Map<String, String> map = new HashMap<>();
|
||||
map.put(Runnable.class.getName(), State.class.getName());
|
||||
map.put(Callable.class.getName(), State.class.getName());
|
||||
map.put(TASK_CLASS_NAME, State.class.getName());
|
||||
return Collections.unmodifiableMap(map);
|
||||
}
|
||||
}
|
|
@ -5,18 +5,16 @@
|
|||
|
||||
package io.opentelemetry.javaagent.instrumentation.scalaconcurrent;
|
||||
|
||||
import static java.util.Collections.singletonMap;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.nameMatches;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.named;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.takesArgument;
|
||||
|
||||
import com.google.auto.service.AutoService;
|
||||
import io.opentelemetry.javaagent.instrumentation.api.ContextStore;
|
||||
import io.opentelemetry.javaagent.instrumentation.api.InstrumentationContext;
|
||||
import io.opentelemetry.javaagent.instrumentation.api.Java8BytecodeBridge;
|
||||
import io.opentelemetry.javaagent.instrumentation.api.concurrent.ExecutorInstrumentationUtils;
|
||||
import io.opentelemetry.javaagent.instrumentation.api.concurrent.State;
|
||||
import io.opentelemetry.javaagent.tooling.Instrumenter;
|
||||
import io.opentelemetry.javaagent.tooling.TypeInstrumentation;
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
import net.bytebuddy.asm.Advice;
|
||||
|
@ -25,12 +23,7 @@ import net.bytebuddy.description.type.TypeDescription;
|
|||
import net.bytebuddy.matcher.ElementMatcher;
|
||||
import scala.concurrent.forkjoin.ForkJoinTask;
|
||||
|
||||
@AutoService(Instrumenter.class)
|
||||
public final class ScalaForkJoinPoolInstrumentation extends Instrumenter.Default {
|
||||
|
||||
public ScalaForkJoinPoolInstrumentation() {
|
||||
super("java_concurrent", "scala_concurrent");
|
||||
}
|
||||
final class ScalaForkJoinPoolInstrumentation implements TypeInstrumentation {
|
||||
|
||||
@Override
|
||||
public ElementMatcher<TypeDescription> typeMatcher() {
|
||||
|
@ -38,11 +31,6 @@ public final class ScalaForkJoinPoolInstrumentation extends Instrumenter.Default
|
|||
return named("scala.concurrent.forkjoin.ForkJoinPool");
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<String, String> contextStore() {
|
||||
return singletonMap(ScalaForkJoinTaskInstrumentation.TASK_CLASS_NAME, State.class.getName());
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
Map<ElementMatcher<? super MethodDescription>, String> transformers = new HashMap<>();
|
||||
|
@ -65,7 +53,7 @@ public final class ScalaForkJoinPoolInstrumentation extends Instrumenter.Default
|
|||
|
||||
@Advice.OnMethodEnter(suppress = Throwable.class)
|
||||
public static State enterJobSubmit(
|
||||
@Advice.Argument(value = 0, readOnly = false) ForkJoinTask task) {
|
||||
@Advice.Argument(value = 0, readOnly = false) ForkJoinTask<?> task) {
|
||||
if (ExecutorInstrumentationUtils.shouldAttachStateToTask(task)) {
|
||||
ContextStore<ForkJoinTask, State> contextStore =
|
||||
InstrumentationContext.get(ForkJoinTask.class, State.class);
|
||||
|
|
|
@ -13,15 +13,12 @@ import static net.bytebuddy.matcher.ElementMatchers.named;
|
|||
import static net.bytebuddy.matcher.ElementMatchers.not;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.takesArguments;
|
||||
|
||||
import com.google.auto.service.AutoService;
|
||||
import io.opentelemetry.context.Scope;
|
||||
import io.opentelemetry.javaagent.instrumentation.api.ContextStore;
|
||||
import io.opentelemetry.javaagent.instrumentation.api.InstrumentationContext;
|
||||
import io.opentelemetry.javaagent.instrumentation.api.concurrent.AdviceUtils;
|
||||
import io.opentelemetry.javaagent.instrumentation.api.concurrent.State;
|
||||
import io.opentelemetry.javaagent.tooling.Instrumenter;
|
||||
import java.util.Collections;
|
||||
import java.util.HashMap;
|
||||
import io.opentelemetry.javaagent.tooling.TypeInstrumentation;
|
||||
import java.util.Map;
|
||||
import java.util.concurrent.Callable;
|
||||
import net.bytebuddy.asm.Advice;
|
||||
|
@ -37,15 +34,10 @@ import scala.concurrent.forkjoin.ForkJoinTask;
|
|||
* <p>Note: There are quite a few separate implementations of {@code ForkJoinTask}/{@code
|
||||
* ForkJoinPool}: JVM, Akka, Scala, Netty to name a few. This class handles Scala version.
|
||||
*/
|
||||
@AutoService(Instrumenter.class)
|
||||
public final class ScalaForkJoinTaskInstrumentation extends Instrumenter.Default {
|
||||
final class ScalaForkJoinTaskInstrumentation implements TypeInstrumentation {
|
||||
|
||||
static final String TASK_CLASS_NAME = "scala.concurrent.forkjoin.ForkJoinTask";
|
||||
|
||||
public ScalaForkJoinTaskInstrumentation() {
|
||||
super("java_concurrent", "scala_concurrent");
|
||||
}
|
||||
|
||||
@Override
|
||||
public ElementMatcher<ClassLoader> classLoaderMatcher() {
|
||||
// Optimization for expensive typeMatcher.
|
||||
|
@ -57,15 +49,6 @@ public final class ScalaForkJoinTaskInstrumentation extends Instrumenter.Default
|
|||
return extendsClass(named(TASK_CLASS_NAME));
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<String, String> contextStore() {
|
||||
Map<String, String> map = new HashMap<>();
|
||||
map.put(Runnable.class.getName(), State.class.getName());
|
||||
map.put(Callable.class.getName(), State.class.getName());
|
||||
map.put(TASK_CLASS_NAME, State.class.getName());
|
||||
return Collections.unmodifiableMap(map);
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
return singletonMap(
|
||||
|
@ -82,7 +65,7 @@ public final class ScalaForkJoinTaskInstrumentation extends Instrumenter.Default
|
|||
* need to use that state.
|
||||
*/
|
||||
@Advice.OnMethodEnter(suppress = Throwable.class)
|
||||
public static Scope enter(@Advice.This ForkJoinTask thiz) {
|
||||
public static Scope enter(@Advice.This ForkJoinTask<?> thiz) {
|
||||
ContextStore<ForkJoinTask, State> contextStore =
|
||||
InstrumentationContext.get(ForkJoinTask.class, State.class);
|
||||
Scope scope = AdviceUtils.startTaskScope(contextStore, thiz);
|
||||
|
|
|
@ -59,16 +59,16 @@ Next, request passes several other methods from Servlet specification, such as
|
|||
|
||||
`protected void org.springframework.web.servlet.FrameworkServlet#doGet(HttpServletRequest, HttpServletResponse)`.
|
||||
|
||||
They are the targets for `HttpServletInstrumentation`.
|
||||
They are the targets for `HttpServletInstrumentationModule`.
|
||||
From the observability point of view nothing of interest usually happens inside these methods.
|
||||
Thus it usually does not make sense to create spans from them, as they would only add useless noise.
|
||||
For this reason `HttpServletInstrumentation` is disabled by default.
|
||||
In rare cases when you need it, you can enable it using configuration property `otel.integration.servlet-service.enabled`.
|
||||
For this reason `HttpServletInstrumentationModule` is disabled by default.
|
||||
In rare cases when you need it, you can enable it using configuration property `otel.instrumentation.servlet-service.enabled`.
|
||||
|
||||
In exactly the same situation are all other Servlet filters beyond the initial entry point.
|
||||
Usually unimportant, they may be sometimes of interest during troubleshooting.
|
||||
They are instrumented by `FilterInstrumentation` which is also disabled by default.
|
||||
You can enable it with the configuration property `otel.integration.servlet-filter.enabled`.
|
||||
They are instrumented by `FilterInstrumentationModule` which is also disabled by default.
|
||||
You can enable it with the configuration property `otel.instrumentation.servlet-filter.enabled`.
|
||||
At last, request processing may reach the specific framework that your application uses.
|
||||
In this case Spring MVC and `OwnerController.initCreationForm`.
|
||||
|
||||
|
@ -88,10 +88,10 @@ Of course, still adhering to OpenTelemetry
|
|||
[semantic conventions](https://github.com/open-telemetry/opentelemetry-specification/blob/master/specification/trace/semantic_conventions/http.md).
|
||||
|
||||
## Additional instrumentations
|
||||
`RequestDispatcherInstrumentation` instruments `javax.servlet.RequestDispatcher.forward` and
|
||||
`RequestDispatcherInstrumentationModule` instruments `javax.servlet.RequestDispatcher.forward` and
|
||||
`javax.servlet.RequestDispatcher.include` methods to create new `INTERNAL` spans around their
|
||||
invocations.
|
||||
|
||||
`HttpServletResponseInstrumentation` instruments `javax.servlet.http.HttpServletResponse.sendError`
|
||||
`HttpServletResponseInstrumentationModule` instruments `javax.servlet.http.HttpServletResponse.sendError`
|
||||
and `javax.servlet.http.HttpServletResponse.sendRedirect` methods to create new `INTERNAL` spans
|
||||
around their invocations.
|
||||
|
|
|
@ -8,15 +8,12 @@ package io.opentelemetry.javaagent.instrumentation.servlet.v2_2;
|
|||
import static io.opentelemetry.javaagent.tooling.ClassLoaderMatcher.hasClassesNamed;
|
||||
import static io.opentelemetry.javaagent.tooling.bytebuddy.matcher.AgentElementMatchers.safeHasSuperType;
|
||||
import static io.opentelemetry.javaagent.tooling.matcher.NameMatchers.namedOneOf;
|
||||
import static java.util.Collections.singletonMap;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.named;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.not;
|
||||
|
||||
import com.google.auto.service.AutoService;
|
||||
import io.opentelemetry.api.trace.Span;
|
||||
import io.opentelemetry.context.Scope;
|
||||
import io.opentelemetry.javaagent.instrumentation.api.InstrumentationContext;
|
||||
import io.opentelemetry.javaagent.tooling.Instrumenter;
|
||||
import io.opentelemetry.javaagent.tooling.TypeInstrumentation;
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
import javax.servlet.ServletRequest;
|
||||
|
@ -38,16 +35,10 @@ import net.bytebuddy.matcher.ElementMatcher;
|
|||
* ServletResponse, Throwable, Span, Scope)} can get it from context and set required span
|
||||
* attribute.
|
||||
*/
|
||||
@AutoService(Instrumenter.class)
|
||||
public final class Servlet2ResponseStatusInstrumentation extends Instrumenter.Default {
|
||||
public Servlet2ResponseStatusInstrumentation() {
|
||||
super("servlet", "servlet-2");
|
||||
}
|
||||
|
||||
// this is required to make sure servlet 2 instrumentation won't apply to servlet 3
|
||||
final class HttpServletResponseInstrumentation implements TypeInstrumentation {
|
||||
@Override
|
||||
public ElementMatcher<ClassLoader> classLoaderMatcher() {
|
||||
return not(hasClassesNamed("javax.servlet.AsyncEvent", "javax.servlet.AsyncListener"));
|
||||
return hasClassesNamed("javax.servlet.http.HttpServletResponse");
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -55,20 +46,15 @@ public final class Servlet2ResponseStatusInstrumentation extends Instrumenter.De
|
|||
return safeHasSuperType(named("javax.servlet.http.HttpServletResponse"));
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<String, String> contextStore() {
|
||||
return singletonMap("javax.servlet.ServletResponse", Integer.class.getName());
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
Map<ElementMatcher<? super MethodDescription>, String> transformers = new HashMap<>();
|
||||
transformers.put(
|
||||
namedOneOf("sendError", "setStatus"),
|
||||
Servlet2ResponseStatusInstrumentation.class.getName() + "$Servlet2ResponseStatusAdvice");
|
||||
HttpServletResponseInstrumentation.class.getName() + "$Servlet2ResponseStatusAdvice");
|
||||
transformers.put(
|
||||
named("sendRedirect"),
|
||||
Servlet2ResponseStatusInstrumentation.class.getName() + "$Servlet2ResponseRedirectAdvice");
|
||||
HttpServletResponseInstrumentation.class.getName() + "$Servlet2ResponseRedirectAdvice");
|
||||
return transformers;
|
||||
}
|
||||
|
|
@ -0,0 +1,52 @@
|
|||
/*
|
||||
* Copyright The OpenTelemetry Authors
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
|
||||
package io.opentelemetry.javaagent.instrumentation.servlet.v2_2;
|
||||
|
||||
import static io.opentelemetry.javaagent.tooling.ClassLoaderMatcher.hasClassesNamed;
|
||||
import static java.util.Collections.singletonMap;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.not;
|
||||
|
||||
import com.google.auto.service.AutoService;
|
||||
import io.opentelemetry.javaagent.tooling.InstrumentationModule;
|
||||
import io.opentelemetry.javaagent.tooling.TypeInstrumentation;
|
||||
import java.util.Arrays;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import net.bytebuddy.matcher.ElementMatcher;
|
||||
|
||||
@AutoService(InstrumentationModule.class)
|
||||
public class Servlet2InstrumentationModule extends InstrumentationModule {
|
||||
public Servlet2InstrumentationModule() {
|
||||
super("servlet", "servlet-2");
|
||||
}
|
||||
|
||||
// this is required to make sure servlet 2 instrumentation won't apply to servlet 3
|
||||
@Override
|
||||
public ElementMatcher.Junction<ClassLoader> classLoaderMatcher() {
|
||||
return not(hasClassesNamed("javax.servlet.AsyncEvent", "javax.servlet.AsyncListener"));
|
||||
}
|
||||
|
||||
@Override
|
||||
public String[] helperClassNames() {
|
||||
return new String[] {
|
||||
"io.opentelemetry.instrumentation.servlet.ServletHttpServerTracer",
|
||||
"io.opentelemetry.instrumentation.servlet.HttpServletRequestGetter",
|
||||
packageName + ".ResponseWithStatus",
|
||||
packageName + ".Servlet2HttpServerTracer"
|
||||
};
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<TypeInstrumentation> typeInstrumentations() {
|
||||
return Arrays.asList(
|
||||
new HttpServletResponseInstrumentation(), new ServletAndFilterChainInstrumentation());
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<String, String> contextStore() {
|
||||
return singletonMap("javax.servlet.ServletResponse", Integer.class.getName());
|
||||
}
|
||||
}
|
|
@ -11,29 +11,20 @@ import static io.opentelemetry.javaagent.tooling.matcher.NameMatchers.namedOneOf
|
|||
import static java.util.Collections.singletonMap;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.isPublic;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.named;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.not;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.takesArgument;
|
||||
|
||||
import com.google.auto.service.AutoService;
|
||||
import io.opentelemetry.javaagent.tooling.Instrumenter;
|
||||
import io.opentelemetry.javaagent.tooling.TypeInstrumentation;
|
||||
import java.util.Map;
|
||||
import net.bytebuddy.description.method.MethodDescription;
|
||||
import net.bytebuddy.description.type.TypeDescription;
|
||||
import net.bytebuddy.matcher.ElementMatcher;
|
||||
|
||||
@AutoService(Instrumenter.class)
|
||||
public final class Servlet2Instrumentation extends Instrumenter.Default {
|
||||
final class ServletAndFilterChainInstrumentation implements TypeInstrumentation {
|
||||
|
||||
public Servlet2Instrumentation() {
|
||||
super("servlet", "servlet-2");
|
||||
}
|
||||
|
||||
// this is required to make sure servlet 2 instrumentation won't apply to servlet 3
|
||||
@Override
|
||||
public ElementMatcher<ClassLoader> classLoaderMatcher() {
|
||||
// Optimization for expensive typeMatcher.
|
||||
return hasClassesNamed("javax.servlet.http.HttpServlet")
|
||||
.and(not(hasClassesNamed("javax.servlet.AsyncEvent", "javax.servlet.AsyncListener")));
|
||||
return hasClassesNamed("javax.servlet.http.HttpServlet");
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -41,22 +32,6 @@ public final class Servlet2Instrumentation extends Instrumenter.Default {
|
|||
return safeHasSuperType(
|
||||
namedOneOf("javax.servlet.FilterChain", "javax.servlet.http.HttpServlet"));
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<String, String> contextStore() {
|
||||
return singletonMap("javax.servlet.ServletResponse", Integer.class.getName());
|
||||
}
|
||||
|
||||
@Override
|
||||
public String[] helperClassNames() {
|
||||
return new String[] {
|
||||
"io.opentelemetry.instrumentation.servlet.ServletHttpServerTracer",
|
||||
"io.opentelemetry.instrumentation.servlet.HttpServletRequestGetter",
|
||||
packageName + ".ResponseWithStatus",
|
||||
packageName + ".Servlet2HttpServerTracer"
|
||||
};
|
||||
}
|
||||
|
||||
/**
|
||||
* Here we are instrumenting the public method for HttpServlet. This should ensure that this
|
||||
* advice is always called before HttpServletInstrumentation which is instrumenting the protected
|
||||
|
@ -69,6 +44,6 @@ public final class Servlet2Instrumentation extends Instrumenter.Default {
|
|||
.and(takesArgument(0, named("javax.servlet.ServletRequest")))
|
||||
.and(takesArgument(1, named("javax.servlet.ServletResponse")))
|
||||
.and(isPublic()),
|
||||
packageName + ".Servlet2Advice");
|
||||
Servlet2Advice.class.getName());
|
||||
}
|
||||
}
|
|
@ -13,12 +13,11 @@ import static net.bytebuddy.matcher.ElementMatchers.isMethod;
|
|||
import static net.bytebuddy.matcher.ElementMatchers.isPublic;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.named;
|
||||
|
||||
import com.google.auto.service.AutoService;
|
||||
import io.opentelemetry.api.trace.Span;
|
||||
import io.opentelemetry.context.Context;
|
||||
import io.opentelemetry.javaagent.instrumentation.api.CallDepthThreadLocalMap;
|
||||
import io.opentelemetry.javaagent.instrumentation.api.Java8BytecodeBridge;
|
||||
import io.opentelemetry.javaagent.tooling.Instrumenter;
|
||||
import io.opentelemetry.javaagent.tooling.TypeInstrumentation;
|
||||
import java.util.Map;
|
||||
import javax.servlet.AsyncContext;
|
||||
import javax.servlet.ServletRequest;
|
||||
|
@ -27,20 +26,7 @@ import net.bytebuddy.description.method.MethodDescription;
|
|||
import net.bytebuddy.description.type.TypeDescription;
|
||||
import net.bytebuddy.matcher.ElementMatcher;
|
||||
|
||||
@AutoService(Instrumenter.class)
|
||||
public final class AsyncContextInstrumentation extends Instrumenter.Default {
|
||||
|
||||
public AsyncContextInstrumentation() {
|
||||
super("servlet", "servlet-3");
|
||||
}
|
||||
|
||||
@Override
|
||||
public String[] helperClassNames() {
|
||||
return new String[] {
|
||||
"io.opentelemetry.instrumentation.servlet.HttpServletRequestGetter",
|
||||
"io.opentelemetry.instrumentation.servlet.ServletHttpServerTracer",
|
||||
};
|
||||
}
|
||||
final class AsyncContextInstrumentation implements TypeInstrumentation {
|
||||
|
||||
@Override
|
||||
public ElementMatcher<ClassLoader> classLoaderMatcher() {
|
||||
|
|
|
@ -0,0 +1,36 @@
|
|||
/*
|
||||
* Copyright The OpenTelemetry Authors
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
|
||||
package io.opentelemetry.javaagent.instrumentation.servlet.v3_0;
|
||||
|
||||
import static java.util.Arrays.asList;
|
||||
|
||||
import com.google.auto.service.AutoService;
|
||||
import io.opentelemetry.javaagent.tooling.InstrumentationModule;
|
||||
import io.opentelemetry.javaagent.tooling.TypeInstrumentation;
|
||||
import java.util.List;
|
||||
|
||||
@AutoService(InstrumentationModule.class)
|
||||
public class Servlet3InstrumentationModule extends InstrumentationModule {
|
||||
public Servlet3InstrumentationModule() {
|
||||
super("servlet", "servlet-3");
|
||||
}
|
||||
|
||||
@Override
|
||||
public String[] helperClassNames() {
|
||||
return new String[] {
|
||||
"io.opentelemetry.instrumentation.servlet.HttpServletRequestGetter",
|
||||
"io.opentelemetry.instrumentation.servlet.ServletHttpServerTracer",
|
||||
packageName + ".Servlet3Advice",
|
||||
packageName + ".Servlet3HttpServerTracer",
|
||||
packageName + ".TagSettingAsyncListener"
|
||||
};
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<TypeInstrumentation> typeInstrumentations() {
|
||||
return asList(new AsyncContextInstrumentation(), new ServletAndFilterChainInstrumentation());
|
||||
}
|
||||
}
|
|
@ -13,19 +13,13 @@ import static net.bytebuddy.matcher.ElementMatchers.isPublic;
|
|||
import static net.bytebuddy.matcher.ElementMatchers.named;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.takesArgument;
|
||||
|
||||
import com.google.auto.service.AutoService;
|
||||
import io.opentelemetry.javaagent.tooling.Instrumenter;
|
||||
import io.opentelemetry.javaagent.tooling.TypeInstrumentation;
|
||||
import java.util.Map;
|
||||
import net.bytebuddy.description.method.MethodDescription;
|
||||
import net.bytebuddy.description.type.TypeDescription;
|
||||
import net.bytebuddy.matcher.ElementMatcher;
|
||||
|
||||
@AutoService(Instrumenter.class)
|
||||
public final class Servlet3Instrumentation extends Instrumenter.Default {
|
||||
public Servlet3Instrumentation() {
|
||||
super("servlet", "servlet-3");
|
||||
}
|
||||
|
||||
final class ServletAndFilterChainInstrumentation implements TypeInstrumentation {
|
||||
@Override
|
||||
public ElementMatcher<ClassLoader> classLoaderMatcher() {
|
||||
// Optimization for expensive typeMatcher.
|
||||
|
@ -38,17 +32,6 @@ public final class Servlet3Instrumentation extends Instrumenter.Default {
|
|||
namedOneOf("javax.servlet.FilterChain", "javax.servlet.http.HttpServlet"));
|
||||
}
|
||||
|
||||
@Override
|
||||
public String[] helperClassNames() {
|
||||
return new String[] {
|
||||
"io.opentelemetry.instrumentation.servlet.HttpServletRequestGetter",
|
||||
"io.opentelemetry.instrumentation.servlet.ServletHttpServerTracer",
|
||||
packageName + ".Servlet3Advice",
|
||||
packageName + ".Servlet3HttpServerTracer",
|
||||
packageName + ".TagSettingAsyncListener"
|
||||
};
|
||||
}
|
||||
|
||||
/**
|
||||
* Here we are instrumenting the public method for HttpServlet. This should ensure that this
|
||||
* advice is always called before HttpServletInstrumentation which is instrumenting the protected
|
||||
|
@ -61,6 +44,6 @@ public final class Servlet3Instrumentation extends Instrumenter.Default {
|
|||
.and(takesArgument(0, named("javax.servlet.ServletRequest")))
|
||||
.and(takesArgument(1, named("javax.servlet.ServletResponse")))
|
||||
.and(isPublic()),
|
||||
packageName + ".Servlet3Advice");
|
||||
Servlet3Advice.class.getName());
|
||||
}
|
||||
}
|
|
@ -4,7 +4,12 @@ muzzle {
|
|||
pass {
|
||||
group = "javax.servlet"
|
||||
module = "servlet-api"
|
||||
versions = "[2.2,)"
|
||||
versions = "(0,)"
|
||||
}
|
||||
pass {
|
||||
group = "javax.servlet"
|
||||
module = 'javax.servlet-api'
|
||||
versions = "[3.0,)"
|
||||
assertInverse = true
|
||||
}
|
||||
}
|
||||
|
|
|
@ -10,6 +10,7 @@ import static io.opentelemetry.javaagent.instrumentation.servlet.dispatcher.Requ
|
|||
import static io.opentelemetry.javaagent.tooling.ClassLoaderMatcher.hasClassesNamed;
|
||||
import static io.opentelemetry.javaagent.tooling.bytebuddy.matcher.AgentElementMatchers.implementsInterface;
|
||||
import static io.opentelemetry.javaagent.tooling.matcher.NameMatchers.namedOneOf;
|
||||
import static java.util.Collections.singletonList;
|
||||
import static java.util.Collections.singletonMap;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.isPublic;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.named;
|
||||
|
@ -22,8 +23,10 @@ import io.opentelemetry.api.trace.SpanContext;
|
|||
import io.opentelemetry.context.Context;
|
||||
import io.opentelemetry.context.Scope;
|
||||
import io.opentelemetry.javaagent.instrumentation.api.Java8BytecodeBridge;
|
||||
import io.opentelemetry.javaagent.tooling.Instrumenter;
|
||||
import io.opentelemetry.javaagent.tooling.InstrumentationModule;
|
||||
import io.opentelemetry.javaagent.tooling.TypeInstrumentation;
|
||||
import java.lang.reflect.Method;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import javax.servlet.RequestDispatcher;
|
||||
import javax.servlet.ServletRequest;
|
||||
|
@ -32,23 +35,12 @@ import net.bytebuddy.description.method.MethodDescription;
|
|||
import net.bytebuddy.description.type.TypeDescription;
|
||||
import net.bytebuddy.matcher.ElementMatcher;
|
||||
|
||||
@AutoService(Instrumenter.class)
|
||||
public final class RequestDispatcherInstrumentation extends Instrumenter.Default {
|
||||
public RequestDispatcherInstrumentation() {
|
||||
@AutoService(InstrumentationModule.class)
|
||||
public final class RequestDispatcherInstrumentationModule extends InstrumentationModule {
|
||||
public RequestDispatcherInstrumentationModule() {
|
||||
super("servlet", "servlet-dispatcher");
|
||||
}
|
||||
|
||||
@Override
|
||||
public ElementMatcher<ClassLoader> classLoaderMatcher() {
|
||||
// Optimization for expensive typeMatcher.
|
||||
return hasClassesNamed("javax.servlet.RequestDispatcher");
|
||||
}
|
||||
|
||||
@Override
|
||||
public ElementMatcher<TypeDescription> typeMatcher() {
|
||||
return implementsInterface(named("javax.servlet.RequestDispatcher"));
|
||||
}
|
||||
|
||||
@Override
|
||||
public String[] helperClassNames() {
|
||||
return new String[] {
|
||||
|
@ -56,20 +48,38 @@ public final class RequestDispatcherInstrumentation extends Instrumenter.Default
|
|||
};
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<TypeInstrumentation> typeInstrumentations() {
|
||||
return singletonList(new RequestDispatcherInstrumentation());
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<String, String> contextStore() {
|
||||
return singletonMap("javax.servlet.RequestDispatcher", String.class.getName());
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
return singletonMap(
|
||||
namedOneOf("forward", "include")
|
||||
.and(takesArguments(2))
|
||||
.and(takesArgument(0, named("javax.servlet.ServletRequest")))
|
||||
.and(takesArgument(1, named("javax.servlet.ServletResponse")))
|
||||
.and(isPublic()),
|
||||
getClass().getName() + "$RequestDispatcherAdvice");
|
||||
private static final class RequestDispatcherInstrumentation implements TypeInstrumentation {
|
||||
@Override
|
||||
public ElementMatcher<ClassLoader> classLoaderMatcher() {
|
||||
// Optimization for expensive typeMatcher.
|
||||
return hasClassesNamed("javax.servlet.RequestDispatcher");
|
||||
}
|
||||
|
||||
@Override
|
||||
public ElementMatcher<TypeDescription> typeMatcher() {
|
||||
return implementsInterface(named("javax.servlet.RequestDispatcher"));
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
return singletonMap(
|
||||
namedOneOf("forward", "include")
|
||||
.and(takesArguments(2))
|
||||
.and(takesArgument(0, named("javax.servlet.ServletRequest")))
|
||||
.and(takesArgument(1, named("javax.servlet.ServletResponse")))
|
||||
.and(isPublic()),
|
||||
RequestDispatcherInstrumentationModule.class.getName() + "$RequestDispatcherAdvice");
|
||||
}
|
||||
}
|
||||
|
||||
public static class RequestDispatcherAdvice {
|
|
@ -8,6 +8,7 @@ package io.opentelemetry.javaagent.instrumentation.servlet.filter;
|
|||
import static io.opentelemetry.javaagent.instrumentation.servlet.filter.FilterTracer.tracer;
|
||||
import static io.opentelemetry.javaagent.tooling.ClassLoaderMatcher.hasClassesNamed;
|
||||
import static io.opentelemetry.javaagent.tooling.bytebuddy.matcher.AgentElementMatchers.implementsInterface;
|
||||
import static java.util.Collections.singletonList;
|
||||
import static java.util.Collections.singletonMap;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.isPublic;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.named;
|
||||
|
@ -18,7 +19,9 @@ import io.opentelemetry.api.trace.Span;
|
|||
import io.opentelemetry.api.trace.Span.Kind;
|
||||
import io.opentelemetry.context.Scope;
|
||||
import io.opentelemetry.javaagent.instrumentation.api.Java8BytecodeBridge;
|
||||
import io.opentelemetry.javaagent.tooling.Instrumenter;
|
||||
import io.opentelemetry.javaagent.tooling.InstrumentationModule;
|
||||
import io.opentelemetry.javaagent.tooling.TypeInstrumentation;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import javax.servlet.Filter;
|
||||
import net.bytebuddy.asm.Advice;
|
||||
|
@ -31,9 +34,9 @@ import net.bytebuddy.matcher.ElementMatcher;
|
|||
*
|
||||
* <p>See README.md for more information about different servlet instrumentations.
|
||||
*/
|
||||
@AutoService(Instrumenter.class)
|
||||
public final class FilterInstrumentation extends Instrumenter.Default {
|
||||
public FilterInstrumentation() {
|
||||
@AutoService(InstrumentationModule.class)
|
||||
public final class FilterInstrumentationModule extends InstrumentationModule {
|
||||
public FilterInstrumentationModule() {
|
||||
super("servlet-filter");
|
||||
}
|
||||
|
||||
|
@ -42,18 +45,6 @@ public final class FilterInstrumentation extends Instrumenter.Default {
|
|||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ElementMatcher<ClassLoader> classLoaderMatcher() {
|
||||
// Optimization for expensive typeMatcher.
|
||||
// return hasClassesNamed("javax.servlet.Filter"); // Not available in 2.2
|
||||
return hasClassesNamed("javax.servlet.http.HttpServlet");
|
||||
}
|
||||
|
||||
@Override
|
||||
public ElementMatcher<TypeDescription> typeMatcher() {
|
||||
return implementsInterface(named("javax.servlet.Filter"));
|
||||
}
|
||||
|
||||
@Override
|
||||
public String[] helperClassNames() {
|
||||
return new String[] {
|
||||
|
@ -62,13 +53,31 @@ public final class FilterInstrumentation extends Instrumenter.Default {
|
|||
}
|
||||
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
return singletonMap(
|
||||
named("doFilter")
|
||||
.and(takesArgument(0, named("javax.servlet.ServletRequest")))
|
||||
.and(takesArgument(1, named("javax.servlet.ServletResponse")))
|
||||
.and(isPublic()),
|
||||
getClass().getName() + "$FilterAdvice");
|
||||
public List<TypeInstrumentation> typeInstrumentations() {
|
||||
return singletonList(new FilterInstrumentation());
|
||||
}
|
||||
|
||||
private static final class FilterInstrumentation implements TypeInstrumentation {
|
||||
@Override
|
||||
public ElementMatcher<ClassLoader> classLoaderMatcher() {
|
||||
// Optimization for expensive typeMatcher.
|
||||
return hasClassesNamed("javax.servlet.Filter");
|
||||
}
|
||||
|
||||
@Override
|
||||
public ElementMatcher<TypeDescription> typeMatcher() {
|
||||
return implementsInterface(named("javax.servlet.Filter"));
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
return singletonMap(
|
||||
named("doFilter")
|
||||
.and(takesArgument(0, named("javax.servlet.ServletRequest")))
|
||||
.and(takesArgument(1, named("javax.servlet.ServletResponse")))
|
||||
.and(isPublic()),
|
||||
FilterInstrumentationModule.class.getName() + "$FilterAdvice");
|
||||
}
|
||||
}
|
||||
|
||||
public static class FilterAdvice {
|
|
@ -8,6 +8,7 @@ package io.opentelemetry.javaagent.instrumentation.servlet.http;
|
|||
import static io.opentelemetry.javaagent.instrumentation.servlet.http.HttpServletTracer.tracer;
|
||||
import static io.opentelemetry.javaagent.tooling.ClassLoaderMatcher.hasClassesNamed;
|
||||
import static io.opentelemetry.javaagent.tooling.bytebuddy.matcher.AgentElementMatchers.extendsClass;
|
||||
import static java.util.Collections.singletonList;
|
||||
import static java.util.Collections.singletonMap;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.isProtected;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.isPublic;
|
||||
|
@ -19,18 +20,21 @@ import com.google.auto.service.AutoService;
|
|||
import io.opentelemetry.api.trace.Span;
|
||||
import io.opentelemetry.context.Scope;
|
||||
import io.opentelemetry.javaagent.instrumentation.api.Java8BytecodeBridge;
|
||||
import io.opentelemetry.javaagent.tooling.Instrumenter;
|
||||
import io.opentelemetry.javaagent.tooling.InstrumentationModule;
|
||||
import io.opentelemetry.javaagent.tooling.TypeInstrumentation;
|
||||
import java.lang.reflect.Method;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import net.bytebuddy.asm.Advice;
|
||||
import net.bytebuddy.description.method.MethodDescription;
|
||||
import net.bytebuddy.description.type.TypeDescription;
|
||||
import net.bytebuddy.matcher.ElementMatcher;
|
||||
|
||||
// Please read README.md of this subproject to understand what is this instrumentation.
|
||||
@AutoService(Instrumenter.class)
|
||||
public final class HttpServletInstrumentation extends Instrumenter.Default {
|
||||
public HttpServletInstrumentation() {
|
||||
// Please read README.md of this subproject to understand what this instrumentation is and why it
|
||||
// requires a separate module.
|
||||
@AutoService(InstrumentationModule.class)
|
||||
public final class HttpServletInstrumentationModule extends InstrumentationModule {
|
||||
public HttpServletInstrumentationModule() {
|
||||
super("servlet-service");
|
||||
}
|
||||
|
||||
|
@ -39,17 +43,6 @@ public final class HttpServletInstrumentation extends Instrumenter.Default {
|
|||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ElementMatcher<ClassLoader> classLoaderMatcher() {
|
||||
// Optimization for expensive typeMatcher.
|
||||
return hasClassesNamed("javax.servlet.http.HttpServlet");
|
||||
}
|
||||
|
||||
@Override
|
||||
public ElementMatcher<TypeDescription> typeMatcher() {
|
||||
return extendsClass(named("javax.servlet.http.HttpServlet"));
|
||||
}
|
||||
|
||||
@Override
|
||||
public String[] helperClassNames() {
|
||||
return new String[] {
|
||||
|
@ -57,19 +50,38 @@ public final class HttpServletInstrumentation extends Instrumenter.Default {
|
|||
};
|
||||
}
|
||||
|
||||
/**
|
||||
* Here we are instrumenting the protected method for HttpServlet. This should ensure that this
|
||||
* advice is always called after Servlet3Instrumentation which is instrumenting the public method.
|
||||
*/
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
return singletonMap(
|
||||
named("service")
|
||||
.or(nameStartsWith("do")) // doGet, doPost, etc
|
||||
.and(takesArgument(0, named("javax.servlet.http.HttpServletRequest")))
|
||||
.and(takesArgument(1, named("javax.servlet.http.HttpServletResponse")))
|
||||
.and(isProtected().or(isPublic())),
|
||||
getClass().getName() + "$HttpServletAdvice");
|
||||
public List<TypeInstrumentation> typeInstrumentations() {
|
||||
return singletonList(new HttpServletInstrumentation());
|
||||
}
|
||||
|
||||
private static final class HttpServletInstrumentation implements TypeInstrumentation {
|
||||
@Override
|
||||
public ElementMatcher<ClassLoader> classLoaderMatcher() {
|
||||
// Optimization for expensive typeMatcher.
|
||||
return hasClassesNamed("javax.servlet.http.HttpServlet");
|
||||
}
|
||||
|
||||
@Override
|
||||
public ElementMatcher<TypeDescription> typeMatcher() {
|
||||
return extendsClass(named("javax.servlet.http.HttpServlet"));
|
||||
}
|
||||
|
||||
/**
|
||||
* Here we are instrumenting the protected method for HttpServlet. This should ensure that this
|
||||
* advice is always called after Servlet3Instrumentation which is instrumenting the public
|
||||
* method.
|
||||
*/
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
return singletonMap(
|
||||
named("service")
|
||||
.or(nameStartsWith("do")) // doGet, doPost, etc
|
||||
.and(takesArgument(0, named("javax.servlet.http.HttpServletRequest")))
|
||||
.and(takesArgument(1, named("javax.servlet.http.HttpServletResponse")))
|
||||
.and(isProtected().or(isPublic())),
|
||||
HttpServletInstrumentationModule.class.getName() + "$HttpServletAdvice");
|
||||
}
|
||||
}
|
||||
|
||||
public static class HttpServletAdvice {
|
|
@ -9,6 +9,7 @@ import static io.opentelemetry.javaagent.instrumentation.servlet.http.HttpServle
|
|||
import static io.opentelemetry.javaagent.tooling.ClassLoaderMatcher.hasClassesNamed;
|
||||
import static io.opentelemetry.javaagent.tooling.bytebuddy.matcher.AgentElementMatchers.implementsInterface;
|
||||
import static io.opentelemetry.javaagent.tooling.matcher.NameMatchers.namedOneOf;
|
||||
import static java.util.Collections.singletonList;
|
||||
import static java.util.Collections.singletonMap;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.named;
|
||||
|
||||
|
@ -18,8 +19,10 @@ import io.opentelemetry.context.Scope;
|
|||
import io.opentelemetry.javaagent.instrumentation.api.CallDepthThreadLocalMap;
|
||||
import io.opentelemetry.javaagent.instrumentation.api.CallDepthThreadLocalMap.Depth;
|
||||
import io.opentelemetry.javaagent.instrumentation.api.Java8BytecodeBridge;
|
||||
import io.opentelemetry.javaagent.tooling.Instrumenter;
|
||||
import io.opentelemetry.javaagent.tooling.InstrumentationModule;
|
||||
import io.opentelemetry.javaagent.tooling.TypeInstrumentation;
|
||||
import java.lang.reflect.Method;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import javax.servlet.http.HttpServletResponse;
|
||||
import net.bytebuddy.asm.Advice;
|
||||
|
@ -27,23 +30,12 @@ import net.bytebuddy.description.method.MethodDescription;
|
|||
import net.bytebuddy.description.type.TypeDescription;
|
||||
import net.bytebuddy.matcher.ElementMatcher;
|
||||
|
||||
@AutoService(Instrumenter.class)
|
||||
public final class HttpServletResponseInstrumentation extends Instrumenter.Default {
|
||||
public HttpServletResponseInstrumentation() {
|
||||
@AutoService(InstrumentationModule.class)
|
||||
public final class HttpServletResponseInstrumentationModule extends InstrumentationModule {
|
||||
public HttpServletResponseInstrumentationModule() {
|
||||
super("servlet", "servlet-response");
|
||||
}
|
||||
|
||||
@Override
|
||||
public ElementMatcher<ClassLoader> classLoaderMatcher() {
|
||||
// Optimization for expensive typeMatcher.
|
||||
return hasClassesNamed("javax.servlet.http.HttpServletResponse");
|
||||
}
|
||||
|
||||
@Override
|
||||
public ElementMatcher<TypeDescription> typeMatcher() {
|
||||
return implementsInterface(named("javax.servlet.http.HttpServletResponse"));
|
||||
}
|
||||
|
||||
@Override
|
||||
public String[] helperClassNames() {
|
||||
return new String[] {
|
||||
|
@ -52,8 +44,26 @@ public final class HttpServletResponseInstrumentation extends Instrumenter.Defau
|
|||
}
|
||||
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
return singletonMap(namedOneOf("sendError", "sendRedirect"), SendAdvice.class.getName());
|
||||
public List<TypeInstrumentation> typeInstrumentations() {
|
||||
return singletonList(new HttpServletResponseInstrumentation());
|
||||
}
|
||||
|
||||
private static final class HttpServletResponseInstrumentation implements TypeInstrumentation {
|
||||
@Override
|
||||
public ElementMatcher<ClassLoader> classLoaderMatcher() {
|
||||
// Optimization for expensive typeMatcher.
|
||||
return hasClassesNamed("javax.servlet.http.HttpServletResponse");
|
||||
}
|
||||
|
||||
@Override
|
||||
public ElementMatcher<TypeDescription> typeMatcher() {
|
||||
return implementsInterface(named("javax.servlet.http.HttpServletResponse"));
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
return singletonMap(namedOneOf("sendError", "sendRedirect"), SendAdvice.class.getName());
|
||||
}
|
||||
}
|
||||
|
||||
public static class SendAdvice {
|
|
@ -5,6 +5,7 @@
|
|||
|
||||
package io.opentelemetry.javaagent.instrumentation.sparkjava;
|
||||
|
||||
import static java.util.Collections.singletonList;
|
||||
import static java.util.Collections.singletonMap;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.isPublic;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.named;
|
||||
|
@ -12,11 +13,11 @@ import static net.bytebuddy.matcher.ElementMatchers.returns;
|
|||
import static net.bytebuddy.matcher.ElementMatchers.takesArgument;
|
||||
|
||||
import com.google.auto.service.AutoService;
|
||||
import io.opentelemetry.api.OpenTelemetry;
|
||||
import io.opentelemetry.api.trace.Span;
|
||||
import io.opentelemetry.api.trace.Tracer;
|
||||
import io.opentelemetry.javaagent.instrumentation.api.Java8BytecodeBridge;
|
||||
import io.opentelemetry.javaagent.tooling.Instrumenter;
|
||||
import io.opentelemetry.javaagent.tooling.InstrumentationModule;
|
||||
import io.opentelemetry.javaagent.tooling.TypeInstrumentation;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import net.bytebuddy.asm.Advice;
|
||||
import net.bytebuddy.description.method.MethodDescription;
|
||||
|
@ -24,41 +25,32 @@ import net.bytebuddy.description.type.TypeDescription;
|
|||
import net.bytebuddy.matcher.ElementMatcher;
|
||||
import spark.routematch.RouteMatch;
|
||||
|
||||
@AutoService(Instrumenter.class)
|
||||
public class RoutesInstrumentation extends Instrumenter.Default {
|
||||
@AutoService(InstrumentationModule.class)
|
||||
public class SparkInstrumentationModule extends InstrumentationModule {
|
||||
|
||||
public RoutesInstrumentation() {
|
||||
public SparkInstrumentationModule() {
|
||||
super("sparkjava", "sparkjava-2.4");
|
||||
}
|
||||
|
||||
@Override
|
||||
public ElementMatcher<TypeDescription> typeMatcher() {
|
||||
return named("spark.route.Routes");
|
||||
public List<TypeInstrumentation> typeInstrumentations() {
|
||||
return singletonList(new RoutesInstrumentation());
|
||||
}
|
||||
|
||||
@Override
|
||||
public String[] helperClassNames() {
|
||||
return new String[] {
|
||||
RoutesInstrumentation.class.getName() + "$TracerHolder",
|
||||
};
|
||||
}
|
||||
private static final class RoutesInstrumentation implements TypeInstrumentation {
|
||||
@Override
|
||||
public ElementMatcher<TypeDescription> typeMatcher() {
|
||||
return named("spark.route.Routes");
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
return singletonMap(
|
||||
named("find")
|
||||
.and(takesArgument(0, named("spark.route.HttpMethod")))
|
||||
.and(returns(named("spark.routematch.RouteMatch")))
|
||||
.and(isPublic()),
|
||||
RoutesInstrumentation.class.getName() + "$RoutesAdvice");
|
||||
}
|
||||
|
||||
public static class TracerHolder {
|
||||
private static final Tracer TRACER =
|
||||
OpenTelemetry.getGlobalTracer("io.opentelemetry.auto.sparkjava-2.3");
|
||||
|
||||
public static Tracer tracer() {
|
||||
return TRACER;
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
return singletonMap(
|
||||
named("find")
|
||||
.and(takesArgument(0, named("spark.route.HttpMethod")))
|
||||
.and(returns(named("spark.routematch.RouteMatch")))
|
||||
.and(isPublic()),
|
||||
SparkInstrumentationModule.class.getName() + "$RoutesAdvice");
|
||||
}
|
||||
}
|
||||
|
|
@ -6,6 +6,7 @@
|
|||
package io.opentelemetry.javaagent.instrumentation.spring.data;
|
||||
|
||||
import static io.opentelemetry.javaagent.instrumentation.spring.data.SpringDataTracer.tracer;
|
||||
import static java.util.Collections.singletonList;
|
||||
import static java.util.Collections.singletonMap;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.isConstructor;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.named;
|
||||
|
@ -13,8 +14,10 @@ import static net.bytebuddy.matcher.ElementMatchers.named;
|
|||
import com.google.auto.service.AutoService;
|
||||
import io.opentelemetry.api.trace.Span;
|
||||
import io.opentelemetry.context.Scope;
|
||||
import io.opentelemetry.javaagent.tooling.Instrumenter;
|
||||
import io.opentelemetry.javaagent.tooling.InstrumentationModule;
|
||||
import io.opentelemetry.javaagent.tooling.TypeInstrumentation;
|
||||
import java.lang.reflect.Method;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import net.bytebuddy.asm.Advice;
|
||||
import net.bytebuddy.description.method.MethodDescription;
|
||||
|
@ -28,18 +31,13 @@ import org.springframework.data.repository.core.RepositoryInformation;
|
|||
import org.springframework.data.repository.core.support.RepositoryFactorySupport;
|
||||
import org.springframework.data.repository.core.support.RepositoryProxyPostProcessor;
|
||||
|
||||
@AutoService(Instrumenter.class)
|
||||
public final class SpringRepositoryInstrumentation extends Instrumenter.Default {
|
||||
@AutoService(InstrumentationModule.class)
|
||||
public final class SpringDataInstrumentationModule extends InstrumentationModule {
|
||||
|
||||
public SpringRepositoryInstrumentation() {
|
||||
public SpringDataInstrumentationModule() {
|
||||
super("spring-data");
|
||||
}
|
||||
|
||||
@Override
|
||||
public ElementMatcher<TypeDescription> typeMatcher() {
|
||||
return named("org.springframework.data.repository.core.support.RepositoryFactorySupport");
|
||||
}
|
||||
|
||||
@Override
|
||||
public String[] helperClassNames() {
|
||||
return new String[] {
|
||||
|
@ -50,10 +48,23 @@ public final class SpringRepositoryInstrumentation extends Instrumenter.Default
|
|||
}
|
||||
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
return singletonMap(
|
||||
isConstructor(),
|
||||
SpringRepositoryInstrumentation.class.getName() + "$RepositoryFactorySupportAdvice");
|
||||
public List<TypeInstrumentation> typeInstrumentations() {
|
||||
return singletonList(new RepositoryFactorySupportInstrumentation());
|
||||
}
|
||||
|
||||
private static final class RepositoryFactorySupportInstrumentation
|
||||
implements TypeInstrumentation {
|
||||
@Override
|
||||
public ElementMatcher<TypeDescription> typeMatcher() {
|
||||
return named("org.springframework.data.repository.core.support.RepositoryFactorySupport");
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
return singletonMap(
|
||||
isConstructor(),
|
||||
SpringDataInstrumentationModule.class.getName() + "$RepositoryFactorySupportAdvice");
|
||||
}
|
||||
}
|
||||
|
||||
public static class RepositoryFactorySupportAdvice {
|
|
@ -5,31 +5,29 @@
|
|||
|
||||
package io.opentelemetry.javaagent.instrumentation.spring.scheduling;
|
||||
|
||||
import static java.util.Collections.singletonList;
|
||||
import static java.util.Collections.singletonMap;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.isConstructor;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.named;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.takesArgument;
|
||||
|
||||
import com.google.auto.service.AutoService;
|
||||
import io.opentelemetry.javaagent.tooling.Instrumenter;
|
||||
import io.opentelemetry.javaagent.tooling.InstrumentationModule;
|
||||
import io.opentelemetry.javaagent.tooling.TypeInstrumentation;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import net.bytebuddy.asm.Advice;
|
||||
import net.bytebuddy.description.method.MethodDescription;
|
||||
import net.bytebuddy.description.type.TypeDescription;
|
||||
import net.bytebuddy.matcher.ElementMatcher;
|
||||
|
||||
@AutoService(Instrumenter.class)
|
||||
public final class SpringSchedulingInstrumentation extends Instrumenter.Default {
|
||||
@AutoService(InstrumentationModule.class)
|
||||
public final class SpringSchedulingInstrumentationModule extends InstrumentationModule {
|
||||
|
||||
public SpringSchedulingInstrumentation() {
|
||||
public SpringSchedulingInstrumentationModule() {
|
||||
super("spring-scheduling");
|
||||
}
|
||||
|
||||
@Override
|
||||
public ElementMatcher<TypeDescription> typeMatcher() {
|
||||
return named("org.springframework.scheduling.config.Task");
|
||||
}
|
||||
|
||||
@Override
|
||||
public String[] helperClassNames() {
|
||||
return new String[] {
|
||||
|
@ -38,10 +36,22 @@ public final class SpringSchedulingInstrumentation extends Instrumenter.Default
|
|||
}
|
||||
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
return singletonMap(
|
||||
isConstructor().and(takesArgument(0, Runnable.class)),
|
||||
SpringSchedulingInstrumentation.class.getName() + "$SpringSchedulingAdvice");
|
||||
public List<TypeInstrumentation> typeInstrumentations() {
|
||||
return singletonList(new TaskInstrumentation());
|
||||
}
|
||||
|
||||
private static final class TaskInstrumentation implements TypeInstrumentation {
|
||||
@Override
|
||||
public ElementMatcher<TypeDescription> typeMatcher() {
|
||||
return named("org.springframework.scheduling.config.Task");
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
return singletonMap(
|
||||
isConstructor().and(takesArgument(0, Runnable.class)),
|
||||
SpringSchedulingInstrumentationModule.class.getName() + "$SpringSchedulingAdvice");
|
||||
}
|
||||
}
|
||||
|
||||
public static class SpringSchedulingAdvice {
|
|
@ -7,31 +7,28 @@ package io.opentelemetry.javaagent.instrumentation.spring.webflux.client;
|
|||
|
||||
import static io.opentelemetry.javaagent.tooling.ClassLoaderMatcher.hasClassesNamed;
|
||||
import static io.opentelemetry.javaagent.tooling.bytebuddy.matcher.AgentElementMatchers.implementsInterface;
|
||||
import static java.util.Collections.singletonList;
|
||||
import static java.util.Collections.singletonMap;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.isMethod;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.isPublic;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.named;
|
||||
|
||||
import com.google.auto.service.AutoService;
|
||||
import io.opentelemetry.javaagent.tooling.Instrumenter;
|
||||
import io.opentelemetry.javaagent.tooling.InstrumentationModule;
|
||||
import io.opentelemetry.javaagent.tooling.TypeInstrumentation;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import net.bytebuddy.description.method.MethodDescription;
|
||||
import net.bytebuddy.description.type.TypeDescription;
|
||||
import net.bytebuddy.matcher.ElementMatcher;
|
||||
|
||||
@AutoService(Instrumenter.class)
|
||||
public class WebClientFilterInstrumentation extends Instrumenter.Default {
|
||||
@AutoService(InstrumentationModule.class)
|
||||
public class WebfluxClientInstrumentationModule extends InstrumentationModule {
|
||||
|
||||
public WebClientFilterInstrumentation() {
|
||||
public WebfluxClientInstrumentationModule() {
|
||||
super("spring-webflux", "spring-webflux-client");
|
||||
}
|
||||
|
||||
@Override
|
||||
public ElementMatcher<ClassLoader> classLoaderMatcher() {
|
||||
// Optimization for expensive typeMatcher.
|
||||
return hasClassesNamed("org.springframework.web.reactive.function.client.WebClient");
|
||||
}
|
||||
|
||||
@Override
|
||||
public String[] helperClassNames() {
|
||||
return new String[] {
|
||||
|
@ -44,14 +41,27 @@ public class WebClientFilterInstrumentation extends Instrumenter.Default {
|
|||
}
|
||||
|
||||
@Override
|
||||
public ElementMatcher<? super TypeDescription> typeMatcher() {
|
||||
return implementsInterface(
|
||||
named("org.springframework.web.reactive.function.client.WebClient$Builder"));
|
||||
public List<TypeInstrumentation> typeInstrumentations() {
|
||||
return singletonList(new WebClientBuilderInstrumentation());
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
return singletonMap(
|
||||
isMethod().and(isPublic()).and(named("build")), packageName + ".WebClientFilterAdvice");
|
||||
private static final class WebClientBuilderInstrumentation implements TypeInstrumentation {
|
||||
@Override
|
||||
public ElementMatcher<ClassLoader> classLoaderMatcher() {
|
||||
// Optimization for expensive typeMatcher.
|
||||
return hasClassesNamed("org.springframework.web.reactive.function.client.WebClient");
|
||||
}
|
||||
|
||||
@Override
|
||||
public ElementMatcher<? super TypeDescription> typeMatcher() {
|
||||
return implementsInterface(
|
||||
named("org.springframework.web.reactive.function.client.WebClient$Builder"));
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
return singletonMap(
|
||||
isMethod().and(isPublic()).and(named("build")), WebClientFilterAdvice.class.getName());
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,25 +0,0 @@
|
|||
/*
|
||||
* Copyright The OpenTelemetry Authors
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
|
||||
package io.opentelemetry.javaagent.instrumentation.spring.webflux.server;
|
||||
|
||||
import io.opentelemetry.javaagent.tooling.Instrumenter;
|
||||
|
||||
public abstract class AbstractWebfluxInstrumentation extends Instrumenter.Default {
|
||||
|
||||
public AbstractWebfluxInstrumentation(String... additionalNames) {
|
||||
super("spring-webflux", additionalNames);
|
||||
}
|
||||
|
||||
@Override
|
||||
public String[] helperClassNames() {
|
||||
return new String[] {
|
||||
packageName + ".SpringWebfluxHttpServerTracer",
|
||||
packageName + ".AdviceUtils",
|
||||
packageName + ".AdviceUtils$SpanFinishingSubscriber",
|
||||
packageName + ".RouteOnSuccessOrError"
|
||||
};
|
||||
}
|
||||
}
|
|
@ -12,15 +12,13 @@ import static net.bytebuddy.matcher.ElementMatchers.named;
|
|||
import static net.bytebuddy.matcher.ElementMatchers.takesArgument;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.takesArguments;
|
||||
|
||||
import com.google.auto.service.AutoService;
|
||||
import io.opentelemetry.javaagent.tooling.Instrumenter;
|
||||
import io.opentelemetry.javaagent.tooling.TypeInstrumentation;
|
||||
import java.util.Map;
|
||||
import net.bytebuddy.description.method.MethodDescription;
|
||||
import net.bytebuddy.description.type.TypeDescription;
|
||||
import net.bytebuddy.matcher.ElementMatcher;
|
||||
|
||||
@AutoService(Instrumenter.class)
|
||||
public final class DispatcherHandlerInstrumentation extends AbstractWebfluxInstrumentation {
|
||||
final class DispatcherHandlerInstrumentation implements TypeInstrumentation {
|
||||
|
||||
@Override
|
||||
public ElementMatcher<TypeDescription> typeMatcher() {
|
||||
|
@ -35,7 +33,6 @@ public final class DispatcherHandlerInstrumentation extends AbstractWebfluxInstr
|
|||
.and(named("handle"))
|
||||
.and(takesArgument(0, named("org.springframework.web.server.ServerWebExchange")))
|
||||
.and(takesArguments(1)),
|
||||
// Cannot reference class directly here because it would lead to class load failure on Java7
|
||||
packageName + ".DispatcherHandlerAdvice");
|
||||
DispatcherHandlerAdvice.class.getName());
|
||||
}
|
||||
}
|
||||
|
|
|
@ -16,15 +16,13 @@ import static net.bytebuddy.matcher.ElementMatchers.not;
|
|||
import static net.bytebuddy.matcher.ElementMatchers.takesArgument;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.takesArguments;
|
||||
|
||||
import com.google.auto.service.AutoService;
|
||||
import io.opentelemetry.javaagent.tooling.Instrumenter;
|
||||
import io.opentelemetry.javaagent.tooling.TypeInstrumentation;
|
||||
import java.util.Map;
|
||||
import net.bytebuddy.description.method.MethodDescription;
|
||||
import net.bytebuddy.description.type.TypeDescription;
|
||||
import net.bytebuddy.matcher.ElementMatcher;
|
||||
|
||||
@AutoService(Instrumenter.class)
|
||||
public final class HandlerAdapterInstrumentation extends AbstractWebfluxInstrumentation {
|
||||
final class HandlerAdapterInstrumentation implements TypeInstrumentation {
|
||||
|
||||
@Override
|
||||
public ElementMatcher<ClassLoader> classLoaderMatcher() {
|
||||
|
@ -47,7 +45,6 @@ public final class HandlerAdapterInstrumentation extends AbstractWebfluxInstrume
|
|||
.and(takesArgument(0, named("org.springframework.web.server.ServerWebExchange")))
|
||||
.and(takesArgument(1, named("java.lang.Object")))
|
||||
.and(takesArguments(2)),
|
||||
// Cannot reference class directly here because it would lead to class load failure on Java7
|
||||
packageName + ".HandlerAdapterAdvice");
|
||||
HandlerAdapterAdvice.class.getName());
|
||||
}
|
||||
}
|
||||
|
|
|
@ -16,19 +16,13 @@ import static net.bytebuddy.matcher.ElementMatchers.not;
|
|||
import static net.bytebuddy.matcher.ElementMatchers.takesArgument;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.takesArguments;
|
||||
|
||||
import com.google.auto.service.AutoService;
|
||||
import io.opentelemetry.javaagent.tooling.Instrumenter;
|
||||
import io.opentelemetry.javaagent.tooling.TypeInstrumentation;
|
||||
import java.util.Map;
|
||||
import net.bytebuddy.description.method.MethodDescription;
|
||||
import net.bytebuddy.description.type.TypeDescription;
|
||||
import net.bytebuddy.matcher.ElementMatcher;
|
||||
|
||||
@AutoService(Instrumenter.class)
|
||||
public final class RouterFunctionInstrumentation extends AbstractWebfluxInstrumentation {
|
||||
|
||||
public RouterFunctionInstrumentation() {
|
||||
super("spring-webflux-functional");
|
||||
}
|
||||
final class RouterFunctionInstrumentation implements TypeInstrumentation {
|
||||
|
||||
@Override
|
||||
public ElementMatcher<ClassLoader> classLoaderMatcher() {
|
||||
|
@ -56,7 +50,6 @@ public final class RouterFunctionInstrumentation extends AbstractWebfluxInstrume
|
|||
takesArgument(
|
||||
0, named("org.springframework.web.reactive.function.server.ServerRequest")))
|
||||
.and(takesArguments(1)),
|
||||
// Cannot reference class directly here because it would lead to class load failure on Java7
|
||||
packageName + ".RouterFunctionAdvice");
|
||||
RouterFunctionAdvice.class.getName());
|
||||
}
|
||||
}
|
||||
|
|
|
@ -0,0 +1,39 @@
|
|||
/*
|
||||
* Copyright The OpenTelemetry Authors
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
|
||||
package io.opentelemetry.javaagent.instrumentation.spring.webflux.server;
|
||||
|
||||
import static java.util.Arrays.asList;
|
||||
|
||||
import com.google.auto.service.AutoService;
|
||||
import io.opentelemetry.javaagent.tooling.InstrumentationModule;
|
||||
import io.opentelemetry.javaagent.tooling.TypeInstrumentation;
|
||||
import java.util.List;
|
||||
|
||||
@AutoService(InstrumentationModule.class)
|
||||
public class WebfluxServerInstrumentationModule extends InstrumentationModule {
|
||||
|
||||
public WebfluxServerInstrumentationModule() {
|
||||
super("spring-webflux", "spring-webflux-server");
|
||||
}
|
||||
|
||||
@Override
|
||||
public String[] helperClassNames() {
|
||||
return new String[] {
|
||||
packageName + ".SpringWebfluxHttpServerTracer",
|
||||
packageName + ".AdviceUtils",
|
||||
packageName + ".AdviceUtils$SpanFinishingSubscriber",
|
||||
packageName + ".RouteOnSuccessOrError"
|
||||
};
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<TypeInstrumentation> typeInstrumentations() {
|
||||
return asList(
|
||||
new DispatcherHandlerInstrumentation(),
|
||||
new HandlerAdapterInstrumentation(),
|
||||
new RouterFunctionInstrumentation());
|
||||
}
|
||||
}
|
|
@ -6,6 +6,7 @@
|
|||
package io.opentelemetry.javaagent.instrumentation.spymemcached;
|
||||
|
||||
import static io.opentelemetry.javaagent.tooling.matcher.NameMatchers.namedOneOf;
|
||||
import static java.util.Collections.singletonList;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.isMethod;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.isPublic;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.named;
|
||||
|
@ -14,8 +15,10 @@ import static net.bytebuddy.matcher.ElementMatchers.returns;
|
|||
|
||||
import com.google.auto.service.AutoService;
|
||||
import io.opentelemetry.javaagent.instrumentation.api.CallDepthThreadLocalMap;
|
||||
import io.opentelemetry.javaagent.tooling.Instrumenter;
|
||||
import io.opentelemetry.javaagent.tooling.InstrumentationModule;
|
||||
import io.opentelemetry.javaagent.tooling.TypeInstrumentation;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import net.bytebuddy.asm.Advice;
|
||||
import net.bytebuddy.description.method.MethodDescription;
|
||||
|
@ -26,20 +29,13 @@ import net.spy.memcached.internal.BulkFuture;
|
|||
import net.spy.memcached.internal.GetFuture;
|
||||
import net.spy.memcached.internal.OperationFuture;
|
||||
|
||||
@AutoService(Instrumenter.class)
|
||||
public final class MemcachedClientInstrumentation extends Instrumenter.Default {
|
||||
@AutoService(InstrumentationModule.class)
|
||||
public final class SpymemcachedInstrumentationModule extends InstrumentationModule {
|
||||
|
||||
private static final String MEMCACHED_PACKAGE = "net.spy.memcached";
|
||||
|
||||
public MemcachedClientInstrumentation() {
|
||||
public SpymemcachedInstrumentationModule() {
|
||||
super("spymemcached");
|
||||
}
|
||||
|
||||
@Override
|
||||
public ElementMatcher<TypeDescription> typeMatcher() {
|
||||
return named(MEMCACHED_PACKAGE + ".MemcachedClient");
|
||||
}
|
||||
|
||||
@Override
|
||||
public String[] helperClassNames() {
|
||||
return new String[] {
|
||||
|
@ -53,28 +49,40 @@ public final class MemcachedClientInstrumentation extends Instrumenter.Default {
|
|||
}
|
||||
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
Map<ElementMatcher<? super MethodDescription>, String> transformers = new HashMap<>();
|
||||
transformers.put(
|
||||
isMethod()
|
||||
.and(isPublic())
|
||||
.and(returns(named(MEMCACHED_PACKAGE + ".internal.OperationFuture")))
|
||||
/*
|
||||
Flush seems to have a bug when listeners may not be always called.
|
||||
Also tracing flush is probably of a very limited value.
|
||||
*/
|
||||
.and(not(named("flush"))),
|
||||
MemcachedClientInstrumentation.class.getName() + "$AsyncOperationAdvice");
|
||||
transformers.put(
|
||||
isMethod().and(isPublic()).and(returns(named(MEMCACHED_PACKAGE + ".internal.GetFuture"))),
|
||||
MemcachedClientInstrumentation.class.getName() + "$AsyncGetAdvice");
|
||||
transformers.put(
|
||||
isMethod().and(isPublic()).and(returns(named(MEMCACHED_PACKAGE + ".internal.BulkFuture"))),
|
||||
MemcachedClientInstrumentation.class.getName() + "$AsyncBulkAdvice");
|
||||
transformers.put(
|
||||
isMethod().and(isPublic()).and(namedOneOf("incr", "decr")),
|
||||
MemcachedClientInstrumentation.class.getName() + "$SyncOperationAdvice");
|
||||
return transformers;
|
||||
public List<TypeInstrumentation> typeInstrumentations() {
|
||||
return singletonList(new MemcachedClientInstrumentation());
|
||||
}
|
||||
|
||||
private static final class MemcachedClientInstrumentation implements TypeInstrumentation {
|
||||
@Override
|
||||
public ElementMatcher<TypeDescription> typeMatcher() {
|
||||
return named("net.spy.memcached.MemcachedClient");
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
Map<ElementMatcher<? super MethodDescription>, String> transformers = new HashMap<>();
|
||||
transformers.put(
|
||||
isMethod()
|
||||
.and(isPublic())
|
||||
.and(returns(named("net.spy.memcached.internal.OperationFuture")))
|
||||
/*
|
||||
Flush seems to have a bug when listeners may not be always called.
|
||||
Also tracing flush is probably of a very limited value.
|
||||
*/
|
||||
.and(not(named("flush"))),
|
||||
SpymemcachedInstrumentationModule.class.getName() + "$AsyncOperationAdvice");
|
||||
transformers.put(
|
||||
isMethod().and(isPublic()).and(returns(named("net.spy.memcached.internal.GetFuture"))),
|
||||
SpymemcachedInstrumentationModule.class.getName() + "$AsyncGetAdvice");
|
||||
transformers.put(
|
||||
isMethod().and(isPublic()).and(returns(named("net.spy.memcached.internal.BulkFuture"))),
|
||||
SpymemcachedInstrumentationModule.class.getName() + "$AsyncBulkAdvice");
|
||||
transformers.put(
|
||||
isMethod().and(isPublic()).and(namedOneOf("incr", "decr")),
|
||||
SpymemcachedInstrumentationModule.class.getName() + "$SyncOperationAdvice");
|
||||
return transformers;
|
||||
}
|
||||
}
|
||||
|
||||
public static class AsyncOperationAdvice {
|
||||
|
@ -89,7 +97,7 @@ public final class MemcachedClientInstrumentation extends Instrumenter.Default {
|
|||
@Advice.Enter int callDepth,
|
||||
@Advice.This MemcachedClient client,
|
||||
@Advice.Origin("#m") String methodName,
|
||||
@Advice.Return OperationFuture future) {
|
||||
@Advice.Return OperationFuture<?> future) {
|
||||
if (callDepth > 0) {
|
||||
return;
|
||||
}
|
||||
|
@ -115,7 +123,7 @@ public final class MemcachedClientInstrumentation extends Instrumenter.Default {
|
|||
@Advice.Enter int callDepth,
|
||||
@Advice.This MemcachedClient client,
|
||||
@Advice.Origin("#m") String methodName,
|
||||
@Advice.Return GetFuture future) {
|
||||
@Advice.Return GetFuture<?> future) {
|
||||
if (callDepth > 0) {
|
||||
return;
|
||||
}
|
||||
|
@ -141,7 +149,7 @@ public final class MemcachedClientInstrumentation extends Instrumenter.Default {
|
|||
@Advice.Enter int callDepth,
|
||||
@Advice.This MemcachedClient client,
|
||||
@Advice.Origin("#m") String methodName,
|
||||
@Advice.Return BulkFuture future) {
|
||||
@Advice.Return BulkFuture<?> future) {
|
||||
if (callDepth > 0) {
|
||||
return;
|
||||
}
|
|
@ -19,7 +19,6 @@ import static net.bytebuddy.matcher.ElementMatchers.named;
|
|||
import static net.bytebuddy.matcher.ElementMatchers.not;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.returns;
|
||||
|
||||
import com.google.auto.service.AutoService;
|
||||
import com.google.common.util.concurrent.FutureCallback;
|
||||
import com.google.common.util.concurrent.Futures;
|
||||
import com.google.common.util.concurrent.ListenableFuture;
|
||||
|
@ -27,19 +26,14 @@ import com.twilio.Twilio;
|
|||
import io.opentelemetry.api.trace.Span;
|
||||
import io.opentelemetry.javaagent.instrumentation.api.CallDepthThreadLocalMap;
|
||||
import io.opentelemetry.javaagent.instrumentation.api.SpanWithScope;
|
||||
import io.opentelemetry.javaagent.tooling.Instrumenter;
|
||||
import io.opentelemetry.javaagent.tooling.TypeInstrumentation;
|
||||
import java.util.Map;
|
||||
import net.bytebuddy.asm.Advice;
|
||||
import net.bytebuddy.description.method.MethodDescription;
|
||||
import net.bytebuddy.matcher.ElementMatcher;
|
||||
|
||||
/** Instrument the Twilio SDK to identify calls as a seperate service. */
|
||||
@AutoService(Instrumenter.class)
|
||||
public class TwilioAsyncInstrumentation extends Instrumenter.Default {
|
||||
|
||||
public TwilioAsyncInstrumentation() {
|
||||
super("twilio-sdk");
|
||||
}
|
||||
/** Instrument the Twilio SDK to identify calls as a separate service. */
|
||||
final class TwilioAsyncInstrumentation implements TypeInstrumentation {
|
||||
|
||||
@Override
|
||||
public ElementMatcher<ClassLoader> classLoaderMatcher() {
|
||||
|
@ -59,15 +53,6 @@ public class TwilioAsyncInstrumentation extends Instrumenter.Default {
|
|||
"com.twilio.base.Updater"));
|
||||
}
|
||||
|
||||
/** Return the helper classes which will be available for use in instrumentation. */
|
||||
@Override
|
||||
public String[] helperClassNames() {
|
||||
return new String[] {
|
||||
packageName + ".TwilioClientDecorator",
|
||||
packageName + ".TwilioAsyncInstrumentation$SpanFinishingCallback",
|
||||
};
|
||||
}
|
||||
|
||||
/** Return bytebuddy transformers for instrumenting the Twilio SDK. */
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
|
@ -122,7 +107,7 @@ public class TwilioAsyncInstrumentation extends Instrumenter.Default {
|
|||
public static void methodExit(
|
||||
@Advice.Enter SpanWithScope spanWithScope,
|
||||
@Advice.Thrown Throwable throwable,
|
||||
@Advice.Return ListenableFuture response) {
|
||||
@Advice.Return ListenableFuture<?> response) {
|
||||
if (spanWithScope == null) {
|
||||
return;
|
||||
}
|
||||
|
@ -142,7 +127,7 @@ public class TwilioAsyncInstrumentation extends Instrumenter.Default {
|
|||
// We're calling an async operation, we still need to finish the span when it's
|
||||
// complete and report the results; set an appropriate callback
|
||||
Futures.addCallback(
|
||||
response, new SpanFinishingCallback(span), Twilio.getExecutorService());
|
||||
response, new SpanFinishingCallback<>(span), Twilio.getExecutorService());
|
||||
}
|
||||
} finally {
|
||||
spanWithScope.closeScope();
|
||||
|
@ -155,7 +140,7 @@ public class TwilioAsyncInstrumentation extends Instrumenter.Default {
|
|||
* FutureCallback, which automatically finishes the span and annotates with any appropriate
|
||||
* metadata on a potential failure.
|
||||
*/
|
||||
public static class SpanFinishingCallback implements FutureCallback {
|
||||
public static class SpanFinishingCallback<T> implements FutureCallback<T> {
|
||||
|
||||
/** Span that we should finish and annotate when the future is complete. */
|
||||
private final Span span;
|
||||
|
|
|
@ -0,0 +1,33 @@
|
|||
/*
|
||||
* Copyright The OpenTelemetry Authors
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
|
||||
package io.opentelemetry.javaagent.instrumentation.twilio;
|
||||
|
||||
import static java.util.Arrays.asList;
|
||||
|
||||
import com.google.auto.service.AutoService;
|
||||
import io.opentelemetry.javaagent.tooling.InstrumentationModule;
|
||||
import io.opentelemetry.javaagent.tooling.TypeInstrumentation;
|
||||
import java.util.List;
|
||||
|
||||
@AutoService(InstrumentationModule.class)
|
||||
public class TwilioInstrumentationModule extends InstrumentationModule {
|
||||
public TwilioInstrumentationModule() {
|
||||
super("twilio-sdk");
|
||||
}
|
||||
|
||||
@Override
|
||||
public String[] helperClassNames() {
|
||||
return new String[] {
|
||||
packageName + ".TwilioClientDecorator",
|
||||
packageName + ".TwilioAsyncInstrumentation$SpanFinishingCallback",
|
||||
};
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<TypeInstrumentation> typeInstrumentations() {
|
||||
return asList(new TwilioAsyncInstrumentation(), new TwilioSyncInstrumentation());
|
||||
}
|
||||
}
|
|
@ -17,24 +17,18 @@ import static net.bytebuddy.matcher.ElementMatchers.isMethod;
|
|||
import static net.bytebuddy.matcher.ElementMatchers.isPublic;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.not;
|
||||
|
||||
import com.google.auto.service.AutoService;
|
||||
import com.twilio.Twilio;
|
||||
import io.opentelemetry.api.trace.Span;
|
||||
import io.opentelemetry.javaagent.instrumentation.api.CallDepthThreadLocalMap;
|
||||
import io.opentelemetry.javaagent.instrumentation.api.SpanWithScope;
|
||||
import io.opentelemetry.javaagent.tooling.Instrumenter;
|
||||
import io.opentelemetry.javaagent.tooling.TypeInstrumentation;
|
||||
import java.util.Map;
|
||||
import net.bytebuddy.asm.Advice;
|
||||
import net.bytebuddy.description.method.MethodDescription;
|
||||
import net.bytebuddy.matcher.ElementMatcher;
|
||||
|
||||
/** Instrument the Twilio SDK to identify calls as a seperate service. */
|
||||
@AutoService(Instrumenter.class)
|
||||
public class TwilioSyncInstrumentation extends Instrumenter.Default {
|
||||
|
||||
public TwilioSyncInstrumentation() {
|
||||
super("twilio-sdk");
|
||||
}
|
||||
/** Instrument the Twilio SDK to identify calls as a separate service. */
|
||||
final class TwilioSyncInstrumentation implements TypeInstrumentation {
|
||||
|
||||
@Override
|
||||
public ElementMatcher<ClassLoader> classLoaderMatcher() {
|
||||
|
@ -56,14 +50,6 @@ public class TwilioSyncInstrumentation extends Instrumenter.Default {
|
|||
"com.twilio.base.Updater"));
|
||||
}
|
||||
|
||||
/** Return the helper classes which will be available for use in instrumentation. */
|
||||
@Override
|
||||
public String[] helperClassNames() {
|
||||
return new String[] {
|
||||
packageName + ".TwilioClientDecorator",
|
||||
};
|
||||
}
|
||||
|
||||
/** Return bytebuddy transformers for instrumenting the Twilio SDK. */
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
|
|
|
@ -7,6 +7,7 @@ package io.opentelemetry.javaagent.instrumentation.vertx;
|
|||
|
||||
import static io.opentelemetry.javaagent.tooling.ClassLoaderMatcher.hasClassesNamed;
|
||||
import static io.opentelemetry.javaagent.tooling.bytebuddy.matcher.AgentElementMatchers.safeHasSuperType;
|
||||
import static java.util.Collections.singletonList;
|
||||
import static java.util.Collections.singletonMap;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.isInterface;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.isMethod;
|
||||
|
@ -15,32 +16,24 @@ import static net.bytebuddy.matcher.ElementMatchers.not;
|
|||
import static net.bytebuddy.matcher.ElementMatchers.takesArgument;
|
||||
|
||||
import com.google.auto.service.AutoService;
|
||||
import io.opentelemetry.javaagent.tooling.Instrumenter;
|
||||
import io.opentelemetry.javaagent.tooling.InstrumentationModule;
|
||||
import io.opentelemetry.javaagent.tooling.TypeInstrumentation;
|
||||
import io.vertx.core.Handler;
|
||||
import io.vertx.ext.web.RoutingContext;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import net.bytebuddy.asm.Advice;
|
||||
import net.bytebuddy.description.method.MethodDescription;
|
||||
import net.bytebuddy.description.type.TypeDescription;
|
||||
import net.bytebuddy.matcher.ElementMatcher;
|
||||
|
||||
@AutoService(Instrumenter.class)
|
||||
public final class RouteInstrumentation extends Instrumenter.Default {
|
||||
@AutoService(InstrumentationModule.class)
|
||||
public final class VertxInstrumentationModule extends InstrumentationModule {
|
||||
|
||||
public RouteInstrumentation() {
|
||||
public VertxInstrumentationModule() {
|
||||
super("vertx");
|
||||
}
|
||||
|
||||
@Override
|
||||
public ElementMatcher<ClassLoader> classLoaderMatcher() {
|
||||
return hasClassesNamed("io.vertx.ext.web.Route");
|
||||
}
|
||||
|
||||
@Override
|
||||
public ElementMatcher<TypeDescription> typeMatcher() {
|
||||
return not(isInterface()).and(safeHasSuperType(named("io.vertx.ext.web.Route")));
|
||||
}
|
||||
|
||||
@Override
|
||||
public String[] helperClassNames() {
|
||||
return new String[] {
|
||||
|
@ -49,10 +42,27 @@ public final class RouteInstrumentation extends Instrumenter.Default {
|
|||
}
|
||||
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
return singletonMap(
|
||||
isMethod().and(named("handler")).and(takesArgument(0, named("io.vertx.core.Handler"))),
|
||||
RouteInstrumentation.class.getName() + "$RouteAdvice");
|
||||
public List<TypeInstrumentation> typeInstrumentations() {
|
||||
return singletonList(new RouteInstrumentation());
|
||||
}
|
||||
|
||||
private static final class RouteInstrumentation implements TypeInstrumentation {
|
||||
@Override
|
||||
public ElementMatcher<ClassLoader> classLoaderMatcher() {
|
||||
return hasClassesNamed("io.vertx.ext.web.Route");
|
||||
}
|
||||
|
||||
@Override
|
||||
public ElementMatcher<TypeDescription> typeMatcher() {
|
||||
return not(isInterface()).and(safeHasSuperType(named("io.vertx.ext.web.Route")));
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
return singletonMap(
|
||||
isMethod().and(named("handler")).and(takesArgument(0, named("io.vertx.core.Handler"))),
|
||||
VertxInstrumentationModule.class.getName() + "$RouteAdvice");
|
||||
}
|
||||
}
|
||||
|
||||
public static class RouteAdvice {
|
|
@ -2,9 +2,9 @@
|
|||
* The majority of monitoring needs of Vert.x application is covered by generic instrumentations.
|
||||
* Such as those of netty or JDBC.
|
||||
*
|
||||
* <p>{@link io.opentelemetry.javaagent.instrumentation.vertx.RouteInstrumentation} wraps all Vert.x
|
||||
* route handlers in order to update the name of the currently active SERVER span with the name of
|
||||
* route. This is, arguably, a much more user-friendly name that defaults provided by HTTP server
|
||||
* instrumentations.
|
||||
* <p>{@link io.opentelemetry.javaagent.instrumentation.vertx.VertxInstrumentationModule} wraps all
|
||||
* Vert.x route handlers in order to update the name of the currently active SERVER span with the
|
||||
* name of route. This is, arguably, a much more user-friendly name that defaults provided by HTTP
|
||||
* server instrumentations.
|
||||
*/
|
||||
package io.opentelemetry.javaagent.instrumentation.vertx;
|
||||
|
|
|
@ -6,16 +6,19 @@
|
|||
package io.opentelemetry.javaagent.instrumentation.vertx.reactive;
|
||||
|
||||
import static io.opentelemetry.javaagent.tooling.ClassLoaderMatcher.hasClassesNamed;
|
||||
import static java.util.Collections.singletonList;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.isConstructor;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.named;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.takesArgument;
|
||||
|
||||
import com.google.auto.service.AutoService;
|
||||
import io.opentelemetry.javaagent.instrumentation.api.Java8BytecodeBridge;
|
||||
import io.opentelemetry.javaagent.tooling.Instrumenter;
|
||||
import io.opentelemetry.javaagent.tooling.InstrumentationModule;
|
||||
import io.opentelemetry.javaagent.tooling.TypeInstrumentation;
|
||||
import io.vertx.core.AsyncResult;
|
||||
import io.vertx.core.Handler;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.function.Consumer;
|
||||
import net.bytebuddy.asm.Advice;
|
||||
|
@ -24,26 +27,13 @@ import net.bytebuddy.description.type.TypeDescription;
|
|||
import net.bytebuddy.matcher.ElementMatcher;
|
||||
|
||||
/** This instrumentation allows span context propagation across Vert.x reactive executions. */
|
||||
@AutoService(Instrumenter.class)
|
||||
public class VertxRxInstrumentation extends Instrumenter.Default {
|
||||
@AutoService(InstrumentationModule.class)
|
||||
public class VertxRxInstrumentationModule extends InstrumentationModule {
|
||||
|
||||
public VertxRxInstrumentation() {
|
||||
public VertxRxInstrumentationModule() {
|
||||
super("vertx");
|
||||
}
|
||||
|
||||
@Override
|
||||
public ElementMatcher<ClassLoader> classLoaderMatcher() {
|
||||
// Different versions of Vert.x has this class in different packages
|
||||
return hasClassesNamed("io.vertx.reactivex.core.impl.AsyncResultSingle")
|
||||
.or(hasClassesNamed("io.vertx.reactivex.impl.AsyncResultSingle"));
|
||||
}
|
||||
|
||||
@Override
|
||||
public ElementMatcher<? super TypeDescription> typeMatcher() {
|
||||
return named("io.vertx.reactivex.core.impl.AsyncResultSingle")
|
||||
.or(named("io.vertx.reactivex.impl.AsyncResultSingle"));
|
||||
}
|
||||
|
||||
@Override
|
||||
public String[] helperClassNames() {
|
||||
return new String[] {
|
||||
|
@ -52,15 +42,35 @@ public class VertxRxInstrumentation extends Instrumenter.Default {
|
|||
}
|
||||
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
Map<ElementMatcher<? super MethodDescription>, String> result = new HashMap<>();
|
||||
result.put(
|
||||
isConstructor().and(takesArgument(0, named("io.vertx.core.Handler"))),
|
||||
this.getClass().getName() + "$AsyncResultSingleHandlerAdvice");
|
||||
result.put(
|
||||
isConstructor().and(takesArgument(0, named("java.util.function.Consumer"))),
|
||||
this.getClass().getName() + "$AsyncResultSingleConsumerAdvice");
|
||||
return result;
|
||||
public List<TypeInstrumentation> typeInstrumentations() {
|
||||
return singletonList(new AsyncResultSingleInstrumentation());
|
||||
}
|
||||
|
||||
private static final class AsyncResultSingleInstrumentation implements TypeInstrumentation {
|
||||
@Override
|
||||
public ElementMatcher<ClassLoader> classLoaderMatcher() {
|
||||
// Different versions of Vert.x has this class in different packages
|
||||
return hasClassesNamed("io.vertx.reactivex.core.impl.AsyncResultSingle")
|
||||
.or(hasClassesNamed("io.vertx.reactivex.impl.AsyncResultSingle"));
|
||||
}
|
||||
|
||||
@Override
|
||||
public ElementMatcher<? super TypeDescription> typeMatcher() {
|
||||
return named("io.vertx.reactivex.core.impl.AsyncResultSingle")
|
||||
.or(named("io.vertx.reactivex.impl.AsyncResultSingle"));
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<? extends ElementMatcher<? super MethodDescription>, String> transformers() {
|
||||
Map<ElementMatcher<? super MethodDescription>, String> result = new HashMap<>();
|
||||
result.put(
|
||||
isConstructor().and(takesArgument(0, named("io.vertx.core.Handler"))),
|
||||
VertxRxInstrumentationModule.class.getName() + "$AsyncResultSingleHandlerAdvice");
|
||||
result.put(
|
||||
isConstructor().and(takesArgument(0, named("java.util.function.Consumer"))),
|
||||
VertxRxInstrumentationModule.class.getName() + "$AsyncResultSingleConsumerAdvice");
|
||||
return result;
|
||||
}
|
||||
}
|
||||
|
||||
public static class AsyncResultSingleHandlerAdvice {
|
|
@ -2,8 +2,8 @@
|
|||
* The majority of monitoring needs of Vert.x application is covered by generic instrumentations.
|
||||
* Such as those of netty or JDBC.
|
||||
*
|
||||
* <p>{@link io.opentelemetry.javaagent.instrumentation.vertx.reactive.VertxRxInstrumentation} wraps
|
||||
* {code AsyncResultSingle} classes from Vert.x RxJava library to ensure proper span context
|
||||
* <p>{@link io.opentelemetry.javaagent.instrumentation.vertx.reactive.VertxRxInstrumentationModule}
|
||||
* wraps {code AsyncResultSingle} classes from Vert.x RxJava library to ensure proper span context
|
||||
* propagation in reactive Vert.x applications.
|
||||
*/
|
||||
package io.opentelemetry.javaagent.instrumentation.vertx.reactive;
|
||||
|
|
Loading…
Reference in New Issue