Enable PrivateConstructorForUtilityClass errorprone check (#6427)

* PrivateConstructorForUtilityClass

* Advice

* More advice

* More

* More advice

* More

* Spotless

* Fix

* Fix

* Fix

* A better solution

* Revert

* More

* Fix

* Spotless

* Fix
This commit is contained in:
Trask Stalnaker 2022-08-10 01:30:22 -07:00 committed by GitHub
parent 643121ff41
commit 68a9f20eb3
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
89 changed files with 376 additions and 158 deletions

View File

@ -89,9 +89,8 @@ tasks {
// allow UPPERCASE type parameter names
disable("TypeParameterNaming")
// Great check, but for bytecode manipulation it's too common to separate over
// onEnter / onExit
// TODO(anuraaga): Only disable for auto instrumentation project.
// In bytecode instrumentation it's very common to separate across onEnter / onExit
// TODO(anuraaga): Only disable for javaagent instrumentation modules.
disable("MustBeClosedChecker")
// Common to avoid an allocation. Revisit if it's worth opt-in suppressing instead of
@ -106,8 +105,7 @@ tasks {
// some moving.
disable("DefaultPackage")
// TODO(anuraaga): Remove this, all our advice classes miss constructors but probably should
// address this.
// we use modified OtelPrivateConstructorForUtilityClass which ignores *Advice classes
disable("PrivateConstructorForUtilityClass")
// TODO(anuraaga): Remove this, probably after instrumenter API migration instead of dealing

View File

@ -0,0 +1,43 @@
/*
* Copyright The OpenTelemetry Authors
* SPDX-License-Identifier: Apache-2.0
*/
package io.opentelemetry.javaagent.customchecks;
import static com.google.errorprone.BugPattern.SeverityLevel.WARNING;
import static com.google.errorprone.matchers.Description.NO_MATCH;
import com.google.auto.service.AutoService;
import com.google.errorprone.BugPattern;
import com.google.errorprone.VisitorState;
import com.google.errorprone.bugpatterns.BugChecker;
import com.google.errorprone.bugpatterns.PrivateConstructorForUtilityClass;
import com.google.errorprone.matchers.Description;
import com.sun.source.tree.ClassTree;
@AutoService(BugChecker.class)
@BugPattern(
summary =
"Classes which are not intended to be instantiated should be made non-instantiable with a private constructor. This includes utility classes (classes with only static members), and the main class.",
severity = WARNING)
public class OtelPrivateConstructorForUtilityClass extends BugChecker
implements BugChecker.ClassTreeMatcher {
private static final long serialVersionUID = 1L;
private final PrivateConstructorForUtilityClass delegate =
new PrivateConstructorForUtilityClass();
@Override
public Description matchClass(ClassTree tree, VisitorState state) {
if (tree.getSimpleName().toString().endsWith("Advice")) {
return NO_MATCH;
}
Description description = delegate.matchClass(tree, state);
if (description == NO_MATCH) {
return description;
}
return describeMatch(tree);
}
}

View File

@ -83,6 +83,9 @@ public class MethodCacheTest {
}
static class TestClass {
public static void method() {}
private TestClass() {}
}
}

View File

@ -112,4 +112,6 @@ final class MetricsView {
}
});
}
private MetricsView() {}
}

View File

@ -54,4 +54,6 @@ public final class LocalRootSpan {
static Context store(Context context, Span span) {
return context.with(KEY, span);
}
private LocalRootSpan() {}
}

View File

@ -13,7 +13,8 @@ import scala.concurrent.impl.Promise;
import scala.runtime.AbstractFunction1;
import scala.util.Try;
public class FutureWrapper {
public final class FutureWrapper {
public static <T> Future<T> wrap(
Future<T> future, ExecutionContext executionContext, Context context) {
Promise.DefaultPromise<T> promise = new Promise.DefaultPromise<>();
@ -31,4 +32,6 @@ public class FutureWrapper {
return promise;
}
private FutureWrapper() {}
}

View File

@ -17,7 +17,7 @@ import io.opentelemetry.instrumentation.api.instrumenter.http.HttpSpanStatusExtr
import io.opentelemetry.javaagent.bootstrap.internal.CommonConfig;
import io.opentelemetry.javaagent.instrumentation.akkahttp.AkkaHttpUtil;
public class AkkaHttpServerSingletons {
public final class AkkaHttpServerSingletons {
private static final Instrumenter<HttpRequest, HttpResponse> INSTRUMENTER;
@ -46,4 +46,6 @@ public class AkkaHttpServerSingletons {
public static HttpResponse errorResponse() {
return (HttpResponse) HttpResponse.create().withStatus(500);
}
private AkkaHttpServerSingletons() {}
}

View File

@ -22,4 +22,6 @@ public final class ApacheHttpClientHelper {
// ended in WrappingStatusSettingResponseHandler
}
}
private ApacheHttpClientHelper() {}
}

View File

@ -23,4 +23,6 @@ public class ApacheHttpClientHelper {
// ended in WrappingStatusSettingResponseHandler
}
}
private ApacheHttpClientHelper() {}
}

View File

