From 8e3c698c3090f842b4ce8c4d6dd09aadceb2e320 Mon Sep 17 00:00:00 2001 From: Daniel Mohedano Date: Fri, 19 Sep 2025 12:09:44 +0200 Subject: [PATCH 1/5] fix: migrate to JUnit 5 --- .../maven3/AbstractMavenTest.java | 96 ---- .../maven3/MavenProjectConfiguratorTest.java | 120 ----- .../maven3/MavenUtilsTest.java | 436 ------------------ .../common/writer/ddagent/CachingTest.java | 8 +- .../ddagent/GenerationalUtf8CacheTest.java | 12 +- .../writer/ddagent/SimpleUtf8CacheTest.java | 16 +- 6 files changed, 17 insertions(+), 671 deletions(-) delete mode 100644 dd-java-agent/instrumentation/maven-3.2.1/src/test/groovy/datadog/trace/instrumentation/maven3/AbstractMavenTest.java delete mode 100644 dd-java-agent/instrumentation/maven-3.2.1/src/test/groovy/datadog/trace/instrumentation/maven3/MavenProjectConfiguratorTest.java delete mode 100644 dd-java-agent/instrumentation/maven-3.2.1/src/test/groovy/datadog/trace/instrumentation/maven3/MavenUtilsTest.java diff --git a/dd-java-agent/instrumentation/maven-3.2.1/src/test/groovy/datadog/trace/instrumentation/maven3/AbstractMavenTest.java b/dd-java-agent/instrumentation/maven-3.2.1/src/test/groovy/datadog/trace/instrumentation/maven3/AbstractMavenTest.java deleted file mode 100644 index 9ec8a47d8ad..00000000000 --- a/dd-java-agent/instrumentation/maven-3.2.1/src/test/groovy/datadog/trace/instrumentation/maven3/AbstractMavenTest.java +++ /dev/null @@ -1,96 +0,0 @@ -package datadog.trace.instrumentation.maven3; - -import static org.junit.Assert.assertTrue; - -import java.io.File; -import java.io.PrintStream; -import java.nio.file.Path; -import java.util.concurrent.atomic.AtomicBoolean; -import java.util.concurrent.atomic.AtomicReference; -import java.util.function.Function; -import org.apache.maven.cli.MavenCli; -import org.apache.maven.eventspy.AbstractEventSpy; -import org.apache.maven.eventspy.EventSpy; -import org.apache.maven.execution.ExecutionEvent; -import org.codehaus.plexus.PlexusContainer; -import org.junit.jupiter.api.io.TempDir; - -public abstract class AbstractMavenTest { - @TempDir static Path WORKING_DIRECTORY; - - protected AbstractMavenTest() { - System.setProperty( - "maven.multiModuleProjectDirectory", - WORKING_DIRECTORY.getRoot().toAbsolutePath().toString()); - } - - protected void executeMaven( - Function mojoStartedHandler, - String pomPath, - String goal, - String... additionalArgs) - throws Exception { - executeMaven(mojoStartedHandler, pomPath, goal, null, null, additionalArgs); - } - - protected void executeMaven( - Function mojoStartedHandler, - String pomPath, - String goal, - PrintStream stdOut, - PrintStream stderr, - String... additionalArgs) - throws Exception { - MojoStartedSpy spy = new MojoStartedSpy(mojoStartedHandler); - MavenCli mavenCli = - new MavenCli() { - @Override - protected void customizeContainer(PlexusContainer container) { - container.addComponent(spy, EventSpy.class, null); - } - }; - - File pomFile = new File(AbstractMavenTest.class.getResource(pomPath).toURI()); - - String[] arguments = new String[additionalArgs.length + 3]; - arguments[0] = "-f"; - arguments[1] = pomFile.getAbsolutePath(); - arguments[2] = goal; - System.arraycopy(additionalArgs, 0, arguments, 3, additionalArgs.length); - - mavenCli.doMain( - arguments, WORKING_DIRECTORY.getRoot().toAbsolutePath().toString(), stdOut, stderr); - - Exception error = spy.handlerError.get(); - if (error != null) { - throw error; - } - assertTrue(spy.handlerRan.get()); - } - - private static final class MojoStartedSpy extends AbstractEventSpy { - private final Function mojoStartedHandler; - private final AtomicBoolean handlerRan = new AtomicBoolean(false); - private final AtomicReference handlerError = new AtomicReference<>(null); - - private MojoStartedSpy(Function mojoStartedHandler) { - this.mojoStartedHandler = mojoStartedHandler; - } - - @Override - public void onEvent(Object o) { - if (!(o instanceof ExecutionEvent)) { - return; - } - ExecutionEvent executionEvent = (ExecutionEvent) o; - if (executionEvent.getType() != ExecutionEvent.Type.MojoStarted) { - return; - } - try { - handlerRan.compareAndSet(false, mojoStartedHandler.apply(executionEvent)); - } catch (Exception error) { - handlerError.compareAndSet(null, error); - } - } - } -} diff --git a/dd-java-agent/instrumentation/maven-3.2.1/src/test/groovy/datadog/trace/instrumentation/maven3/MavenProjectConfiguratorTest.java b/dd-java-agent/instrumentation/maven-3.2.1/src/test/groovy/datadog/trace/instrumentation/maven3/MavenProjectConfiguratorTest.java deleted file mode 100644 index 9359f822402..00000000000 --- a/dd-java-agent/instrumentation/maven-3.2.1/src/test/groovy/datadog/trace/instrumentation/maven3/MavenProjectConfiguratorTest.java +++ /dev/null @@ -1,120 +0,0 @@ -package datadog.trace.instrumentation.maven3; - -import static org.junit.Assert.assertTrue; -import static org.mockito.Mockito.mock; -import static org.mockito.Mockito.when; - -import datadog.trace.api.Config; -import java.io.BufferedReader; -import java.io.ByteArrayInputStream; -import java.io.ByteArrayOutputStream; -import java.io.File; -import java.io.InputStreamReader; -import java.io.PrintStream; -import java.net.URISyntaxException; -import java.util.Arrays; -import java.util.Collection; -import java.util.Collections; -import org.apache.maven.execution.ExecutionEvent; -import org.apache.maven.execution.MavenSession; -import org.apache.maven.plugin.MojoExecution; -import org.apache.maven.project.MavenProject; -import org.junit.Test; -import org.junit.runner.RunWith; -import org.junit.runners.Parameterized; -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; - -@RunWith(Parameterized.class) -public class MavenProjectConfiguratorTest extends AbstractMavenTest { - - private static final Logger LOGGER = LoggerFactory.getLogger(MavenProjectConfiguratorTest.class); - - @Parameterized.Parameters(name = "{0} - {1}") - public static Collection surefireVersions() { - return Arrays.asList( - new Object[][] { - {"sampleProject/pom.xml", "test", new String[] {"-X", "-DargLine=-DmyArgLineProp=true"}}, - { - "sampleProject/pom.xml", - "surefire:test", - new String[] {"-X", "-DargLine=-DmyArgLineProp=true"} - }, - {"sampleProjectArgLine/pom.xml", "test", new String[] {"-X"}}, - {"sampleProjectArgLine/pom.xml", "surefire:test", new String[] {"-X"}}, - {"sampleProjectSurefireArgLine/pom.xml", "test", new String[] {"-X"}}, - {"sampleProjectSurefireArgLine/pom.xml", "surefire:test", new String[] {"-X"}}, - {"sampleProjectSurefireLateProcessingArgLine/pom.xml", "test", new String[] {"-X"}}, - }); - } - - private final String pomPath; - private final String goal; - private final String[] additionalCmdLineArgs; - - public MavenProjectConfiguratorTest(String pomPath, String goal, String[] additionalCmdLineArgs) { - this.pomPath = pomPath; - this.goal = goal; - this.additionalCmdLineArgs = additionalCmdLineArgs; - } - - @Test - public void testTracerInjection() throws Exception { - ByteArrayOutputStream stdOutBaos = new ByteArrayOutputStream(); - PrintStream buildOutput = new PrintStream(stdOutBaos); - - ByteArrayOutputStream stdErrBaos = new ByteArrayOutputStream(); - PrintStream buildError = new PrintStream(stdErrBaos); - - try { - executeMaven( - this::injectTracer, pomPath, goal, buildOutput, buildError, additionalCmdLineArgs); - - boolean javaAgentInjected = false; - boolean argLinePreserved = false; - - byte[] buildOutputBytes = stdOutBaos.toByteArray(); - BufferedReader buildOutputReader = - new BufferedReader(new InputStreamReader(new ByteArrayInputStream(buildOutputBytes))); - String buildOutputLine; - while ((buildOutputLine = buildOutputReader.readLine()) != null) { - javaAgentInjected |= buildOutputLine.contains("TEST JAVA AGENT STARTED"); - argLinePreserved |= - buildOutputLine.contains("surefire") - && buildOutputLine.contains("Forking command line") - && buildOutputLine.contains("-DmyArgLineProp=true"); - } - - assertTrue("Tracer wasn't injected", javaAgentInjected); - assertTrue("Original argLine was not preserved", argLinePreserved); - - } catch (Exception | Error e) { - LOGGER.info("Build output:\n\n" + stdOutBaos); - LOGGER.info("Build error:\n\n" + stdErrBaos); - throw e; - } - } - - private boolean injectTracer(ExecutionEvent executionEvent) { - MojoExecution mojoExecution = executionEvent.getMojoExecution(); - if (!MavenUtils.isTestExecution(mojoExecution)) { - return false; - } - MavenSession session = executionEvent.getSession(); - MavenProject project = executionEvent.getProject(); - - try { - Config config = mock(Config.class); - when(config.isCiVisibilityAutoConfigurationEnabled()).thenReturn(true); - when(config.getCiVisibilityDebugPort()).thenReturn(null); - when(config.getCiVisibilityAgentJarFile()) - .thenReturn(new File(MavenUtilsTest.class.getResource("simple-agent.jar").toURI())); - MavenProjectConfigurator.INSTANCE.configureTracer( - session, project, mojoExecution, Collections.emptyMap(), config); - return true; - - } catch (URISyntaxException e) { - throw new RuntimeException(e); - } - } -} diff --git a/dd-java-agent/instrumentation/maven-3.2.1/src/test/groovy/datadog/trace/instrumentation/maven3/MavenUtilsTest.java b/dd-java-agent/instrumentation/maven-3.2.1/src/test/groovy/datadog/trace/instrumentation/maven3/MavenUtilsTest.java deleted file mode 100644 index d3865a25a8d..00000000000 --- a/dd-java-agent/instrumentation/maven-3.2.1/src/test/groovy/datadog/trace/instrumentation/maven3/MavenUtilsTest.java +++ /dev/null @@ -1,436 +0,0 @@ -package datadog.trace.instrumentation.maven3; - -import static org.hamcrest.MatcherAssert.assertThat; -import static org.hamcrest.Matchers.endsWith; -import static org.hamcrest.Matchers.equalTo; -import static org.hamcrest.Matchers.hasItem; -import static org.hamcrest.Matchers.hasSize; -import static org.hamcrest.Matchers.hasToString; -import static org.hamcrest.Matchers.notNullValue; - -import datadog.trace.api.civisibility.domain.JavaAgent; -import freemarker.template.Configuration; -import freemarker.template.Template; -import freemarker.template.TemplateException; -import freemarker.template.TemplateExceptionHandler; -import java.io.File; -import java.io.FileWriter; -import java.io.IOException; -import java.net.URISyntaxException; -import java.nio.file.Path; -import java.util.Arrays; -import java.util.Collection; -import java.util.Collections; -import java.util.List; -import java.util.Map; -import javax.xml.parsers.DocumentBuilder; -import javax.xml.parsers.DocumentBuilderFactory; -import okhttp3.OkHttpClient; -import okhttp3.Request; -import okhttp3.Response; -import org.apache.maven.artifact.versioning.ComparableVersion; -import org.apache.maven.execution.ExecutionEvent; -import org.apache.maven.execution.MavenSession; -import org.apache.maven.plugin.MojoExecution; -import org.apache.maven.project.MavenProject; -import org.codehaus.plexus.PlexusContainer; -import org.junit.Assume; -import org.junit.Test; -import org.junit.runner.RunWith; -import org.junit.runners.Parameterized; -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; -import org.w3c.dom.Document; -import org.w3c.dom.NodeList; - -@RunWith(Parameterized.class) -public class MavenUtilsTest extends AbstractMavenTest { - - private static final Logger LOGGER = LoggerFactory.getLogger(MavenUtilsTest.class); - - private static final Configuration FREEMARKER = new Configuration(Configuration.VERSION_2_3_30); - - static { - FREEMARKER.setClassForTemplateLoading(MavenUtilsTest.class, ""); - FREEMARKER.setDefaultEncoding("UTF-8"); - FREEMARKER.setTemplateExceptionHandler(TemplateExceptionHandler.RETHROW_HANDLER); - FREEMARKER.setLogTemplateExceptions(true); - FREEMARKER.setWrapUncheckedExceptions(true); - } - - private static final ComparableVersion SUREFIRE_3_0_0 = new ComparableVersion("3.0.0"); - private static final ComparableVersion SUREFIRE_3_2_0 = new ComparableVersion("3.2.0"); - private static final ComparableVersion MAVEN_3_3_1 = new ComparableVersion("3.3.1"); - - private final ComparableVersion surefirePluginVersion; - - public MavenUtilsTest( - ComparableVersion surefirePluginVersion, ComparableVersion minRequiredMavenVersion) { - Assume.assumeTrue( - "Newer maven version required to run chosen version of Surefire plugin", - minRequiredMavenVersion.compareTo(getCurrentMavenVersion()) <= 0); - this.surefirePluginVersion = surefirePluginVersion; - } - - private ComparableVersion getCurrentMavenVersion() { - return new ComparableVersion(MavenSession.class.getPackage().getImplementationVersion()); - } - - @Test - public void testGetMojoConfigValueReturnsNullIfValueNotSet() throws Exception { - executeMaven( - this::assertGetMojoConfigValueReturnsNullIfValueNotSet, - "samplePom.xml", - String.format( - "org.apache.maven.plugins:maven-surefire-plugin:%s:test", surefirePluginVersion)); - } - - private boolean assertGetMojoConfigValueReturnsNullIfValueNotSet(ExecutionEvent executionEvent) { - MojoExecution mojoExecution = executionEvent.getMojoExecution(); - if (!MavenUtils.isTestExecution(mojoExecution)) { - return false; - } - MavenSession session = executionEvent.getSession(); - String forkCount = MavenUtils.getConfigurationValue(session, mojoExecution, "forkCount"); - assertThat(forkCount, equalTo(null)); - return true; - } - - @Test - public void testGetMojoConfigValueReturnsConfiguredValue() throws Exception { - executeMaven( - this::assertGetMojoConfigValueReturnsConfiguredValue, - "samplePom.xml", - String.format( - "org.apache.maven.plugins:maven-surefire-plugin:%s:test", surefirePluginVersion)); - } - - private boolean assertGetMojoConfigValueReturnsConfiguredValue(ExecutionEvent executionEvent) { - MojoExecution mojoExecution = executionEvent.getMojoExecution(); - if (!MavenUtils.isTestExecution(mojoExecution)) { - return false; - } - MavenSession session = executionEvent.getSession(); - String threadCount = MavenUtils.getConfigurationValue(session, mojoExecution, "threadCount"); - assertThat(threadCount, equalTo("112")); - return true; - } - - @Test - public void testGetMojoConfigValueResolvesPropertyPlaceholders() throws Exception { - executeMaven( - this::assertGetMojoConfigValueResolvesPropertyPlaceholders, - "samplePom.xml", - String.format( - "org.apache.maven.plugins:maven-surefire-plugin:%s:test", surefirePluginVersion)); - } - - private boolean assertGetMojoConfigValueResolvesPropertyPlaceholders( - ExecutionEvent executionEvent) { - MojoExecution mojoExecution = executionEvent.getMojoExecution(); - if (!MavenUtils.isTestExecution(mojoExecution)) { - return false; - } - MavenSession session = executionEvent.getSession(); - String forkedProcessExitTimeoutInSeconds = - MavenUtils.getConfigurationValue(session, mojoExecution, "forkedProcessTimeoutInSeconds"); - assertThat(forkedProcessExitTimeoutInSeconds, equalTo("887")); - return true; - } - - @Test - public void testGetMojoConfigValueResolvesPropertiesSuppliedViaCmdLine() throws Exception { - executeMaven( - this::assertGetMojoConfigValueResolvesPropertiesSuppliedViaCmdLine, - "samplePom.xml", - String.format( - "org.apache.maven.plugins:maven-surefire-plugin:%s:test", surefirePluginVersion), - "-Dsurefire.parallel.timeout=112233"); - } - - private boolean assertGetMojoConfigValueResolvesPropertiesSuppliedViaCmdLine( - ExecutionEvent executionEvent) { - MojoExecution mojoExecution = executionEvent.getMojoExecution(); - if (!MavenUtils.isTestExecution(mojoExecution)) { - return false; - } - MavenSession session = executionEvent.getSession(); - String parallelTestsTimeoutInSeconds = - MavenUtils.getConfigurationValue(session, mojoExecution, "parallelTestsTimeoutInSeconds"); - assertThat(parallelTestsTimeoutInSeconds, equalTo("112233")); - return true; - } - - @Test - public void testGetArgLineResolvesLatePropertyPlaceholders() throws Exception { - executeMaven( - this::assertGetArgLineResolvesLatePropertyPlaceholders, - "samplePom.xml", - String.format( - "org.apache.maven.plugins:maven-surefire-plugin:%s:test", surefirePluginVersion)); - } - - private boolean assertGetArgLineResolvesLatePropertyPlaceholders(ExecutionEvent executionEvent) { - MojoExecution mojoExecution = executionEvent.getMojoExecution(); - if (!MavenUtils.isTestExecution(mojoExecution)) { - return false; - } - MavenSession session = executionEvent.getSession(); - MavenProject project = executionEvent.getProject(); - String argLine = MavenUtils.getArgLine(session, project, mojoExecution); - assertThat(argLine, equalTo("-Xms128m -Xmx2g")); - return true; - } - - @Test - public void testGetJacocoAgent() throws Exception { - executeMaven(this::assertGetJacocoAgent, "samplePomJacoco.xml", "test"); - } - - private boolean assertGetJacocoAgent(ExecutionEvent executionEvent) { - MojoExecution mojoExecution = executionEvent.getMojoExecution(); - if (!MavenUtils.isTestExecution(mojoExecution)) { - return false; - } - MavenSession session = executionEvent.getSession(); - MavenProject project = executionEvent.getProject(); - JavaAgent jacocoAgent = MavenUtils.getJacocoAgent(session, project, mojoExecution); - assertThat(jacocoAgent, notNullValue()); - assertThat(jacocoAgent.getPath(), endsWith("org.jacoco.agent-0.8.11-runtime.jar")); - assertThat(jacocoAgent.getArguments(), notNullValue()); - return true; - } - - @Test - public void testGetEffectiveJvmFallbackUsesJvmProperty() throws Exception { - executeMaven( - this::assertGetEffectiveJvmFallbackUsesJvmProperty, - "samplePom.xml", - String.format( - "org.apache.maven.plugins:maven-surefire-plugin:%s:test", surefirePluginVersion)); - } - - private boolean assertGetEffectiveJvmFallbackUsesJvmProperty(ExecutionEvent executionEvent) { - MojoExecution mojoExecution = executionEvent.getMojoExecution(); - if (!MavenUtils.isTestExecution(mojoExecution)) { - return false; - } - MavenSession session = executionEvent.getSession(); - String effectiveJvm = MavenUtils.getEffectiveJvmFallback(session, mojoExecution); - assertThat(effectiveJvm, equalTo("jvm-config-property-value")); - return true; - } - - @Test - public void testGetEffectiveJvmFallbackUsesToolchains() throws Exception { - Assume.assumeTrue(surefirePluginVersion.compareTo(SUREFIRE_3_0_0) >= 0); - Assume.assumeTrue(getCurrentMavenVersion().compareTo(MAVEN_3_3_1) >= 0); - - File toolchainsFile = createToolchainsFile(); - executeMaven( - this::assertGetEffectiveJvmFallbackUsesToolchains, - "samplePomToolchains.xml", - String.format( - "org.apache.maven.plugins:maven-surefire-plugin:%s:test", surefirePluginVersion), - "--global-toolchains", - toolchainsFile.getAbsolutePath()); - } - - private boolean assertGetEffectiveJvmFallbackUsesToolchains(ExecutionEvent executionEvent) { - MojoExecution mojoExecution = executionEvent.getMojoExecution(); - if (!MavenUtils.isTestExecution(mojoExecution)) { - return false; - } - MavenSession session = executionEvent.getSession(); - String effectiveJvm = MavenUtils.getEffectiveJvmFallback(session, mojoExecution); - assertThat(effectiveJvm, endsWith("/my-jdk-home/bin/java")); - return true; - } - - /** - * "jdkHome" in toolchains.xml has to point to an existing folder, so this method processes - * toolchains template, substituting the path to the real my-jdk-home directory. - */ - private static File createToolchainsFile() - throws URISyntaxException, IOException, TemplateException { - File toolchainJdkHome = new File(MavenUtilsTest.class.getResource("my-jdk-home").toURI()); - Map replacements = - Collections.singletonMap("my_jdk_home_path", toolchainJdkHome.getAbsolutePath()); - - File toolchainsFile = WORKING_DIRECTORY.getRoot().resolve("toolchains.xml").toFile(); - try (FileWriter toolchainsFileWriter = new FileWriter(toolchainsFile)) { - Template coveragesTemplate = FREEMARKER.getTemplate("sampleToolchains.ftl"); - coveragesTemplate.process(replacements, toolchainsFileWriter); - } - return toolchainsFile; - } - - @Test - public void testGetForkedJvmPath() throws Exception { - executeMaven( - this::assertGetForkedJvmPath, - "samplePomJacoco.xml", - String.format( - "org.apache.maven.plugins:maven-surefire-plugin:%s:test", surefirePluginVersion)); - } - - private boolean assertGetForkedJvmPath(ExecutionEvent executionEvent) { - MojoExecution mojoExecution = executionEvent.getMojoExecution(); - if (!MavenUtils.isTestExecution(mojoExecution)) { - return false; - } - MavenSession session = executionEvent.getSession(); - Path jvmPath = MavenUtils.getForkedJvmPath(session, mojoExecution); - assertThat(jvmPath, hasToString(endsWith("/java"))); - return true; - } - - @Test - public void testGetClasspath() throws Exception { - executeMaven( - this::assertGetClasspath, - "samplePom.xml", - String.format( - "org.apache.maven.plugins:maven-surefire-plugin:%s:test", surefirePluginVersion)); - } - - private boolean assertGetClasspath(ExecutionEvent executionEvent) { - MojoExecution mojoExecution = executionEvent.getMojoExecution(); - if (!MavenUtils.isTestExecution(mojoExecution)) { - return false; - } - MavenSession session = executionEvent.getSession(); - List classpath = MavenUtils.getClasspath(session, mojoExecution); - assertThat(classpath, hasSize(5)); - assertThat(classpath, hasItem(hasToString(endsWith("/test-classes")))); - assertThat(classpath, hasItem(hasToString(endsWith("/classes")))); - assertThat(classpath, hasItem(hasToString(endsWith("/junit-4.13.2.jar")))); - assertThat(classpath, hasItem(hasToString(endsWith("/hamcrest-core-1.3.jar")))); - assertThat(classpath, hasItem(hasToString(endsWith("/commons-lang3-3.17.0.jar")))); - return true; - } - - @Test - public void testGetClasspathConsidersAdditionalClasspathDependencies() throws Exception { - Assume.assumeTrue(surefirePluginVersion.compareTo(SUREFIRE_3_2_0) >= 0); - executeMaven( - this::assertGetClasspathConsidersAdditionalClasspathDependencies, - "samplePomAdditionalClasspathDependencies.xml", - String.format( - "org.apache.maven.plugins:maven-surefire-plugin:%s:test", surefirePluginVersion)); - } - - private boolean assertGetClasspathConsidersAdditionalClasspathDependencies( - ExecutionEvent executionEvent) { - MojoExecution mojoExecution = executionEvent.getMojoExecution(); - if (!MavenUtils.isTestExecution(mojoExecution)) { - return false; - } - MavenSession session = executionEvent.getSession(); - List classpath = MavenUtils.getClasspath(session, mojoExecution); - assertThat(classpath, hasSize(5)); - assertThat(classpath, hasItem(hasToString(endsWith("/test-classes")))); - assertThat(classpath, hasItem(hasToString(endsWith("/classes")))); - assertThat(classpath, hasItem(hasToString(endsWith("/junit-4.13.2.jar")))); - assertThat(classpath, hasItem(hasToString(endsWith("/hamcrest-core-1.3.jar")))); - assertThat(classpath, hasItem(hasToString(endsWith("/commons-io-2.16.1.jar")))); - return true; - } - - @Test - public void testGetClasspathConsidersAdditionalClasspathElements() throws Exception { - executeMaven( - this::assertGetClasspathConsidersAdditionalClasspathElements, - "samplePomAdditionalClasspathElements.xml", - String.format( - "org.apache.maven.plugins:maven-surefire-plugin:%s:test", surefirePluginVersion)); - } - - private boolean assertGetClasspathConsidersAdditionalClasspathElements( - ExecutionEvent executionEvent) { - MojoExecution mojoExecution = executionEvent.getMojoExecution(); - if (!MavenUtils.isTestExecution(mojoExecution)) { - return false; - } - MavenSession session = executionEvent.getSession(); - List classpath = MavenUtils.getClasspath(session, mojoExecution); - assertThat(classpath, hasSize(6)); - assertThat(classpath, hasItem(hasToString(endsWith("/test-classes")))); - assertThat(classpath, hasItem(hasToString(endsWith("/classes")))); - assertThat(classpath, hasItem(hasToString(endsWith("/junit-4.13.2.jar")))); - assertThat(classpath, hasItem(hasToString(endsWith("/hamcrest-core-1.3.jar")))); - assertThat(classpath, hasItem(hasToString(equalTo("/path/to/additional/classpath/element")))); - assertThat( - classpath, hasItem(hasToString(equalTo("/path/to/another/additional/classpath/element")))); - return true; - } - - @Test - public void testGetContainer() throws Exception { - executeMaven( - this::assertGetContainer, - "samplePom.xml", - String.format( - "org.apache.maven.plugins:maven-surefire-plugin:%s:test", surefirePluginVersion)); - } - - private boolean assertGetContainer(ExecutionEvent executionEvent) { - MojoExecution mojoExecution = executionEvent.getMojoExecution(); - if (!MavenUtils.isTestExecution(mojoExecution)) { - return false; - } - MavenSession session = executionEvent.getSession(); - PlexusContainer container = MavenUtils.getContainer(session); - assertThat(container, notNullValue()); - return true; - } - - @Parameterized.Parameters(name = "{0}") - public static Collection surefireVersions() { - return Arrays.asList( - new Object[][] { - {new ComparableVersion("2.17"), new ComparableVersion("3.0.0")}, - {new ComparableVersion("2.21.0"), new ComparableVersion("3.0.0")}, - {new ComparableVersion("3.0.0"), new ComparableVersion("3.0.0")}, - {new ComparableVersion("3.5.0"), new ComparableVersion("3.6.3")}, - {new ComparableVersion(getLatestMavenSurefireVersion()), new ComparableVersion("3.6.3")} - }); - } - - private static String getLatestMavenSurefireVersion() { - OkHttpClient client = new OkHttpClient(); - Request request = - new Request.Builder() - .url( - "https://repo.maven.apache.org/maven2/org/apache/maven/plugins/maven-surefire-plugin/maven-metadata.xml") - .build(); - try (Response response = client.newCall(request).execute()) { - if (response.isSuccessful()) { - DocumentBuilderFactory dbFactory = DocumentBuilderFactory.newInstance(); - DocumentBuilder dBuilder = dbFactory.newDocumentBuilder(); - Document doc = dBuilder.parse(response.body().byteStream()); - doc.getDocumentElement().normalize(); - - NodeList versionList = doc.getElementsByTagName("latest"); - if (versionList.getLength() > 0) { - String version = versionList.item(0).getTextContent(); - if (!version.contains("alpha") && !version.contains("beta")) { - LOGGER.info("Will run the 'latest' tests with version " + version); - return version; - } - } - } else { - LOGGER.warn( - "Could not get latest Maven Surefire version, response from repo.maven.apache.org is " - + response.code() - + ":" - + response.body().string()); - } - } catch (Exception e) { - LOGGER.warn("Could not get latest Maven Surefire version", e); - } - String hardcodedLatestVersion = "3.5.0"; // latest version that is known to work - LOGGER.info("Will run the 'latest' tests with hard-coded version " + hardcodedLatestVersion); - return hardcodedLatestVersion; - } -} diff --git a/dd-trace-core/src/test/java/datadog/trace/common/writer/ddagent/CachingTest.java b/dd-trace-core/src/test/java/datadog/trace/common/writer/ddagent/CachingTest.java index 87e709d8910..51c6f1d79fe 100644 --- a/dd-trace-core/src/test/java/datadog/trace/common/writer/ddagent/CachingTest.java +++ b/dd-trace-core/src/test/java/datadog/trace/common/writer/ddagent/CachingTest.java @@ -1,10 +1,10 @@ package datadog.trace.common.writer.ddagent; -import static org.junit.Assert.assertEquals; -import static org.junit.Assert.assertFalse; -import static org.junit.Assert.assertTrue; +import static org.junit.jupiter.api.Assertions.assertEquals; +import static org.junit.jupiter.api.Assertions.assertFalse; +import static org.junit.jupiter.api.Assertions.assertTrue; -import org.junit.Test; +import org.junit.jupiter.api.Test; public class CachingTest { @Test diff --git a/dd-trace-core/src/test/java/datadog/trace/common/writer/ddagent/GenerationalUtf8CacheTest.java b/dd-trace-core/src/test/java/datadog/trace/common/writer/ddagent/GenerationalUtf8CacheTest.java index 3412a40dc13..9d9d0fde384 100644 --- a/dd-trace-core/src/test/java/datadog/trace/common/writer/ddagent/GenerationalUtf8CacheTest.java +++ b/dd-trace-core/src/test/java/datadog/trace/common/writer/ddagent/GenerationalUtf8CacheTest.java @@ -1,15 +1,15 @@ package datadog.trace.common.writer.ddagent; -import static org.junit.Assert.assertArrayEquals; -import static org.junit.Assert.assertEquals; -import static org.junit.Assert.assertNotEquals; -import static org.junit.Assert.assertNotSame; -import static org.junit.Assert.assertSame; +import static org.junit.jupiter.api.Assertions.assertArrayEquals; +import static org.junit.jupiter.api.Assertions.assertEquals; +import static org.junit.jupiter.api.Assertions.assertNotEquals; +import static org.junit.jupiter.api.Assertions.assertNotSame; +import static org.junit.jupiter.api.Assertions.assertSame; import java.nio.charset.StandardCharsets; import java.util.Random; import java.util.concurrent.ThreadLocalRandom; -import org.junit.Test; +import org.junit.jupiter.api.Test; import org.junit.jupiter.params.ParameterizedTest; import org.junit.jupiter.params.provider.ValueSource; diff --git a/dd-trace-core/src/test/java/datadog/trace/common/writer/ddagent/SimpleUtf8CacheTest.java b/dd-trace-core/src/test/java/datadog/trace/common/writer/ddagent/SimpleUtf8CacheTest.java index 5921a751cd5..811ff56ce57 100644 --- a/dd-trace-core/src/test/java/datadog/trace/common/writer/ddagent/SimpleUtf8CacheTest.java +++ b/dd-trace-core/src/test/java/datadog/trace/common/writer/ddagent/SimpleUtf8CacheTest.java @@ -1,15 +1,15 @@ package datadog.trace.common.writer.ddagent; -import static org.junit.Assert.assertArrayEquals; -import static org.junit.Assert.assertEquals; -import static org.junit.Assert.assertNotEquals; -import static org.junit.Assert.assertNotSame; -import static org.junit.Assert.assertSame; +import static org.junit.jupiter.api.Assertions.assertArrayEquals; +import static org.junit.jupiter.api.Assertions.assertEquals; +import static org.junit.jupiter.api.Assertions.assertNotEquals; +import static org.junit.jupiter.api.Assertions.assertNotSame; +import static org.junit.jupiter.api.Assertions.assertSame; import java.nio.charset.StandardCharsets; import java.util.Random; import java.util.concurrent.ThreadLocalRandom; -import org.junit.Test; +import org.junit.jupiter.api.Test; import org.junit.jupiter.params.ParameterizedTest; import org.junit.jupiter.params.provider.ValueSource; @@ -153,8 +153,6 @@ static final String nextValue() { } static final void printStats(SimpleUtf8Cache cache) { - System.out.printf( - "eden hits: %5d\tpromotion hits: %5d\tpromotions: %5d\tearly: %5d\tlocal evictions: %5d\tglobal evictions: %5d%n", - cache.hits, cache.evictions); + System.out.printf("eden hits: %5d\tpromotions: %5d", cache.hits, cache.evictions); } } From 7d582cc222e637d4b96f92731d05eb3ee003f7aa Mon Sep 17 00:00:00 2001 From: Daniel Mohedano Date: Fri, 19 Sep 2025 12:10:49 +0200 Subject: [PATCH 2/5] fix: add maven tests back --- .../maven3/AbstractMavenTest.java | 96 ++++ .../maven3/MavenProjectConfiguratorTest.java | 108 ++++ .../maven3/MavenUtilsTest.java | 501 ++++++++++++++++++ 3 files changed, 705 insertions(+) create mode 100644 dd-java-agent/instrumentation/maven-3.2.1/src/test/java/datadog/trace/instrumentation/maven3/AbstractMavenTest.java create mode 100644 dd-java-agent/instrumentation/maven-3.2.1/src/test/java/datadog/trace/instrumentation/maven3/MavenProjectConfiguratorTest.java create mode 100644 dd-java-agent/instrumentation/maven-3.2.1/src/test/java/datadog/trace/instrumentation/maven3/MavenUtilsTest.java diff --git a/dd-java-agent/instrumentation/maven-3.2.1/src/test/java/datadog/trace/instrumentation/maven3/AbstractMavenTest.java b/dd-java-agent/instrumentation/maven-3.2.1/src/test/java/datadog/trace/instrumentation/maven3/AbstractMavenTest.java new file mode 100644 index 00000000000..9ec8a47d8ad --- /dev/null +++ b/dd-java-agent/instrumentation/maven-3.2.1/src/test/java/datadog/trace/instrumentation/maven3/AbstractMavenTest.java @@ -0,0 +1,96 @@ +package datadog.trace.instrumentation.maven3; + +import static org.junit.Assert.assertTrue; + +import java.io.File; +import java.io.PrintStream; +import java.nio.file.Path; +import java.util.concurrent.atomic.AtomicBoolean; +import java.util.concurrent.atomic.AtomicReference; +import java.util.function.Function; +import org.apache.maven.cli.MavenCli; +import org.apache.maven.eventspy.AbstractEventSpy; +import org.apache.maven.eventspy.EventSpy; +import org.apache.maven.execution.ExecutionEvent; +import org.codehaus.plexus.PlexusContainer; +import org.junit.jupiter.api.io.TempDir; + +public abstract class AbstractMavenTest { + @TempDir static Path WORKING_DIRECTORY; + + protected AbstractMavenTest() { + System.setProperty( + "maven.multiModuleProjectDirectory", + WORKING_DIRECTORY.getRoot().toAbsolutePath().toString()); + } + + protected void executeMaven( + Function mojoStartedHandler, + String pomPath, + String goal, + String... additionalArgs) + throws Exception { + executeMaven(mojoStartedHandler, pomPath, goal, null, null, additionalArgs); + } + + protected void executeMaven( + Function mojoStartedHandler, + String pomPath, + String goal, + PrintStream stdOut, + PrintStream stderr, + String... additionalArgs) + throws Exception { + MojoStartedSpy spy = new MojoStartedSpy(mojoStartedHandler); + MavenCli mavenCli = + new MavenCli() { + @Override + protected void customizeContainer(PlexusContainer container) { + container.addComponent(spy, EventSpy.class, null); + } + }; + + File pomFile = new File(AbstractMavenTest.class.getResource(pomPath).toURI()); + + String[] arguments = new String[additionalArgs.length + 3]; + arguments[0] = "-f"; + arguments[1] = pomFile.getAbsolutePath(); + arguments[2] = goal; + System.arraycopy(additionalArgs, 0, arguments, 3, additionalArgs.length); + + mavenCli.doMain( + arguments, WORKING_DIRECTORY.getRoot().toAbsolutePath().toString(), stdOut, stderr); + + Exception error = spy.handlerError.get(); + if (error != null) { + throw error; + } + assertTrue(spy.handlerRan.get()); + } + + private static final class MojoStartedSpy extends AbstractEventSpy { + private final Function mojoStartedHandler; + private final AtomicBoolean handlerRan = new AtomicBoolean(false); + private final AtomicReference handlerError = new AtomicReference<>(null); + + private MojoStartedSpy(Function mojoStartedHandler) { + this.mojoStartedHandler = mojoStartedHandler; + } + + @Override + public void onEvent(Object o) { + if (!(o instanceof ExecutionEvent)) { + return; + } + ExecutionEvent executionEvent = (ExecutionEvent) o; + if (executionEvent.getType() != ExecutionEvent.Type.MojoStarted) { + return; + } + try { + handlerRan.compareAndSet(false, mojoStartedHandler.apply(executionEvent)); + } catch (Exception error) { + handlerError.compareAndSet(null, error); + } + } + } +} diff --git a/dd-java-agent/instrumentation/maven-3.2.1/src/test/java/datadog/trace/instrumentation/maven3/MavenProjectConfiguratorTest.java b/dd-java-agent/instrumentation/maven-3.2.1/src/test/java/datadog/trace/instrumentation/maven3/MavenProjectConfiguratorTest.java new file mode 100644 index 00000000000..89811dabb1f --- /dev/null +++ b/dd-java-agent/instrumentation/maven-3.2.1/src/test/java/datadog/trace/instrumentation/maven3/MavenProjectConfiguratorTest.java @@ -0,0 +1,108 @@ +package datadog.trace.instrumentation.maven3; + +import static org.junit.jupiter.api.Assertions.assertTrue; +import static org.mockito.Mockito.mock; +import static org.mockito.Mockito.when; + +import datadog.trace.api.Config; +import java.io.BufferedReader; +import java.io.ByteArrayInputStream; +import java.io.ByteArrayOutputStream; +import java.io.File; +import java.io.InputStreamReader; +import java.io.PrintStream; +import java.net.URISyntaxException; +import java.util.Collections; +import java.util.stream.Stream; +import org.apache.maven.execution.ExecutionEvent; +import org.apache.maven.execution.MavenSession; +import org.apache.maven.plugin.MojoExecution; +import org.apache.maven.project.MavenProject; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.Arguments; +import org.junit.jupiter.params.provider.MethodSource; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +public class MavenProjectConfiguratorTest extends AbstractMavenTest { + + private static final Logger LOGGER = LoggerFactory.getLogger(MavenProjectConfiguratorTest.class); + + public static Stream surefireVersions() { + return Stream.of( + Arguments.of( + "sampleProject/pom.xml", "test", new String[] {"-X", "-DargLine=-DmyArgLineProp=true"}), + Arguments.of( + "sampleProject/pom.xml", + "surefire:test", + new String[] {"-X", "-DargLine=-DmyArgLineProp=true"}), + Arguments.of("sampleProjectArgLine/pom.xml", "test", new String[] {"-X"}), + Arguments.of("sampleProjectArgLine/pom.xml", "surefire:test", new String[] {"-X"}), + Arguments.of("sampleProjectSurefireArgLine/pom.xml", "test", new String[] {"-X"}), + Arguments.of("sampleProjectSurefireArgLine/pom.xml", "surefire:test", new String[] {"-X"}), + Arguments.of( + "sampleProjectSurefireLateProcessingArgLine/pom.xml", "test", new String[] {"-X"})); + } + + @ParameterizedTest + @MethodSource("surefireVersions") + public void testTracerInjection(String pomPath, String goal, String[] additionalCmdLineArgs) + throws Exception { + ByteArrayOutputStream stdOutBaos = new ByteArrayOutputStream(); + PrintStream buildOutput = new PrintStream(stdOutBaos); + + ByteArrayOutputStream stdErrBaos = new ByteArrayOutputStream(); + PrintStream buildError = new PrintStream(stdErrBaos); + + try { + executeMaven( + this::injectTracer, pomPath, goal, buildOutput, buildError, additionalCmdLineArgs); + + boolean javaAgentInjected = false; + boolean argLinePreserved = false; + + byte[] buildOutputBytes = stdOutBaos.toByteArray(); + BufferedReader buildOutputReader = + new BufferedReader(new InputStreamReader(new ByteArrayInputStream(buildOutputBytes))); + String buildOutputLine; + while ((buildOutputLine = buildOutputReader.readLine()) != null) { + javaAgentInjected |= buildOutputLine.contains("TEST JAVA AGENT STARTED"); + argLinePreserved |= + buildOutputLine.contains("surefire") + && buildOutputLine.contains("Forking command line") + && buildOutputLine.contains("-DmyArgLineProp=true"); + } + + assertTrue(javaAgentInjected, "Tracer wasn't injected"); + assertTrue(argLinePreserved, "Original argLine was not preserved"); + + } catch (Exception | Error e) { + LOGGER.info("Build output:\n\n" + stdOutBaos); + LOGGER.info("Build error:\n\n" + stdErrBaos); + throw e; + } + } + + private boolean injectTracer(ExecutionEvent executionEvent) { + MojoExecution mojoExecution = executionEvent.getMojoExecution(); + if (!MavenUtils.isTestExecution(mojoExecution)) { + return false; + } + MavenSession session = executionEvent.getSession(); + MavenProject project = executionEvent.getProject(); + + try { + Config config = mock(Config.class); + when(config.isCiVisibilityAutoConfigurationEnabled()).thenReturn(true); + when(config.getCiVisibilityDebugPort()).thenReturn(null); + when(config.getCiVisibilityAgentJarFile()) + .thenReturn(new File(MavenUtilsTest.class.getResource("simple-agent.jar").toURI())); + MavenProjectConfigurator.INSTANCE.configureTracer( + session, project, mojoExecution, Collections.emptyMap(), config); + return true; + + } catch (URISyntaxException e) { + throw new RuntimeException(e); + } + } +} diff --git a/dd-java-agent/instrumentation/maven-3.2.1/src/test/java/datadog/trace/instrumentation/maven3/MavenUtilsTest.java b/dd-java-agent/instrumentation/maven-3.2.1/src/test/java/datadog/trace/instrumentation/maven3/MavenUtilsTest.java new file mode 100644 index 00000000000..28ea052f672 --- /dev/null +++ b/dd-java-agent/instrumentation/maven-3.2.1/src/test/java/datadog/trace/instrumentation/maven3/MavenUtilsTest.java @@ -0,0 +1,501 @@ +package datadog.trace.instrumentation.maven3; + +import static org.hamcrest.MatcherAssert.assertThat; +import static org.hamcrest.Matchers.endsWith; +import static org.hamcrest.Matchers.equalTo; +import static org.hamcrest.Matchers.hasItem; +import static org.hamcrest.Matchers.hasSize; +import static org.hamcrest.Matchers.hasToString; +import static org.hamcrest.Matchers.notNullValue; + +import datadog.trace.api.civisibility.domain.JavaAgent; +import freemarker.template.Configuration; +import freemarker.template.Template; +import freemarker.template.TemplateException; +import freemarker.template.TemplateExceptionHandler; +import java.io.File; +import java.io.FileWriter; +import java.io.IOException; +import java.net.URISyntaxException; +import java.nio.file.Path; +import java.util.Collections; +import java.util.List; +import java.util.Map; +import java.util.stream.Stream; +import javax.xml.parsers.DocumentBuilder; +import javax.xml.parsers.DocumentBuilderFactory; +import okhttp3.OkHttpClient; +import okhttp3.Request; +import okhttp3.Response; +import org.apache.maven.artifact.versioning.ComparableVersion; +import org.apache.maven.execution.ExecutionEvent; +import org.apache.maven.execution.MavenSession; +import org.apache.maven.plugin.MojoExecution; +import org.apache.maven.project.MavenProject; +import org.codehaus.plexus.PlexusContainer; +import org.junit.jupiter.api.Assumptions; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.Arguments; +import org.junit.jupiter.params.provider.MethodSource; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; +import org.w3c.dom.Document; +import org.w3c.dom.NodeList; + +public class MavenUtilsTest extends AbstractMavenTest { + + private static final Logger LOGGER = LoggerFactory.getLogger(MavenUtilsTest.class); + + private static final Configuration FREEMARKER = new Configuration(Configuration.VERSION_2_3_30); + + static { + FREEMARKER.setClassForTemplateLoading(MavenUtilsTest.class, ""); + FREEMARKER.setDefaultEncoding("UTF-8"); + FREEMARKER.setTemplateExceptionHandler(TemplateExceptionHandler.RETHROW_HANDLER); + FREEMARKER.setLogTemplateExceptions(true); + FREEMARKER.setWrapUncheckedExceptions(true); + } + + private static final ComparableVersion SUREFIRE_3_0_0 = new ComparableVersion("3.0.0"); + private static final ComparableVersion SUREFIRE_3_2_0 = new ComparableVersion("3.2.0"); + private static final ComparableVersion MAVEN_3_3_1 = new ComparableVersion("3.3.1"); + + public static Stream surefireVersions() { + return Stream.of( + Arguments.of(new ComparableVersion("2.17"), new ComparableVersion("3.0.0")), + Arguments.of(new ComparableVersion("2.21.0"), new ComparableVersion("3.0.0")), + Arguments.of(new ComparableVersion("3.0.0"), new ComparableVersion("3.0.0")), + Arguments.of(new ComparableVersion("3.5.0"), new ComparableVersion("3.6.3")), + Arguments.of( + new ComparableVersion(getLatestMavenSurefireVersion()), + new ComparableVersion("3.6.3"))); + } + + private ComparableVersion getCurrentMavenVersion() { + return new ComparableVersion(MavenSession.class.getPackage().getImplementationVersion()); + } + + @ParameterizedTest + @MethodSource("surefireVersions") + public void testGetMojoConfigValueReturnsNullIfValueNotSet( + ComparableVersion surefirePluginVersion, ComparableVersion minRequiredMavenVersion) + throws Exception { + Assumptions.assumeTrue( + minRequiredMavenVersion.compareTo(getCurrentMavenVersion()) <= 0, + "Newer maven version required to run chosen version of Surefire plugin"); + executeMaven( + this::assertGetMojoConfigValueReturnsNullIfValueNotSet, + "samplePom.xml", + String.format( + "org.apache.maven.plugins:maven-surefire-plugin:%s:test", surefirePluginVersion)); + } + + private boolean assertGetMojoConfigValueReturnsNullIfValueNotSet(ExecutionEvent executionEvent) { + MojoExecution mojoExecution = executionEvent.getMojoExecution(); + if (!MavenUtils.isTestExecution(mojoExecution)) { + return false; + } + MavenSession session = executionEvent.getSession(); + String forkCount = MavenUtils.getConfigurationValue(session, mojoExecution, "forkCount"); + assertThat(forkCount, equalTo(null)); + return true; + } + + @ParameterizedTest + @MethodSource("surefireVersions") + public void testGetMojoConfigValueReturnsConfiguredValue( + ComparableVersion surefirePluginVersion, ComparableVersion minRequiredMavenVersion) + throws Exception { + Assumptions.assumeTrue( + minRequiredMavenVersion.compareTo(getCurrentMavenVersion()) <= 0, + "Newer maven version required to run chosen version of Surefire plugin"); + executeMaven( + this::assertGetMojoConfigValueReturnsConfiguredValue, + "samplePom.xml", + String.format( + "org.apache.maven.plugins:maven-surefire-plugin:%s:test", surefirePluginVersion)); + } + + private boolean assertGetMojoConfigValueReturnsConfiguredValue(ExecutionEvent executionEvent) { + MojoExecution mojoExecution = executionEvent.getMojoExecution(); + if (!MavenUtils.isTestExecution(mojoExecution)) { + return false; + } + MavenSession session = executionEvent.getSession(); + String threadCount = MavenUtils.getConfigurationValue(session, mojoExecution, "threadCount"); + assertThat(threadCount, equalTo("112")); + return true; + } + + @ParameterizedTest + @MethodSource("surefireVersions") + public void testGetMojoConfigValueResolvesPropertyPlaceholders( + ComparableVersion surefirePluginVersion, ComparableVersion minRequiredMavenVersion) + throws Exception { + Assumptions.assumeTrue( + minRequiredMavenVersion.compareTo(getCurrentMavenVersion()) <= 0, + "Newer maven version required to run chosen version of Surefire plugin"); + executeMaven( + this::assertGetMojoConfigValueResolvesPropertyPlaceholders, + "samplePom.xml", + String.format( + "org.apache.maven.plugins:maven-surefire-plugin:%s:test", surefirePluginVersion)); + } + + private boolean assertGetMojoConfigValueResolvesPropertyPlaceholders( + ExecutionEvent executionEvent) { + MojoExecution mojoExecution = executionEvent.getMojoExecution(); + if (!MavenUtils.isTestExecution(mojoExecution)) { + return false; + } + MavenSession session = executionEvent.getSession(); + String forkedProcessExitTimeoutInSeconds = + MavenUtils.getConfigurationValue(session, mojoExecution, "forkedProcessTimeoutInSeconds"); + assertThat(forkedProcessExitTimeoutInSeconds, equalTo("887")); + return true; + } + + @ParameterizedTest + @MethodSource("surefireVersions") + public void testGetMojoConfigValueResolvesPropertiesSuppliedViaCmdLine( + ComparableVersion surefirePluginVersion, ComparableVersion minRequiredMavenVersion) + throws Exception { + Assumptions.assumeTrue( + minRequiredMavenVersion.compareTo(getCurrentMavenVersion()) <= 0, + "Newer maven version required to run chosen version of Surefire plugin"); + executeMaven( + this::assertGetMojoConfigValueResolvesPropertiesSuppliedViaCmdLine, + "samplePom.xml", + String.format( + "org.apache.maven.plugins:maven-surefire-plugin:%s:test", surefirePluginVersion), + "-Dsurefire.parallel.timeout=112233"); + } + + private boolean assertGetMojoConfigValueResolvesPropertiesSuppliedViaCmdLine( + ExecutionEvent executionEvent) { + MojoExecution mojoExecution = executionEvent.getMojoExecution(); + if (!MavenUtils.isTestExecution(mojoExecution)) { + return false; + } + MavenSession session = executionEvent.getSession(); + String parallelTestsTimeoutInSeconds = + MavenUtils.getConfigurationValue(session, mojoExecution, "parallelTestsTimeoutInSeconds"); + assertThat(parallelTestsTimeoutInSeconds, equalTo("112233")); + return true; + } + + @ParameterizedTest + @MethodSource("surefireVersions") + public void testGetArgLineResolvesLatePropertyPlaceholders( + ComparableVersion surefirePluginVersion, ComparableVersion minRequiredMavenVersion) + throws Exception { + Assumptions.assumeTrue( + minRequiredMavenVersion.compareTo(getCurrentMavenVersion()) <= 0, + "Newer maven version required to run chosen version of Surefire plugin"); + executeMaven( + this::assertGetArgLineResolvesLatePropertyPlaceholders, + "samplePom.xml", + String.format( + "org.apache.maven.plugins:maven-surefire-plugin:%s:test", surefirePluginVersion)); + } + + private boolean assertGetArgLineResolvesLatePropertyPlaceholders(ExecutionEvent executionEvent) { + MojoExecution mojoExecution = executionEvent.getMojoExecution(); + if (!MavenUtils.isTestExecution(mojoExecution)) { + return false; + } + MavenSession session = executionEvent.getSession(); + MavenProject project = executionEvent.getProject(); + String argLine = MavenUtils.getArgLine(session, project, mojoExecution); + assertThat(argLine, equalTo("-Xms128m -Xmx2g")); + return true; + } + + @ParameterizedTest + @MethodSource("surefireVersions") + public void testGetJacocoAgent( + ComparableVersion surefirePluginVersion, ComparableVersion minRequiredMavenVersion) + throws Exception { + Assumptions.assumeTrue( + minRequiredMavenVersion.compareTo(getCurrentMavenVersion()) <= 0, + "Newer maven version required to run chosen version of Surefire plugin"); + executeMaven(this::assertGetJacocoAgent, "samplePomJacoco.xml", "test"); + } + + private boolean assertGetJacocoAgent(ExecutionEvent executionEvent) { + MojoExecution mojoExecution = executionEvent.getMojoExecution(); + if (!MavenUtils.isTestExecution(mojoExecution)) { + return false; + } + MavenSession session = executionEvent.getSession(); + MavenProject project = executionEvent.getProject(); + JavaAgent jacocoAgent = MavenUtils.getJacocoAgent(session, project, mojoExecution); + assertThat(jacocoAgent, notNullValue()); + assertThat(jacocoAgent.getPath(), endsWith("org.jacoco.agent-0.8.11-runtime.jar")); + assertThat(jacocoAgent.getArguments(), notNullValue()); + return true; + } + + @ParameterizedTest + @MethodSource("surefireVersions") + public void testGetEffectiveJvmFallbackUsesJvmProperty( + ComparableVersion surefirePluginVersion, ComparableVersion minRequiredMavenVersion) + throws Exception { + Assumptions.assumeTrue( + minRequiredMavenVersion.compareTo(getCurrentMavenVersion()) <= 0, + "Newer maven version required to run chosen version of Surefire plugin"); + executeMaven( + this::assertGetEffectiveJvmFallbackUsesJvmProperty, + "samplePom.xml", + String.format( + "org.apache.maven.plugins:maven-surefire-plugin:%s:test", surefirePluginVersion)); + } + + private boolean assertGetEffectiveJvmFallbackUsesJvmProperty(ExecutionEvent executionEvent) { + MojoExecution mojoExecution = executionEvent.getMojoExecution(); + if (!MavenUtils.isTestExecution(mojoExecution)) { + return false; + } + MavenSession session = executionEvent.getSession(); + String effectiveJvm = MavenUtils.getEffectiveJvmFallback(session, mojoExecution); + assertThat(effectiveJvm, equalTo("jvm-config-property-value")); + return true; + } + + @ParameterizedTest + @MethodSource("surefireVersions") + public void testGetEffectiveJvmFallbackUsesToolchains( + ComparableVersion surefirePluginVersion, ComparableVersion minRequiredMavenVersion) + throws Exception { + Assumptions.assumeTrue( + minRequiredMavenVersion.compareTo(getCurrentMavenVersion()) <= 0, + "Newer maven version required to run chosen version of Surefire plugin"); + Assumptions.assumeTrue(surefirePluginVersion.compareTo(SUREFIRE_3_0_0) >= 0); + Assumptions.assumeTrue(getCurrentMavenVersion().compareTo(MAVEN_3_3_1) >= 0); + + File toolchainsFile = createToolchainsFile(); + executeMaven( + this::assertGetEffectiveJvmFallbackUsesToolchains, + "samplePomToolchains.xml", + String.format( + "org.apache.maven.plugins:maven-surefire-plugin:%s:test", surefirePluginVersion), + "--global-toolchains", + toolchainsFile.getAbsolutePath()); + } + + private boolean assertGetEffectiveJvmFallbackUsesToolchains(ExecutionEvent executionEvent) { + MojoExecution mojoExecution = executionEvent.getMojoExecution(); + if (!MavenUtils.isTestExecution(mojoExecution)) { + return false; + } + MavenSession session = executionEvent.getSession(); + String effectiveJvm = MavenUtils.getEffectiveJvmFallback(session, mojoExecution); + assertThat(effectiveJvm, endsWith("/my-jdk-home/bin/java")); + return true; + } + + /** + * "jdkHome" in toolchains.xml has to point to an existing folder, so this method processes + * toolchains template, substituting the path to the real my-jdk-home directory. + */ + private static File createToolchainsFile() + throws URISyntaxException, IOException, TemplateException { + File toolchainJdkHome = new File(MavenUtilsTest.class.getResource("my-jdk-home").toURI()); + Map replacements = + Collections.singletonMap("my_jdk_home_path", toolchainJdkHome.getAbsolutePath()); + + File toolchainsFile = WORKING_DIRECTORY.getRoot().resolve("toolchains.xml").toFile(); + try (FileWriter toolchainsFileWriter = new FileWriter(toolchainsFile)) { + Template coveragesTemplate = FREEMARKER.getTemplate("sampleToolchains.ftl"); + coveragesTemplate.process(replacements, toolchainsFileWriter); + } + return toolchainsFile; + } + + @ParameterizedTest + @MethodSource("surefireVersions") + public void testGetForkedJvmPath( + ComparableVersion surefirePluginVersion, ComparableVersion minRequiredMavenVersion) + throws Exception { + Assumptions.assumeTrue( + minRequiredMavenVersion.compareTo(getCurrentMavenVersion()) <= 0, + "Newer maven version required to run chosen version of Surefire plugin"); + executeMaven( + this::assertGetForkedJvmPath, + "samplePomJacoco.xml", + String.format( + "org.apache.maven.plugins:maven-surefire-plugin:%s:test", surefirePluginVersion)); + } + + private boolean assertGetForkedJvmPath(ExecutionEvent executionEvent) { + MojoExecution mojoExecution = executionEvent.getMojoExecution(); + if (!MavenUtils.isTestExecution(mojoExecution)) { + return false; + } + MavenSession session = executionEvent.getSession(); + Path jvmPath = MavenUtils.getForkedJvmPath(session, mojoExecution); + assertThat(jvmPath, hasToString(endsWith("/java"))); + return true; + } + + @ParameterizedTest + @MethodSource("surefireVersions") + public void testGetClasspath( + ComparableVersion surefirePluginVersion, ComparableVersion minRequiredMavenVersion) + throws Exception { + Assumptions.assumeTrue( + minRequiredMavenVersion.compareTo(getCurrentMavenVersion()) <= 0, + "Newer maven version required to run chosen version of Surefire plugin"); + executeMaven( + this::assertGetClasspath, + "samplePom.xml", + String.format( + "org.apache.maven.plugins:maven-surefire-plugin:%s:test", surefirePluginVersion)); + } + + private boolean assertGetClasspath(ExecutionEvent executionEvent) { + MojoExecution mojoExecution = executionEvent.getMojoExecution(); + if (!MavenUtils.isTestExecution(mojoExecution)) { + return false; + } + MavenSession session = executionEvent.getSession(); + List classpath = MavenUtils.getClasspath(session, mojoExecution); + assertThat(classpath, hasSize(5)); + assertThat(classpath, hasItem(hasToString(endsWith("/test-classes")))); + assertThat(classpath, hasItem(hasToString(endsWith("/classes")))); + assertThat(classpath, hasItem(hasToString(endsWith("/junit-4.13.2.jar")))); + assertThat(classpath, hasItem(hasToString(endsWith("/hamcrest-core-1.3.jar")))); + assertThat(classpath, hasItem(hasToString(endsWith("/commons-lang3-3.17.0.jar")))); + return true; + } + + @ParameterizedTest + @MethodSource("surefireVersions") + public void testGetClasspathConsidersAdditionalClasspathDependencies( + ComparableVersion surefirePluginVersion, ComparableVersion minRequiredMavenVersion) + throws Exception { + Assumptions.assumeTrue( + minRequiredMavenVersion.compareTo(getCurrentMavenVersion()) <= 0, + "Newer maven version required to run chosen version of Surefire plugin"); + Assumptions.assumeTrue(surefirePluginVersion.compareTo(SUREFIRE_3_2_0) >= 0); + executeMaven( + this::assertGetClasspathConsidersAdditionalClasspathDependencies, + "samplePomAdditionalClasspathDependencies.xml", + String.format( + "org.apache.maven.plugins:maven-surefire-plugin:%s:test", surefirePluginVersion)); + } + + private boolean assertGetClasspathConsidersAdditionalClasspathDependencies( + ExecutionEvent executionEvent) { + MojoExecution mojoExecution = executionEvent.getMojoExecution(); + if (!MavenUtils.isTestExecution(mojoExecution)) { + return false; + } + MavenSession session = executionEvent.getSession(); + List classpath = MavenUtils.getClasspath(session, mojoExecution); + assertThat(classpath, hasSize(5)); + assertThat(classpath, hasItem(hasToString(endsWith("/test-classes")))); + assertThat(classpath, hasItem(hasToString(endsWith("/classes")))); + assertThat(classpath, hasItem(hasToString(endsWith("/junit-4.13.2.jar")))); + assertThat(classpath, hasItem(hasToString(endsWith("/hamcrest-core-1.3.jar")))); + assertThat(classpath, hasItem(hasToString(endsWith("/commons-io-2.16.1.jar")))); + return true; + } + + @ParameterizedTest + @MethodSource("surefireVersions") + public void testGetClasspathConsidersAdditionalClasspathElements( + ComparableVersion surefirePluginVersion, ComparableVersion minRequiredMavenVersion) + throws Exception { + Assumptions.assumeTrue( + minRequiredMavenVersion.compareTo(getCurrentMavenVersion()) <= 0, + "Newer maven version required to run chosen version of Surefire plugin"); + executeMaven( + this::assertGetClasspathConsidersAdditionalClasspathElements, + "samplePomAdditionalClasspathElements.xml", + String.format( + "org.apache.maven.plugins:maven-surefire-plugin:%s:test", surefirePluginVersion)); + } + + private boolean assertGetClasspathConsidersAdditionalClasspathElements( + ExecutionEvent executionEvent) { + MojoExecution mojoExecution = executionEvent.getMojoExecution(); + if (!MavenUtils.isTestExecution(mojoExecution)) { + return false; + } + MavenSession session = executionEvent.getSession(); + List classpath = MavenUtils.getClasspath(session, mojoExecution); + assertThat(classpath, hasSize(6)); + assertThat(classpath, hasItem(hasToString(endsWith("/test-classes")))); + assertThat(classpath, hasItem(hasToString(endsWith("/classes")))); + assertThat(classpath, hasItem(hasToString(endsWith("/junit-4.13.2.jar")))); + assertThat(classpath, hasItem(hasToString(endsWith("/hamcrest-core-1.3.jar")))); + assertThat(classpath, hasItem(hasToString(equalTo("/path/to/additional/classpath/element")))); + assertThat( + classpath, hasItem(hasToString(equalTo("/path/to/another/additional/classpath/element")))); + return true; + } + + @ParameterizedTest + @MethodSource("surefireVersions") + public void testGetContainer( + ComparableVersion surefirePluginVersion, ComparableVersion minRequiredMavenVersion) + throws Exception { + Assumptions.assumeTrue( + minRequiredMavenVersion.compareTo(getCurrentMavenVersion()) <= 0, + "Newer maven version required to run chosen version of Surefire plugin"); + executeMaven( + this::assertGetContainer, + "samplePom.xml", + String.format( + "org.apache.maven.plugins:maven-surefire-plugin:%s:test", surefirePluginVersion)); + } + + private boolean assertGetContainer(ExecutionEvent executionEvent) { + MojoExecution mojoExecution = executionEvent.getMojoExecution(); + if (!MavenUtils.isTestExecution(mojoExecution)) { + return false; + } + MavenSession session = executionEvent.getSession(); + PlexusContainer container = MavenUtils.getContainer(session); + assertThat(container, notNullValue()); + return true; + } + + private static String getLatestMavenSurefireVersion() { + OkHttpClient client = new OkHttpClient(); + Request request = + new Request.Builder() + .url( + "https://repo.maven.apache.org/maven2/org/apache/maven/plugins/maven-surefire-plugin/maven-metadata.xml") + .build(); + try (Response response = client.newCall(request).execute()) { + if (response.isSuccessful()) { + DocumentBuilderFactory dbFactory = DocumentBuilderFactory.newInstance(); + DocumentBuilder dBuilder = dbFactory.newDocumentBuilder(); + Document doc = dBuilder.parse(response.body().byteStream()); + doc.getDocumentElement().normalize(); + + NodeList versionList = doc.getElementsByTagName("latest"); + if (versionList.getLength() > 0) { + String version = versionList.item(0).getTextContent(); + if (!version.contains("alpha") && !version.contains("beta")) { + LOGGER.info("Will run the 'latest' tests with version " + version); + return version; + } + } + } else { + LOGGER.warn( + "Could not get latest Maven Surefire version, response from repo.maven.apache.org is " + + response.code() + + ":" + + response.body().string()); + } + } catch (Exception e) { + LOGGER.warn("Could not get latest Maven Surefire version", e); + } + String hardcodedLatestVersion = "3.5.0"; // latest version that is known to work + LOGGER.info("Will run the 'latest' tests with hard-coded version " + hardcodedLatestVersion); + return hardcodedLatestVersion; + } +} From 3ccd7f51955001049626bac556e9dbaa8adaec47 Mon Sep 17 00:00:00 2001 From: Daniel Mohedano Date: Fri, 19 Sep 2025 12:34:25 +0200 Subject: [PATCH 3/5] fix: add new line to stat --- .../trace/common/writer/ddagent/SimpleUtf8CacheTest.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/dd-trace-core/src/test/java/datadog/trace/common/writer/ddagent/SimpleUtf8CacheTest.java b/dd-trace-core/src/test/java/datadog/trace/common/writer/ddagent/SimpleUtf8CacheTest.java index 811ff56ce57..dd062c3820a 100644 --- a/dd-trace-core/src/test/java/datadog/trace/common/writer/ddagent/SimpleUtf8CacheTest.java +++ b/dd-trace-core/src/test/java/datadog/trace/common/writer/ddagent/SimpleUtf8CacheTest.java @@ -153,6 +153,6 @@ static final String nextValue() { } static final void printStats(SimpleUtf8Cache cache) { - System.out.printf("eden hits: %5d\tpromotions: %5d", cache.hits, cache.evictions); + System.out.printf("eden hits: %5d\tpromotions: %5d%n", cache.hits, cache.evictions); } } From 1d17958b839858df7d203d78399a19def85d0b2f Mon Sep 17 00:00:00 2001 From: Douglas Q Hawkins Date: Fri, 19 Sep 2025 09:08:25 -0400 Subject: [PATCH 4/5] Making bigStrings no cache tests more reliable - updating tests to not use magic number and use MAX_ENTRY_LEN of their respective cache - had to make MAX_ENTRY_LEN package visible in both caches --- .../trace/common/writer/ddagent/GenerationalUtf8Cache.java | 2 +- .../datadog/trace/common/writer/ddagent/SimpleUtf8Cache.java | 2 +- .../trace/common/writer/ddagent/GenerationalUtf8CacheTest.java | 2 +- .../trace/common/writer/ddagent/SimpleUtf8CacheTest.java | 2 +- 4 files changed, 4 insertions(+), 4 deletions(-) diff --git a/dd-trace-core/src/main/java/datadog/trace/common/writer/ddagent/GenerationalUtf8Cache.java b/dd-trace-core/src/main/java/datadog/trace/common/writer/ddagent/GenerationalUtf8Cache.java index ec815ce3936..12854f86d5e 100644 --- a/dd-trace-core/src/main/java/datadog/trace/common/writer/ddagent/GenerationalUtf8Cache.java +++ b/dd-trace-core/src/main/java/datadog/trace/common/writer/ddagent/GenerationalUtf8Cache.java @@ -85,7 +85,7 @@ public final class GenerationalUtf8Cache implements EncodingCache { private static final double EDEN_PROPORTION = 1D / 3D; private static final double TENURED_PROPORTION = 1 - EDEN_PROPORTION; - private static final int MAX_ENTRY_LEN = 256; + static final int MAX_ENTRY_LEN = 256; private final CacheEntry[] edenEntries; private final int[] edenMarkers; diff --git a/dd-trace-core/src/main/java/datadog/trace/common/writer/ddagent/SimpleUtf8Cache.java b/dd-trace-core/src/main/java/datadog/trace/common/writer/ddagent/SimpleUtf8Cache.java index b1786753246..ab751b6a5ac 100644 --- a/dd-trace-core/src/main/java/datadog/trace/common/writer/ddagent/SimpleUtf8Cache.java +++ b/dd-trace-core/src/main/java/datadog/trace/common/writer/ddagent/SimpleUtf8Cache.java @@ -53,7 +53,7 @@ public final class SimpleUtf8Cache implements EncodingCache { private static final double HIT_DECAY = 0.5D; private static final double PURGE_THRESHOLD = 0.25D; - private static final int MAX_ENTRY_LEN = 128; + static final int MAX_ENTRY_LEN = 128; protected int hits = 0; protected int evictions = 0; diff --git a/dd-trace-core/src/test/java/datadog/trace/common/writer/ddagent/GenerationalUtf8CacheTest.java b/dd-trace-core/src/test/java/datadog/trace/common/writer/ddagent/GenerationalUtf8CacheTest.java index 9d9d0fde384..facd64e71dc 100644 --- a/dd-trace-core/src/test/java/datadog/trace/common/writer/ddagent/GenerationalUtf8CacheTest.java +++ b/dd-trace-core/src/test/java/datadog/trace/common/writer/ddagent/GenerationalUtf8CacheTest.java @@ -148,7 +148,7 @@ public void fuzz() { @Test public void bigString_dont_cache() { String lorem = "Lorem ipsum dolor sit amet"; - while (lorem.length() < 500) { + while (lorem.length() <= GenerationalUtf8Cache.MAX_ENTRY_LEN) { lorem += lorem; } byte[] expected = lorem.getBytes(StandardCharsets.UTF_8); diff --git a/dd-trace-core/src/test/java/datadog/trace/common/writer/ddagent/SimpleUtf8CacheTest.java b/dd-trace-core/src/test/java/datadog/trace/common/writer/ddagent/SimpleUtf8CacheTest.java index dd062c3820a..521bf229e4d 100644 --- a/dd-trace-core/src/test/java/datadog/trace/common/writer/ddagent/SimpleUtf8CacheTest.java +++ b/dd-trace-core/src/test/java/datadog/trace/common/writer/ddagent/SimpleUtf8CacheTest.java @@ -96,7 +96,7 @@ public void fuzz() { @Test public void bigString_dont_cache() { String lorem = "Lorem ipsum dolor sit amet"; - while (lorem.length() < 100) { + while (lorem.length() <= SimpleUtf8Cache.MAX_ENTRY_LEN) { lorem += lorem; } byte[] expected = lorem.getBytes(StandardCharsets.UTF_8); From 67f1cf75fc8fd6e52d571ae8f02811e8d5ba7381 Mon Sep 17 00:00:00 2001 From: Daniel Mohedano Date: Fri, 19 Sep 2025 16:21:37 +0200 Subject: [PATCH 5/5] fix: tempdir usage without getRoot --- .../trace/instrumentation/maven3/AbstractMavenTest.java | 6 ++---- .../trace/instrumentation/maven3/MavenUtilsTest.java | 2 +- 2 files changed, 3 insertions(+), 5 deletions(-) diff --git a/dd-java-agent/instrumentation/maven-3.2.1/src/test/java/datadog/trace/instrumentation/maven3/AbstractMavenTest.java b/dd-java-agent/instrumentation/maven-3.2.1/src/test/java/datadog/trace/instrumentation/maven3/AbstractMavenTest.java index 9ec8a47d8ad..5dc7a261d2c 100644 --- a/dd-java-agent/instrumentation/maven-3.2.1/src/test/java/datadog/trace/instrumentation/maven3/AbstractMavenTest.java +++ b/dd-java-agent/instrumentation/maven-3.2.1/src/test/java/datadog/trace/instrumentation/maven3/AbstractMavenTest.java @@ -20,8 +20,7 @@ public abstract class AbstractMavenTest { protected AbstractMavenTest() { System.setProperty( - "maven.multiModuleProjectDirectory", - WORKING_DIRECTORY.getRoot().toAbsolutePath().toString()); + "maven.multiModuleProjectDirectory", WORKING_DIRECTORY.toAbsolutePath().toString()); } protected void executeMaven( @@ -58,8 +57,7 @@ protected void customizeContainer(PlexusContainer container) { arguments[2] = goal; System.arraycopy(additionalArgs, 0, arguments, 3, additionalArgs.length); - mavenCli.doMain( - arguments, WORKING_DIRECTORY.getRoot().toAbsolutePath().toString(), stdOut, stderr); + mavenCli.doMain(arguments, WORKING_DIRECTORY.toAbsolutePath().toString(), stdOut, stderr); Exception error = spy.handlerError.get(); if (error != null) { diff --git a/dd-java-agent/instrumentation/maven-3.2.1/src/test/java/datadog/trace/instrumentation/maven3/MavenUtilsTest.java b/dd-java-agent/instrumentation/maven-3.2.1/src/test/java/datadog/trace/instrumentation/maven3/MavenUtilsTest.java index 28ea052f672..fdf39a29966 100644 --- a/dd-java-agent/instrumentation/maven-3.2.1/src/test/java/datadog/trace/instrumentation/maven3/MavenUtilsTest.java +++ b/dd-java-agent/instrumentation/maven-3.2.1/src/test/java/datadog/trace/instrumentation/maven3/MavenUtilsTest.java @@ -304,7 +304,7 @@ private static File createToolchainsFile() Map replacements = Collections.singletonMap("my_jdk_home_path", toolchainJdkHome.getAbsolutePath()); - File toolchainsFile = WORKING_DIRECTORY.getRoot().resolve("toolchains.xml").toFile(); + File toolchainsFile = WORKING_DIRECTORY.resolve("toolchains.xml").toFile(); try (FileWriter toolchainsFileWriter = new FileWriter(toolchainsFile)) { Template coveragesTemplate = FREEMARKER.getTemplate("sampleToolchains.ftl"); coveragesTemplate.process(replacements, toolchainsFileWriter);