@ -51,6 +51,7 @@ public class AbstractStreamMessageSubscriptionInstrumentation implements TypeIns
}
}
@SuppressWarnings("unused")
public static class WrapCompletableFutureAdvice {
@Advice.OnMethodEnter(suppress = Throwable.class)

View File

@ -14,7 +14,7 @@ import io.opentelemetry.instrumentation.awslambdacore.v1_0.AwsLambdaRequest;
* This class is internal and is hence not for public use. Its APIs are unstable and can change at
* any time.
*/
public class AwsLambdaFunctionInstrumenterFactory {
public final class AwsLambdaFunctionInstrumenterFactory {
public static AwsLambdaFunctionInstrumenter createInstrumenter(OpenTelemetry openTelemetry) {
return new AwsLambdaFunctionInstrumenter(
@ -30,4 +30,6 @@ public class AwsLambdaFunctionInstrumenterFactory {
private static String spanName(AwsLambdaRequest input) {
return input.getAwsContext().getFunctionName();
}
private AwsLambdaFunctionInstrumenterFactory() {}
}

View File

@ -17,7 +17,7 @@ import io.opentelemetry.instrumentation.awslambdacore.v1_0.internal.AwsLambdaFun
* This class is internal and is hence not for public use. Its APIs are unstable and can change at
* any time.
*/
public class AwsLambdaEventsInstrumenterFactory {
public final class AwsLambdaEventsInstrumenterFactory {
public static AwsLambdaFunctionInstrumenter createInstrumenter(OpenTelemetry openTelemetry) {
return new AwsLambdaFunctionInstrumenter(
@ -39,4 +39,6 @@ public class AwsLambdaEventsInstrumenterFactory {
}
return name == null ? input.getAwsContext().getFunctionName() : name;
}
private AwsLambdaEventsInstrumenterFactory() {}
}

View File

@ -15,7 +15,7 @@ import io.opentelemetry.instrumentation.api.instrumenter.SpanKindExtractor;
* This class is internal and is hence not for public use. Its APIs are unstable and can change at
* any time.
*/
public class AwsLambdaSqsInstrumenterFactory {
public final class AwsLambdaSqsInstrumenterFactory {
public static Instrumenter<SQSEvent, Void> forEvent(OpenTelemetry openTelemetry) {
return Instrumenter.<SQSEvent, Void>builder(
@ -55,4 +55,6 @@ public class AwsLambdaSqsInstrumenterFactory {
return source + " process";
}
private AwsLambdaSqsInstrumenterFactory() {}
}

View File

@ -36,6 +36,7 @@ public class AzureHttpClientInstrumentation implements TypeInstrumentation {
this.getClass().getName() + "$SuppressNestedClientAdvice");
}
@SuppressWarnings("unused")
public static class SuppressNestedClientAdvice {
@Advice.OnMethodExit(suppress = Throwable.class)

View File

@ -36,6 +36,7 @@ public class AzureHttpClientInstrumentation implements TypeInstrumentation {
this.getClass().getName() + "$SuppressNestedClientAdvice");
}
@SuppressWarnings("unused")
public static class SuppressNestedClientAdvice {
@Advice.OnMethodExit(suppress = Throwable.class)

View File

@ -14,4 +14,6 @@ public class OuterClass {
@Retention(RUNTIME)
@Target(METHOD)
public @interface InterestingMethod {}
private OuterClass() {}
}

View File

@ -72,6 +72,7 @@ public class BootDelegationInstrumentation implements TypeInstrumentation {
}
public static class Holder {
public static final List<String> bootstrapPackagesPrefixes = findBootstrapPackagePrefixes();
/**
@ -95,6 +96,8 @@ public class BootDelegationInstrumentation implements TypeInstrumentation {
return Constants.BOOTSTRAP_PACKAGE_PREFIXES;
}
}
private Holder() {}
}
@SuppressWarnings("unused")

View File

@ -36,7 +36,7 @@ public class DefineClassInstrumentation implements TypeInstrumentation {
transformer.applyAdviceToMethod(
named("defineClass")
.and(takesArguments(String.class, ByteBuffer.class, ProtectionDomain.class)),
DefineClassInstrumentation.class.getName() + "$DefineClassAdvice2");
DefineClassInstrumentation.class.getName() + "$DefineClassWithThreeArgsAdvice");
}
@SuppressWarnings("unused")
@ -59,7 +59,7 @@ public class DefineClassInstrumentation implements TypeInstrumentation {
}
@SuppressWarnings("unused")
public static class DefineClassAdvice2 {
public static class DefineClassWithThreeArgsAdvice {
@Advice.OnMethodEnter(suppress = Throwable.class)
public static DefineClassContext onEnter(
@Advice.This ClassLoader classLoader,

View File

@ -4,7 +4,10 @@
*/
public class TestLambda {
static Runnable makeRunnable() {
return () -> {};
}
private TestLambda() {}
}

View File

@ -26,7 +26,7 @@ public class TestTypeInstrumentation implements TypeInstrumentation {
transformer.applyAdviceToMethod(
named("testMethod"), TestTypeInstrumentation.class.getName() + "$TestAdvice");
transformer.applyAdviceToMethod(
named("testMethod2"), TestTypeInstrumentation.class.getName() + "$TestAdvice2");
named("testMethod2"), TestTypeInstrumentation.class.getName() + "$Test2Advice");
}
@SuppressWarnings("unused")
@ -41,7 +41,7 @@ public class TestTypeInstrumentation implements TypeInstrumentation {
}
@SuppressWarnings("unused")
public static class TestAdvice2 {
public static class Test2Advice {
@Advice.OnMethodExit
public static void methodExit(

View File

@ -38,11 +38,11 @@ public class UrlClassLoaderInstrumentation implements TypeInstrumentation {
.and(takesArgument(0, URL.class))
.and(isProtected())
.and(not(isStatic())),
UrlClassLoaderInstrumentation.class.getName() + "$InvalidateClassLoaderMatcher");
UrlClassLoaderInstrumentation.class.getName() + "$AddUrlAdvice");
}
@SuppressWarnings("unused")
public static class InvalidateClassLoaderMatcher {
public static class AddUrlAdvice {
@Advice.OnMethodExit(suppress = Throwable.class)
public static void onExit(@Advice.This URLClassLoader loader) {
ClassLoaderMatcherCacheHolder.invalidateAllCachesForClassLoader(loader);

View File

@ -66,4 +66,6 @@ public class JavaInterfaces {
// do nothing
}
}
private JavaInterfaces() {}
}

View File

@ -66,4 +66,6 @@ public class JavaInterfaces {
// do nothing
}
}
private JavaInterfaces() {}
}

View File

@ -66,4 +66,6 @@ public class JavaInterfaces {
// do nothing
}
}
private JavaInterfaces() {}
}

View File

@ -89,6 +89,7 @@ public class JbossExtLogRecordInstrumentation implements TypeInstrumentation {
}
}
@SuppressWarnings("unused")
public static class GetMdcCopyAdvice {
@Advice.OnMethodExit(suppress = Throwable.class)

View File

@ -9,7 +9,7 @@ import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Proxy;
import java.sql.Statement;
public class ProxyStatementFactory {
public final class ProxyStatementFactory {
public static Statement proxyStatement(Statement statement) throws Exception {
TestClassLoader classLoader = new TestClassLoader(ProxyStatementFactory.class.getClassLoader());
@ -33,4 +33,6 @@ public class ProxyStatementFactory {
return proxyStatement;
}
private ProxyStatementFactory() {}
}

View File

@ -35,4 +35,6 @@ public final class DataSourceSingletons {
public static Instrumenter<DataSource, Void> instrumenter() {
return INSTRUMENTER;
}
private DataSourceSingletons() {}
}

View File

@ -9,4 +9,6 @@ public class JavaLambdaMaker {
public static Runnable lambda(Runnable runnable) {
return runnable::run;
}
private JavaLambdaMaker() {}
}

View File

@ -31,11 +31,11 @@ public class JspCompilationContextInstrumentation implements TypeInstrumentation
public void transform(TypeTransformer transformer) {
transformer.applyAdviceToMethod(
named("compile").and(takesArguments(0)).and(isPublic()),
JspCompilationContextInstrumentation.class.getName() + "$JasperJspCompilationContext");
JspCompilationContextInstrumentation.class.getName() + "$CompileAdvice");
}
@SuppressWarnings("unused")
public static class JasperJspCompilationContext {
public static class CompileAdvice {
@Advice.OnMethodEnter(suppress = Throwable.class)
public static void onEnter(

View File

@ -75,4 +75,6 @@ public final class InstrumentationPoints {
private static boolean isNonInstrumentingKeyword(ProtocolKeyword keyword) {
return keyword == SEGFAULT;
}
private InstrumentationPoints() {}
}

View File

@ -11,7 +11,7 @@ import java.util.Collections;
import java.util.HashSet;
import java.util.Set;
public class LettuceInstrumentationUtil {
public final class LettuceInstrumentationUtil {
private static final Set<String> nonInstrumentingCommands =
Collections.unmodifiableSet(
@ -46,4 +46,6 @@ public class LettuceInstrumentationUtil {
}
return commandName;
}
private LettuceInstrumentationUtil() {}
}

View File

@ -11,7 +11,7 @@ import io.opentelemetry.instrumentation.logback.appender.v1_0.internal.LoggingEv
import io.opentelemetry.javaagent.bootstrap.internal.InstrumentationConfig;
import java.util.List;
public class LogbackSingletons {
public final class LogbackSingletons {
private static final LoggingEventMapper mapper;
@ -32,4 +32,6 @@ public class LogbackSingletons {
public static LoggingEventMapper mapper() {
return mapper;
}
private LogbackSingletons() {}
}

View File

@ -35,4 +35,6 @@ class MongoInstrumenterFactory {
.addAttributesExtractor(attributesExtractor)
.buildInstrumenter(SpanKindExtractor.alwaysClient());
}
private MongoInstrumenterFactory() {}
}

View File

@ -31,6 +31,7 @@ public class DefaultConnectionPoolInstrumentation implements TypeInstrumentation
this.getClass().getName() + "$SingleResultCallbackAdvice");
}
@SuppressWarnings("unused")
public static class SingleResultCallbackAdvice {
@Advice.OnMethodEnter(suppress = Throwable.class)

View File

@ -0,0 +1,54 @@
/*
* Copyright The OpenTelemetry Authors
* SPDX-License-Identifier: Apache-2.0
*/
package io.opentelemetry.javaagent.instrumentation.netty.v3_8;
import io.opentelemetry.javaagent.instrumentation.netty.v3_8.client.HttpClientRequestTracingHandler;
import io.opentelemetry.javaagent.instrumentation.netty.v3_8.client.HttpClientResponseTracingHandler;
import io.opentelemetry.javaagent.instrumentation.netty.v3_8.client.HttpClientTracingHandler;
import io.opentelemetry.javaagent.instrumentation.netty.v3_8.server.HttpServerRequestTracingHandler;
import io.opentelemetry.javaagent.instrumentation.netty.v3_8.server.HttpServerResponseTracingHandler;
import io.opentelemetry.javaagent.instrumentation.netty.v3_8.server.HttpServerTracingHandler;
import org.jboss.netty.channel.ChannelHandler;
import org.jboss.netty.channel.ChannelPipeline;
import org.jboss.netty.handler.codec.http.HttpClientCodec;
import org.jboss.netty.handler.codec.http.HttpRequestDecoder;
import org.jboss.netty.handler.codec.http.HttpRequestEncoder;
import org.jboss.netty.handler.codec.http.HttpResponseDecoder;
import org.jboss.netty.handler.codec.http.HttpResponseEncoder;
import org.jboss.netty.handler.codec.http.HttpServerCodec;
/**
* When certain handlers are added to the pipeline, we want to add our corresponding tracing
* handlers. If those handlers are later removed, we may want to remove our handlers. That is not
* currently implemented.
*/
public final class ChannelPipelineUtil {
public static void wrapHandler(ChannelPipeline pipeline, ChannelHandler handler) {
// Server pipeline handlers
if (handler instanceof HttpServerCodec) {
pipeline.addLast(HttpServerTracingHandler.class.getName(), new HttpServerTracingHandler());
} else if (handler instanceof HttpRequestDecoder) {
pipeline.addLast(
HttpServerRequestTracingHandler.class.getName(), new HttpServerRequestTracingHandler());
} else if (handler instanceof HttpResponseEncoder) {
pipeline.addLast(
HttpServerResponseTracingHandler.class.getName(), new HttpServerResponseTracingHandler());
} else
// Client pipeline handlers
if (handler instanceof HttpClientCodec) {
pipeline.addLast(HttpClientTracingHandler.class.getName(), new HttpClientTracingHandler());
} else if (handler instanceof HttpRequestEncoder) {
pipeline.addLast(
HttpClientRequestTracingHandler.class.getName(), new HttpClientRequestTracingHandler());
} else if (handler instanceof HttpResponseDecoder) {
pipeline.addLast(
HttpClientResponseTracingHandler.class.getName(), new HttpClientResponseTracingHandler());
}
}
private ChannelPipelineUtil() {}
}

View File

@ -15,23 +15,11 @@ import static net.bytebuddy.matcher.ElementMatchers.takesArgument;
import io.opentelemetry.javaagent.bootstrap.CallDepth;
import io.opentelemetry.javaagent.extension.instrumentation.TypeInstrumentation;
import io.opentelemetry.javaagent.extension.instrumentation.TypeTransformer;
import io.opentelemetry.javaagent.instrumentation.netty.v3_8.client.HttpClientRequestTracingHandler;
import io.opentelemetry.javaagent.instrumentation.netty.v3_8.client.HttpClientResponseTracingHandler;
import io.opentelemetry.javaagent.instrumentation.netty.v3_8.client.HttpClientTracingHandler;
import io.opentelemetry.javaagent.instrumentation.netty.v3_8.server.HttpServerRequestTracingHandler;
import io.opentelemetry.javaagent.instrumentation.netty.v3_8.server.HttpServerResponseTracingHandler;
import io.opentelemetry.javaagent.instrumentation.netty.v3_8.server.HttpServerTracingHandler;
import net.bytebuddy.asm.Advice;
import net.bytebuddy.description.type.TypeDescription;
import net.bytebuddy.matcher.ElementMatcher;
import org.jboss.netty.channel.ChannelHandler;
import org.jboss.netty.channel.ChannelPipeline;
import org.jboss.netty.handler.codec.http.HttpClientCodec;
import org.jboss.netty.handler.codec.http.HttpRequestDecoder;
import org.jboss.netty.handler.codec.http.HttpRequestEncoder;
import org.jboss.netty.handler.codec.http.HttpResponseDecoder;
import org.jboss.netty.handler.codec.http.HttpResponseEncoder;
import org.jboss.netty.handler.codec.http.HttpServerCodec;
public class NettyChannelPipelineInstrumentation implements TypeInstrumentation {
@ -59,38 +47,6 @@ public class NettyChannelPipelineInstrumentation implements TypeInstrumentation
NettyChannelPipelineInstrumentation.class.getName() + "$ChannelPipelineAdd3ArgsAdvice");
}
/**
* When certain handlers are added to the pipeline, we want to add our corresponding tracing
* handlers. If those handlers are later removed, we may want to remove our handlers. That is not
* currently implemented.
*/
public static class ChannelPipelineAdviceUtil {
public static void wrapHandler(ChannelPipeline pipeline, ChannelHandler handler) {
// Server pipeline handlers
if (handler instanceof HttpServerCodec) {
pipeline.addLast(HttpServerTracingHandler.class.getName(), new HttpServerTracingHandler());
} else if (handler instanceof HttpRequestDecoder) {
pipeline.addLast(
HttpServerRequestTracingHandler.class.getName(), new HttpServerRequestTracingHandler());
} else if (handler instanceof HttpResponseEncoder) {
pipeline.addLast(
HttpServerResponseTracingHandler.class.getName(),
new HttpServerResponseTracingHandler());
} else
// Client pipeline handlers
if (handler instanceof HttpClientCodec) {
pipeline.addLast(HttpClientTracingHandler.class.getName(), new HttpClientTracingHandler());
} else if (handler instanceof HttpRequestEncoder) {
pipeline.addLast(
HttpClientRequestTracingHandler.class.getName(), new HttpClientRequestTracingHandler());
} else if (handler instanceof HttpResponseDecoder) {
pipeline.addLast(
HttpClientResponseTracingHandler.class.getName(),
new HttpClientResponseTracingHandler());
}
}
}
@SuppressWarnings("unused")
public static class ChannelPipelineAdd2ArgsAdvice {
@ -118,7 +74,7 @@ public class NettyChannelPipelineInstrumentation implements TypeInstrumentation
return;
}
ChannelPipelineAdviceUtil.wrapHandler(pipeline, handler);
ChannelPipelineUtil.wrapHandler(pipeline, handler);
}
}
@ -149,7 +105,7 @@ public class NettyChannelPipelineInstrumentation implements TypeInstrumentation
return;
}
ChannelPipelineAdviceUtil.wrapHandler(pipeline, handler);
ChannelPipelineUtil.wrapHandler(pipeline, handler);
}
}
}

View File

@ -58,4 +58,6 @@ public class AttributeKeys {
ConcurrentMap<String, AttributeKey<?>> classLoaderMap = mapSupplier.get(AttributeKey.class);
return (AttributeKey<T>) classLoaderMap.computeIfAbsent(key, AttributeKey::new);
}
private AttributeKeys() {}
}

View File

@ -160,4 +160,6 @@ public class Bridging {
applicationTraceState.forEach(agentTraceState::put);
return agentTraceState.build();
}
private Bridging() {}
}

View File

@ -27,7 +27,7 @@ public class OpenTelemetryInstrumentation implements TypeInstrumentation {
none(), OpenTelemetryInstrumentation.class.getName() + "$InitAdvice");
}
@SuppressWarnings({"unused", "ReturnValueIgnored"})
@SuppressWarnings({"ReturnValueIgnored", "unused"})
public static class InitAdvice {
@Advice.OnMethodEnter
public static void init() {

View File

@ -28,7 +28,7 @@ public class OpenTelemetryInstrumentation implements TypeInstrumentation {
none(), OpenTelemetryInstrumentation.class.getName() + "$InitAdvice");
}
@SuppressWarnings({"unused", "ReturnValueIgnored"})
@SuppressWarnings({"ReturnValueIgnored", "unused"})
public static class InitAdvice {
@Advice.OnMethodEnter
public static void init() {

View File

@ -18,6 +18,7 @@ import java.lang.reflect.Method;
import java.util.logging.Logger;
public final class WithSpanSingletons {
private static final String INSTRUMENTATION_NAME =
"io.opentelemetry.opentelemetry-extension-annotations-1.0";
@ -90,4 +91,6 @@ public final class WithSpanSingletons {
}
return spanName;
}
private WithSpanSingletons() {}
}

View File

@ -18,6 +18,7 @@ import java.lang.reflect.Method;
import java.util.logging.Logger;
public final class WithSpanSingletons {
private static final String INSTRUMENTATION_NAME =
"io.opentelemetry.opentelemetry-instrumentation-annotations-1.16";
@ -90,4 +91,6 @@ public final class WithSpanSingletons {
}
return spanName;
}
private WithSpanSingletons() {}
}

View File

@ -7,7 +7,7 @@ package io.opentelemetry.javaagent.instrumentation.testing;
import io.opentelemetry.instrumentation.api.internal.SpanKey;
public class AgentSpanTesting {
public final class AgentSpanTesting {
/**
* Runs the provided {@code runnable} inside the scope of an SERVER span with name {@code
@ -24,4 +24,6 @@ public class AgentSpanTesting {
public static void runWithAllSpanKeys(String spanName, Runnable runnable) {
runnable.run();
}
private AgentSpanTesting() {}
}

View File

@ -13,7 +13,7 @@ import scala.concurrent.ExecutionContext;
import scala.concurrent.Future;
import scala.runtime.AbstractFunction1;
public class ResponseFutureWrapper {
public final class ResponseFutureWrapper {
public static Future<Result> wrap(
Future<Result> future, Context context, ExecutionContext executionContext) {
@ -35,4 +35,6 @@ public class ResponseFutureWrapper {
},
executionContext);
}
private ResponseFutureWrapper() {}
}

View File

@ -39,8 +39,11 @@ public class RabbitCommandInstrumentation implements TypeInstrumentation {
RabbitCommandInstrumentation.class.getName() + "$CommandConstructorAdvice");
}
public static class SpanHolder {
public static final class SpanHolder {
public static final ThreadLocal<Context> CURRENT_RABBIT_CONTEXT = new ThreadLocal<>();
private SpanHolder() {}
}
@SuppressWarnings("unused")

View File

@ -20,7 +20,8 @@ import io.opentelemetry.javaagent.bootstrap.internal.InstrumentationConfig;
import java.util.ArrayList;
import java.util.List;
public class RabbitSingletons {
public final class RabbitSingletons {
private static final boolean CAPTURE_EXPERIMENTAL_SPAN_ATTRIBUTES =
InstrumentationConfig.get()
.getBoolean("otel.instrumentation.rabbitmq.experimental-span-attributes", false);
@ -91,4 +92,6 @@ public class RabbitSingletons {
.addAttributesExtractors(extractors)
.buildConsumerInstrumenter(DeliveryRequestGetter.INSTANCE);
}
private RabbitSingletons() {}
}

View File

@ -21,7 +21,7 @@ import org.restlet.Response;
* This class is internal and is hence not for public use. Its APIs are unstable and can change at
* any time.
*/
public class RestletInstrumenterFactory {
public final class RestletInstrumenterFactory {
private static final String INSTRUMENTATION_NAME = "io.opentelemetry.restlet-2.0";
@ -42,4 +42,6 @@ public class RestletInstrumenterFactory {
.addOperationMetrics(HttpServerMetrics.get())
.buildServerInstrumenter(new RestletHeadersGetter());
}
private RestletInstrumenterFactory() {}
}

View File

@ -12,6 +12,7 @@ import org.apache.rocketmq.client.hook.ConsumeMessageHook;
import org.apache.rocketmq.client.hook.SendMessageHook;
public final class RocketMqClientHooks {
private static final RocketMqTelemetry TELEMETRY =
RocketMqTelemetry.builder(GlobalOpenTelemetry.get())
.setPropagationEnabled(
@ -27,4 +28,6 @@ public final class RocketMqClientHooks {
TELEMETRY.newTracingConsumeMessageHook();
public static final SendMessageHook SEND_MESSAGE_HOOK = TELEMETRY.newTracingSendMessageHook();
private RocketMqClientHooks() {}
}

View File

@ -28,10 +28,11 @@ public class RocketMqConsumerInstrumentation implements TypeInstrumentation {
public void transform(TypeTransformer transformer) {
transformer.applyAdviceToMethod(
isMethod().and(named("start")).and(takesArguments(0)),
RocketMqConsumerInstrumentation.class.getName() + "$AdviceStart");
RocketMqConsumerInstrumentation.class.getName() + "$StartAdvice");
}
public static class AdviceStart {
@SuppressWarnings("unused")
public static class StartAdvice {
@Advice.OnMethodEnter(suppress = Throwable.class)
public static void onEnter(
@Advice.FieldValue(

View File

@ -28,10 +28,11 @@ public class RocketMqProducerInstrumentation implements TypeInstrumentation {
public void transform(TypeTransformer transformer) {
transformer.applyAdviceToMethod(
isMethod().and(named("start")).and(takesArguments(0)),
RocketMqProducerInstrumentation.class.getName() + "$AdviceStart");
RocketMqProducerInstrumentation.class.getName() + "$StartAdvice");
}
public static class AdviceStart {
@SuppressWarnings("unused")
public static class StartAdvice {
@Advice.OnMethodEnter(suppress = Throwable.class)
public static void onEnter(
@Advice.FieldValue(value = "defaultMQProducerImpl", declaringType = DefaultMQProducer.class)

View File

@ -110,4 +110,6 @@ class RocketMqInstrumenterFactory {
private static String spanNameOnReceive(Void unused) {
return "multiple_sources receive";
}
private RocketMqInstrumenterFactory() {}
}

View File

@ -79,4 +79,6 @@ public final class BufferPools {
}
};
}
private BufferPools() {}
}

View File

@ -40,4 +40,6 @@ public class RequestDispatcherServlet {
dispatcher.include(req, resp);
}
}
private RequestDispatcherServlet() {}
}

View File

@ -40,4 +40,6 @@ public class RequestDispatcherServlet {
dispatcher.include(req, resp);
}
}
private RequestDispatcherServlet() {}
}

View File

@ -65,4 +65,6 @@ public class HttpServletResponseAdviceHelper {
instrumenter.end(context, request, null, throwable);
}
}
private HttpServletResponseAdviceHelper() {}
}

View File

@ -21,4 +21,6 @@ public class TestSparkJavaApplication {
Spark.awaitInitialization();
}
private TestSparkJavaApplication() {}
}

View File

@ -44,6 +44,8 @@ import org.springframework.expression.spel.standard.SpelExpressionParser;
@EnableConfigurationProperties({MetricExportProperties.class, SamplerProperties.class})
public class OpenTelemetryAutoConfiguration {
public OpenTelemetryAutoConfiguration() {}
@Configuration
@ConditionalOnMissingBean(OpenTelemetry.class)
public static class OpenTelemetryBeanConfig {

View File

@ -92,4 +92,6 @@ public final class CompositeTextMapPropagatorFactory {
private static boolean isOnClasspath(String clazz) {
return ClassUtils.isPresent(clazz, null);
}
private CompositeTextMapPropagatorFactory() {}
}

View File

@ -46,6 +46,7 @@ public class ApplicationContextInstrumentation implements TypeInstrumentation {
ApplicationContextInstrumentation.class.getName() + "$PostProcessBeanFactoryAdvice");
}
@SuppressWarnings("unused")
public static class PostProcessBeanFactoryAdvice {
@Advice.OnMethodEnter(suppress = Throwable.class)
public static void onEnter(@Advice.Argument(0) ConfigurableListableBeanFactory beanFactory) {

View File

@ -7,7 +7,7 @@ package io.opentelemetry.javaagent.instrumentation.spring.webflux;
import io.opentelemetry.javaagent.bootstrap.internal.InstrumentationConfig;
public class SpringWebfluxConfig {
public final class SpringWebfluxConfig {
private static final boolean CAPTURE_EXPERIMENTAL_SPAN_ATTRIBUTES =
InstrumentationConfig.get()
@ -16,4 +16,6 @@ public class SpringWebfluxConfig {
public static boolean captureExperimentalSpanAttributes() {
return CAPTURE_EXPERIMENTAL_SPAN_ATTRIBUTES;
}
private SpringWebfluxConfig() {}
}

View File

@ -14,7 +14,7 @@ import io.opentelemetry.javaagent.bootstrap.internal.InstrumentationConfig;
import java.util.List;
import org.springframework.web.reactive.function.client.ExchangeFilterFunction;
public class WebClientHelper {
public final class WebClientHelper {
private static final SpringWebfluxTelemetry INSTRUMENTATION =
SpringWebfluxTelemetry.builder(GlobalOpenTelemetry.get())
@ -33,4 +33,6 @@ public class WebClientHelper {
public static void addFilter(List<ExchangeFilterFunction> exchangeFilterFunctions) {
INSTRUMENTATION.addClientTracingFilter(exchangeFilterFunctions);
}
private WebClientHelper() {}
}

View File

@ -13,7 +13,7 @@ import javax.annotation.Nullable;
import org.springframework.web.server.ServerWebExchange;
import reactor.core.publisher.Mono;
public class AdviceUtils {
public final class AdviceUtils {
public static final String ON_SPAN_END = AdviceUtils.class.getName() + ".Context";
@ -53,4 +53,6 @@ public class AdviceUtils {
interface OnSpanEnd {
void end(Throwable throwable);
}
private AdviceUtils() {}
}

View File

@ -11,6 +11,7 @@ import net.bytebuddy.asm.Advice;
import org.apache.coyote.Request;
import org.apache.coyote.Response;
@SuppressWarnings("unused")
public class Tomcat10AttachResponseAdvice {
@Advice.OnMethodExit(onThrowable = Throwable.class, suppress = Throwable.class)

View File

@ -11,6 +11,7 @@ import net.bytebuddy.asm.Advice;
import org.apache.coyote.Request;
import org.apache.coyote.Response;
@SuppressWarnings("unused")
public class Tomcat7AttachResponseAdvice {
@Advice.OnMethodExit(onThrowable = Throwable.class, suppress = Throwable.class)

View File

@ -13,7 +13,7 @@ import io.opentelemetry.instrumentation.api.instrumenter.InstrumenterBuilder;
import io.opentelemetry.instrumentation.api.util.SpanNames;
import io.opentelemetry.javaagent.bootstrap.internal.InstrumentationConfig;
public class TwilioSingletons {
public final class TwilioSingletons {
private static final boolean CAPTURE_EXPERIMENTAL_SPAN_ATTRIBUTES =
InstrumentationConfig.get()
@ -23,8 +23,7 @@ public class TwilioSingletons {
static {
InstrumenterBuilder<String, Object> instrumenterBuilder =
Instrumenter.<String, Object>builder(
GlobalOpenTelemetry.get(), "io.opentelemetry.twilio-6.6", str -> str);
Instrumenter.builder(GlobalOpenTelemetry.get(), "io.opentelemetry.twilio-6.6", str -> str);
if (CAPTURE_EXPERIMENTAL_SPAN_ATTRIBUTES) {
instrumenterBuilder.addAttributesExtractor(new TwilioExperimentalAttributesExtractor());
@ -41,4 +40,6 @@ public class TwilioSingletons {
public static String spanName(Object serviceExecutor, String methodName) {
return SpanNames.fromMethod(serviceExecutor.getClass(), methodName);
}
private TwilioSingletons() {}
}

View File

@ -30,6 +30,7 @@ public class HttpClientImplInstrumentation implements TypeInstrumentation {
isConstructor(), HttpClientImplInstrumentation.class.getName() + "$AttachStateAdvice");
}
@SuppressWarnings("unused")
public static class AttachStateAdvice {
@Advice.OnMethodExit(suppress = Throwable.class)
public static void attachHttpClientOptions(

View File

@ -45,6 +45,7 @@ public class HttpRequestImplInstrumentation implements TypeInstrumentation {
HttpRequestImplInstrumentation.class.getName() + "$Vertx37Advice");
}
@SuppressWarnings("unused")
public static class Vertx30Advice {
@Advice.OnMethodExit(suppress = Throwable.class)
public static void attachRequestInfo(
@ -58,10 +59,11 @@ public class HttpRequestImplInstrumentation implements TypeInstrumentation {
.set(
request,
VertxRequestInfo.create(
httpClientOptions != null ? httpClientOptions.isSsl() : false, host, port));
httpClientOptions != null && httpClientOptions.isSsl(), host, port));
}
}
@SuppressWarnings("unused")
public static class Vertx34Advice {
@Advice.OnMethodExit(suppress = Throwable.class)
public static void attachRequestInfo(
@ -74,6 +76,7 @@ public class HttpRequestImplInstrumentation implements TypeInstrumentation {
}
}
@SuppressWarnings("unused")
public static class Vertx37Advice {
@Advice.OnMethodExit(suppress = Throwable.class)
public static void attachRequestInfo(

View File

@ -9,7 +9,7 @@ import java.lang.instrument.Instrumentation;
import javax.annotation.Nullable;
/** This class serves as an "everywhere accessible" source of {@link Instrumentation} instance. */
public class InstrumentationHolder {
public final class InstrumentationHolder {
@Nullable private static volatile Instrumentation instrumentation;
@ -21,4 +21,6 @@ public class InstrumentationHolder {
public static void setInstrumentation(Instrumentation instrumentation) {
InstrumentationHolder.instrumentation = instrumentation;
}
private InstrumentationHolder() {}
}

View File

@ -9,8 +9,9 @@ import java.io.File;
import javax.annotation.Nullable;
// this is currently unused in this repository, but is available for use in distros
/** This class serves as an "everywhere accessible" source of the agent jar file. */
public class JavaagentFileHolder {
public final class JavaagentFileHolder {
@Nullable private static volatile File javaagentFile;
@ -22,4 +23,6 @@ public class JavaagentFileHolder {
public static void setJavaagentFile(File javaagentFile) {
JavaagentFileHolder.javaagentFile = javaagentFile;
}
private JavaagentFileHolder() {}
}

View File

@ -17,7 +17,7 @@ import io.opentelemetry.sdk.common.CompletableResultCode;
import io.opentelemetry.sdk.logs.SdkLogEmitterProvider;
import java.util.Arrays;
public class OpenTelemetryInstaller {
public final class OpenTelemetryInstaller {
/**
* Install the {@link OpenTelemetrySdk} using autoconfigure, and return the {@link
@ -58,4 +58,6 @@ public class OpenTelemetryInstaller {
return autoConfiguredSdk;
}
private OpenTelemetryInstaller() {}
}

View File

@ -119,6 +119,7 @@ class ExceptionHandlerTest {
}
public static class SomeClass {
public static boolean isInstrumented() {
return false;
}
@ -136,5 +137,7 @@ class ExceptionHandlerTest {
Object o = new Object();
System.out.println("large stack: " + l + ' ' + i + ' ' + d + ' ' + o);
}
private SomeClass() {}
}
}

View File

@ -8,6 +8,9 @@ package io.opentelemetry.javaagent;
import io.opentracing.contrib.dropwizard.Trace;
public class ClassToInstrument {
@Trace
public static void someMethod() {}
protected ClassToInstrument() {}
}

View File

@ -261,4 +261,6 @@ public class IntegrationTestUtils {
}
}
}
private IntegrationTestUtils() {}
}

View File

@ -9,6 +9,7 @@ import java.net.URL;
import java.net.URLClassLoader;
public class AgentLoadedChecker {
public static void main(String[] args) throws ClassNotFoundException {
// Empty class loader that delegates to bootstrap
URLClassLoader emptyClassLoader = new URLClassLoader(new URL[] {}, null);
@ -20,4 +21,6 @@ public class AgentLoadedChecker {
"Agent loaded into class loader other than bootstrap: " + agentClass.getClassLoader());
}
}
private AgentLoadedChecker() {}
}

View File

@ -6,6 +6,7 @@
package jvmbootstraptest;
public class LogLevelChecker {
// returns an exception if logs are not in DEBUG
public static void main(String[] args) {
@ -16,4 +17,6 @@ public class LogLevelChecker {
throw new IllegalStateException("debug mode not set");
}
}
private LogLevelChecker() {}
}

View File

@ -6,10 +6,13 @@
package jvmbootstraptest;
public class MyClassLoaderIsNotBootstrap {
public static void main(String[] args) {
if (MyClassLoaderIsNotBootstrap.class.getClassLoader() == null) {
throw new IllegalStateException(
"Application level class was loaded by the bootstrap class loader");
}
}
private MyClassLoaderIsNotBootstrap() {}
}

View File

@ -15,7 +15,7 @@ import io.opentelemetry.test.AnotherTestInterface
import io.opentelemetry.test.TestAbstractSuperClass
import io.opentelemetry.test.TestInterface
import muzzle.TestClasses
import muzzle.TestClasses.MethodBodyAdvice
import muzzle.TestClasses.Nested
import org.objectweb.asm.Type
import spock.lang.Shared
import spock.lang.Specification
@ -35,22 +35,22 @@ class ReferenceMatcherTest extends Specification {
static final TEST_EXTERNAL_INSTRUMENTATION_PACKAGE = "com.external.otel.instrumentation"
@Shared
ClassLoader safeClasspath = new URLClassLoader([ClasspathUtils.createJarWithClasses(MethodBodyAdvice.A,
MethodBodyAdvice.B,
MethodBodyAdvice.SomeInterface,
MethodBodyAdvice.SomeImplementation)] as URL[],
ClassLoader safeClasspath = new URLClassLoader([ClasspathUtils.createJarWithClasses(Nested.A,
Nested.B,
Nested.SomeInterface,
Nested.SomeImplementation)] as URL[],
(ClassLoader) null)
@Shared
ClassLoader unsafeClasspath = new URLClassLoader([ClasspathUtils.createJarWithClasses(MethodBodyAdvice.A,
MethodBodyAdvice.SomeInterface,
MethodBodyAdvice.SomeImplementation)] as URL[],
ClassLoader unsafeClasspath = new URLClassLoader([ClasspathUtils.createJarWithClasses(Nested.A,
Nested.SomeInterface,
Nested.SomeImplementation)] as URL[],
(ClassLoader) null)
def "match safe classpaths"() {
setup:
def collector = new ReferenceCollector({ false })
collector.collectReferencesFromAdvice(MethodBodyAdvice.name)
collector.collectReferencesFromAdvice(TestClasses.MethodBodyAdvice.name)
def refMatcher = createMatcher(collector.getReferences())
expect:
@ -60,7 +60,7 @@ class ReferenceMatcherTest extends Specification {
def "matching does not hold a strong reference to classloaders"() {
expect:
MuzzleWeakReferenceTest.classLoaderRefIsGarbageCollected()
MuzzleWeakReferenceTestUtil.classLoaderRefIsGarbageCollected()
}
private static class CountingClassLoader extends URLClassLoader {
@ -80,14 +80,14 @@ class ReferenceMatcherTest extends Specification {
def "muzzle type pool caches"() {
setup:
def cl = new CountingClassLoader(
[ClasspathUtils.createJarWithClasses(MethodBodyAdvice.A,
MethodBodyAdvice.B,
MethodBodyAdvice.SomeInterface,
MethodBodyAdvice.SomeImplementation)] as URL[],
[ClasspathUtils.createJarWithClasses(Nested.A,
Nested.B,
Nested.SomeInterface,
Nested.SomeImplementation)] as URL[],
(ClassLoader) null)
def collector = new ReferenceCollector({ false })
collector.collectReferencesFromAdvice(MethodBodyAdvice.name)
collector.collectReferencesFromAdvice(Nested.name)
def refMatcher1 = createMatcher(collector.getReferences())
def refMatcher2 = createMatcher(collector.getReferences())
@ -114,8 +114,8 @@ class ReferenceMatcherTest extends Specification {
where:
referenceName | referenceFlag | classToCheck | expectedMismatches
MethodBodyAdvice.B.name | NON_INTERFACE | MethodBodyAdvice.B | []
MethodBodyAdvice.B.name | INTERFACE | MethodBodyAdvice.B | [Mismatch.MissingFlag]
Nested.B.name | NON_INTERFACE | Nested.B | []
Nested.B.name | INTERFACE | Nested.B | [Mismatch.MissingFlag]
}
def "method match #methodTestDesc"() {
@ -134,13 +134,13 @@ class ReferenceMatcherTest extends Specification {
where:
methodName | methodDesc | methodFlags | classToCheck | expectedMismatches | methodTestDesc
"method" | "(Ljava/lang/String;)Ljava/lang/String;" | [] | MethodBodyAdvice.B | [] | "match method declared in class"
"hashCode" | "()I" | [] | MethodBodyAdvice.B | [] | "match method declared in superclass"
"someMethod" | "()V" | [] | MethodBodyAdvice.SomeInterface | [] | "match method declared in interface"
"privateStuff" | "()V" | [PRIVATE_OR_HIGHER] | MethodBodyAdvice.B | [] | "match private method"
"privateStuff" | "()V" | [PROTECTED_OR_HIGHER] | MethodBodyAdvice.B2 | [Mismatch.MissingFlag] | "fail match private in supertype"
"staticMethod" | "()V" | [NON_STATIC] | MethodBodyAdvice.B | [Mismatch.MissingFlag] | "static method mismatch"
"missingMethod" | "()V" | [] | MethodBodyAdvice.B | [Mismatch.MissingMethod] | "missing method mismatch"
"method" | "(Ljava/lang/String;)Ljava/lang/String;" | [] | Nested.B | [] | "match method declared in class"
"hashCode" | "()I" | [] | Nested.B | [] | "match method declared in superclass"
"someMethod" | "()V" | [] | Nested.SomeInterface | [] | "match method declared in interface"
"privateStuff" | "()V" | [PRIVATE_OR_HIGHER] | Nested.B | [] | "match private method"
"privateStuff" | "()V" | [PROTECTED_OR_HIGHER] | Nested.B2 | [Mismatch.MissingFlag] | "fail match private in supertype"
"staticMethod" | "()V" | [NON_STATIC] | Nested.B | [Mismatch.MissingFlag] | "static method mismatch"
"missingMethod" | "()V" | [] | Nested.B | [Mismatch.MissingMethod] | "missing method mismatch"
}
def "field match #fieldTestDesc"() {
@ -158,14 +158,14 @@ class ReferenceMatcherTest extends Specification {
where:
fieldName | fieldType | fieldFlags | classToCheck | expectedMismatches | fieldTestDesc
"missingField" | "Ljava/lang/String;" | [] | MethodBodyAdvice.A | [Mismatch.MissingField] | "mismatch missing field"
"privateField" | "Ljava/lang/String;" | [] | MethodBodyAdvice.A | [Mismatch.MissingField] | "mismatch field type signature"
"privateField" | "Ljava/lang/Object;" | [PRIVATE_OR_HIGHER] | MethodBodyAdvice.A | [] | "match private field"
"privateField" | "Ljava/lang/Object;" | [PROTECTED_OR_HIGHER] | MethodBodyAdvice.A2 | [Mismatch.MissingFlag] | "mismatch private field in supertype"
"protectedField" | "Ljava/lang/Object;" | [STATIC] | MethodBodyAdvice.A | [Mismatch.MissingFlag] | "mismatch static field"
"staticB" | Type.getType(MethodBodyAdvice.B).getDescriptor() | [STATIC, PROTECTED_OR_HIGHER] | MethodBodyAdvice.A | [] | "match static field"
"number" | "I" | [PACKAGE_OR_HIGHER] | MethodBodyAdvice.Primitives | [] | "match primitive int"
"flag" | "Z" | [PACKAGE_OR_HIGHER] | MethodBodyAdvice.Primitives | [] | "match primitive boolean"
"missingField" | "Ljava/lang/String;" | [] | Nested.A | [Mismatch.MissingField] | "mismatch missing field"
"privateField" | "Ljava/lang/String;" | [] | Nested.A | [Mismatch.MissingField] | "mismatch field type signature"
"privateField" | "Ljava/lang/Object;" | [PRIVATE_OR_HIGHER] | Nested.A | [] | "match private field"
"privateField" | "Ljava/lang/Object;" | [PROTECTED_OR_HIGHER] | Nested.A2 | [Mismatch.MissingFlag] | "mismatch private field in supertype"
"protectedField" | "Ljava/lang/Object;" | [STATIC] | Nested.A | [Mismatch.MissingFlag] | "mismatch static field"
"staticB" | Type.getType(Nested.B).getDescriptor() | [STATIC, PROTECTED_OR_HIGHER] | Nested.A | [] | "match static field"
"number" | "I" | [PACKAGE_OR_HIGHER] | Nested.Primitives | [] | "match primitive int"
"flag" | "Z" | [PACKAGE_OR_HIGHER] | Nested.Primitives | [] | "match primitive boolean"
}
def "should not check abstract #desc helper classes"() {

View File

@ -8,7 +8,8 @@ package io.opentelemetry.instrumentation;
import muzzle.TestClasses;
public class OtherTestHelperClasses {
public static class Foo implements TestClasses.MethodBodyAdvice.SomeInterface {
public static class Foo implements TestClasses.Nested.SomeInterface {
@Override
public void someMethod() {}
}
@ -30,4 +31,6 @@ public class OtherTestHelperClasses {
abstract int getAnswer();
}
private OtherTestHelperClasses() {}
}

View File

@ -10,6 +10,7 @@ import java.util.List;
import javax.annotation.Nullable;
public class TestHelperClasses {
public static class Helper extends HelperSuperClass implements HelperInterface {
@Override
@ -59,4 +60,6 @@ public class TestHelperClasses {
return 12345;
}
}
private TestHelperClasses() {}
}

View File

@ -7,6 +7,7 @@ package io.opentelemetry.javaagent.tooling.muzzle;
@SuppressWarnings("unused")
public class DeclaredFieldTestClass {
public static class Advice {
public void instrument() {
new Helper().foo();
@ -25,4 +26,6 @@ public class DeclaredFieldTestClass {
public static class LibraryBaseClass {
protected Object superField;
}
private DeclaredFieldTestClass() {}
}

View File

@ -10,9 +10,9 @@ import java.lang.ref.WeakReference;
import java.net.URL;
import java.net.URLClassLoader;
import java.util.Collections;
import muzzle.TestClasses;
import muzzle.TestClasses.MethodBodyAdvice;
public class MuzzleWeakReferenceTest {
public class MuzzleWeakReferenceTestUtil {
// Spock holds strong references to all local variables. For weak reference testing we must create
// our strong references away from Spock in this java class.
@ -21,7 +21,7 @@ public class MuzzleWeakReferenceTest {
ClassLoader loader = new URLClassLoader(new URL[0], null);
WeakReference<ClassLoader> clRef = new WeakReference<>(loader);
ReferenceCollector collector = new ReferenceCollector(className -> false);
collector.collectReferencesFromAdvice(TestClasses.MethodBodyAdvice.class.getName());
collector.collectReferencesFromAdvice(MethodBodyAdvice.class.getName());
ReferenceMatcher refMatcher =
new ReferenceMatcher(
Collections.emptyList(), collector.getReferences(), className -> false);
@ -30,4 +30,6 @@ public class MuzzleWeakReferenceTest {
GcUtils.awaitGc(clRef);
return clRef.get() == null;
}
private MuzzleWeakReferenceTestUtil() {}
}

View File

@ -29,6 +29,7 @@ import muzzle.TestClasses;
import muzzle.TestClasses.HelperAdvice;
import muzzle.TestClasses.LdcAdvice;
import muzzle.TestClasses.MethodBodyAdvice;
import muzzle.TestClasses.Nested;
import org.assertj.core.api.Assertions;
import org.junit.jupiter.api.Test;
import org.junit.jupiter.params.ParameterizedTest;
@ -48,17 +49,17 @@ class ReferenceCollectorTest {
assertThat(references)
.containsOnlyKeys(
MethodBodyAdvice.A.class.getName(),
MethodBodyAdvice.B.class.getName(),
MethodBodyAdvice.SomeInterface.class.getName(),
MethodBodyAdvice.SomeImplementation.class.getName());
Nested.A.class.getName(),
Nested.B.class.getName(),
Nested.SomeInterface.class.getName(),
Nested.SomeImplementation.class.getName());
ClassRef refB = references.get(MethodBodyAdvice.B.class.getName());
ClassRef refA = references.get(MethodBodyAdvice.A.class.getName());
ClassRef refB = references.get(Nested.B.class.getName());
ClassRef refA = references.get(Nested.A.class.getName());
// interface flags
assertThat(refB.getFlags()).contains(ManifestationFlag.NON_INTERFACE);
assertThat(references.get(MethodBodyAdvice.SomeInterface.class.getName()).getFlags())
assertThat(references.get(Nested.SomeInterface.class.getName()).getFlags())
.contains(ManifestationFlag.INTERFACE);
// class access flags
@ -92,12 +93,12 @@ class ReferenceCollectorTest {
@Test
public void protectedRefTest() {
ReferenceCollector collector = new ReferenceCollector(s -> false);
collector.collectReferencesFromAdvice(MethodBodyAdvice.B2.class.getName());
collector.collectReferencesFromAdvice(Nested.B2.class.getName());
collector.prune();
Map<String, ClassRef> references = collector.getReferences();
assertMethod(
references.get(MethodBodyAdvice.B.class.getName()),
references.get(Nested.B.class.getName()),
"protectedMethod",
"()V",
PROTECTED_OR_HIGHER,
@ -111,7 +112,7 @@ class ReferenceCollectorTest {
collector.prune();
Map<String, ClassRef> references = collector.getReferences();
assertThat(references).containsKey(MethodBodyAdvice.A.class.getName());
assertThat(references).containsKey(Nested.A.class.getName());
}
@Test
@ -121,7 +122,7 @@ class ReferenceCollectorTest {
collector.prune();
Map<String, ClassRef> references = collector.getReferences();
assertThat(references).containsKey(MethodBodyAdvice.A.class.getName());
assertThat(references).containsKey(Nested.A.class.getName());
}
@Test
@ -131,23 +132,23 @@ class ReferenceCollectorTest {
collector.prune();
Map<String, ClassRef> references = collector.getReferences();
assertThat(references).containsKey("muzzle.TestClasses$MethodBodyAdvice$SomeImplementation");
assertThat(references).containsKey("muzzle.TestClasses$Nested$SomeImplementation");
assertMethod(
references.get("muzzle.TestClasses$MethodBodyAdvice$SomeImplementation"),
references.get("muzzle.TestClasses$Nested$SomeImplementation"),
"someMethod",
"()V",
PROTECTED_OR_HIGHER,
OwnershipFlag.NON_STATIC);
assertThat(references).containsKey("muzzle.TestClasses$MethodBodyAdvice$B");
assertThat(references).containsKey("muzzle.TestClasses$Nested$B");
assertMethod(
references.get("muzzle.TestClasses$MethodBodyAdvice$B"),
references.get("muzzle.TestClasses$Nested$B"),
"staticMethod",
"()V",
PROTECTED_OR_HIGHER,
OwnershipFlag.STATIC);
assertThat(references).containsKey("muzzle.TestClasses$MethodBodyAdvice$A");
assertThat(references).containsKey("muzzle.TestClasses$Nested$A");
assertMethod(
references.get("muzzle.TestClasses$MethodBodyAdvice$A"),
references.get("muzzle.TestClasses$Nested$A"),
"<init>",
"()V",
PROTECTED_OR_HIGHER,

View File

@ -8,8 +8,9 @@ package io.opentelemetry.javaagent.tooling.muzzle;
import io.opentelemetry.context.Context;
import io.opentelemetry.instrumentation.api.util.VirtualField;
@SuppressWarnings("ReturnValueIgnored")
@SuppressWarnings({"ReturnValueIgnored", "unused"})
public class VirtualFieldTestClasses {
public static class ValidAdvice {
public static void advice() {
Runnable.class.getName();
@ -71,4 +72,6 @@ public class VirtualFieldTestClasses {
public static class Key2 {}
public static class State {}
private VirtualFieldTestClasses() {}
}

View File

@ -7,6 +7,7 @@ package muzzle;
@SuppressWarnings("unused")
public class HelperReferenceWrapperTestClasses {
interface Interface1 {
void foo();
}
@ -24,4 +25,6 @@ public class HelperReferenceWrapperTestClasses {
@SuppressWarnings("MethodCanBeStatic")
private void privateMethodsToo() {}
}
private HelperReferenceWrapperTestClasses() {}
}

View File

@ -13,22 +13,24 @@ import net.bytebuddy.asm.Advice;
@SuppressWarnings("unused")
public class TestClasses {
@SuppressWarnings("ClassNamedLikeTypeParameter")
public static class MethodBodyAdvice {
@SuppressWarnings("ReturnValueIgnored")
@Advice.OnMethodEnter
@SuppressWarnings("ReturnValueIgnored")
public static void methodBodyAdvice() {
A a = new A();
SomeInterface inter = new SomeImplementation();
Nested.A a = new Nested.A();
Nested.SomeInterface inter = new Nested.SomeImplementation();
inter.someMethod();
a.publicB.method("foo");
a.publicB.methodWithPrimitives(false);
a.publicB.methodWithArrays(new String[0]);
B.staticMethod();
A.staticB.method("bar");
Nested.B.staticMethod();
Nested.A.staticB.method("bar");
new int[0].clone();
}
}
@SuppressWarnings("ClassNamedLikeTypeParameter")
public static class Nested {
public static class A {
public B publicB = new B();
protected Object protectedField = null;
@ -85,6 +87,8 @@ public class TestClasses {
}
public interface AnotherInterface extends SomeInterface {}
private Nested() {}
}
public abstract static class BaseClassWithConstructor {
@ -94,21 +98,20 @@ public class TestClasses {
public static class LdcAdvice {
@SuppressWarnings("ReturnValueIgnored")
public static void ldcMethod() {
MethodBodyAdvice.A.class.getName();
Nested.A.class.getName();
}
}
public static class InstanceofAdvice {
public static boolean instanceofMethod(Object a) {
return a instanceof MethodBodyAdvice.A;
return a instanceof Nested.A;
}
}
public static class InvokeDynamicAdvice {
public static MethodBodyAdvice.SomeInterface invokeDynamicMethod(
MethodBodyAdvice.SomeImplementation a) {
Runnable staticMethod = MethodBodyAdvice.B::staticMethod;
Runnable constructorMethod = MethodBodyAdvice.A::new;
public static Nested.SomeInterface invokeDynamicMethod(Nested.SomeImplementation a) {
Runnable staticMethod = Nested.B::staticMethod;
Runnable constructorMethod = Nested.A::new;
return a::someMethod;
}
}
@ -130,4 +133,6 @@ public class TestClasses {
new ExternalHelper().instrument();
}
}
private TestClasses() {}
}

View File

@ -127,4 +127,6 @@ public class FakeBackendMain {
server.start().join();
Runtime.getRuntime().addShutdownHook(new Thread(() -> server.stop().join()));
}
private FakeBackendMain() {}
}

View File

@ -22,4 +22,6 @@ public class TestMain {
logger.info("Server started at port 8080.");
server.awaitTermination();
}
private TestMain() {}
}

View File

@ -14,4 +14,6 @@ public class SpringbootApplication {
public static void main(String[] args) {
SpringApplication.run(SpringbootApplication.class, args);
}
private SpringbootApplication() {}
}

View File

@ -8,7 +8,7 @@ package io.opentelemetry.javaagent.testing.exporter;
import java.util.List;
import java.util.concurrent.TimeUnit;
public class AgentTestingExporterFactory {
public final class AgentTestingExporterFactory {
static final OtlpInMemorySpanExporter spanExporter = new OtlpInMemorySpanExporter();
static final OtlpInMemoryMetricExporter metricExporter = new OtlpInMemoryMetricExporter();
@ -38,4 +38,6 @@ public class AgentTestingExporterFactory {
public static boolean forceFlushCalled() {
return AgentTestingCustomizer.spanProcessor.forceFlushCalled;
}
private AgentTestingExporterFactory() {}
}