diff --git a/pitest-command-line/src/main/java/org/pitest/mutationtest/commandline/OptionsParser.java b/pitest-command-line/src/main/java/org/pitest/mutationtest/commandline/OptionsParser.java index 8e8bec934..fc9595f68 100644 --- a/pitest-command-line/src/main/java/org/pitest/mutationtest/commandline/OptionsParser.java +++ b/pitest-command-line/src/main/java/org/pitest/mutationtest/commandline/OptionsParser.java @@ -148,8 +148,12 @@ public class OptionsParser { private final ArgumentAcceptingOptionSpec exportLineCoverageSpec; private final OptionSpec javaExecutable; private final OptionSpec pluginPropertiesSpec; + + // unused but temporarily retained private final OptionSpec testPluginSpec; private final ArgumentAcceptingOptionSpec includeLaunchClasspathSpec; + + // unused but temporarily retained private final ArgumentAcceptingOptionSpec useClasspathJarSpec; private final OptionSpec projectBaseSpec; private final OptionSpec inputEncoding; @@ -463,8 +467,6 @@ private ParseResult parseCommandLine(final ReportOptions data, data.setIncludeLaunchClasspath(booleanValue(includeLaunchClasspathSpec, userArgs)); - data.setUseClasspathJar(booleanValue(useClasspathJarSpec, userArgs)); - data.setShouldCreateTimestampedReports(booleanValue(timestampedReportsSpec, userArgs)); data.setNumberOfThreads(this.threadsSpec.value(userArgs)); @@ -559,7 +561,7 @@ private void setClassPath(final OptionSet userArgs, final ReportOptions data) { LOG.warning("Unable to read class path file:" + this.classPathFile.value(userArgs).getAbsolutePath() + " - " + ioe.getMessage()); } - data.setUseClasspathJar(true); + } elements.addAll(this.additionalClassPathSpec.values(userArgs)); data.setClassPathElements(elements); diff --git a/pitest-command-line/src/test/java/org/pitest/mutationtest/commandline/OptionsParserTest.java b/pitest-command-line/src/test/java/org/pitest/mutationtest/commandline/OptionsParserTest.java index 2bdc9295b..fdce204a8 100644 --- a/pitest-command-line/src/test/java/org/pitest/mutationtest/commandline/OptionsParserTest.java +++ b/pitest-command-line/src/test/java/org/pitest/mutationtest/commandline/OptionsParserTest.java @@ -350,14 +350,6 @@ public void shouldAcceptFileWithListOfAdditionalClassPathElements() { assertTrue(actual.contains("/etc/bar")); } - @Test - public void alsoSetsUseClasspathJarWhenClasspathFileProvided() { - final ClassLoader classLoader = getClass().getClassLoader(); - final File classPathFile = new File(classLoader.getResource("testClassPathFile.txt").getFile()); - final ReportOptions ro = parseAddingRequiredArgs("--classPathFile", - classPathFile.getAbsolutePath()); - assertThat(ro.useClasspathJar()).isTrue(); - } @Test public void shouldFailWhenNoMutationsSetByDefault() { @@ -621,28 +613,10 @@ public void shouldIncludePluginPropertyValuesWhenMultipleKeys() { assertEquals("2", actual.getFreeFormProperties().getProperty("bar")); } - @Test - public void shouldDefaultToNotUsingAClasspathJar() { - final ReportOptions actual = parseAddingRequiredArgs(); - assertFalse(actual.useClasspathJar()); - } - - @Test - public void shouldUseClasspathJarWhenFlagSet() { - final ReportOptions actual = parseAddingRequiredArgs("--useClasspathJar"); - assertTrue(actual.useClasspathJar()); - } - - @Test - public void shouldUseClasspathJarWhenTrueSupplied() { - final ReportOptions actual = parseAddingRequiredArgs("--useClasspathJar=true"); - assertTrue(actual.useClasspathJar()); - } @Test - public void shouldNotUseClasspathJarWhenFalseSupplied() { - final ReportOptions actual = parseAddingRequiredArgs("--useClasspathJar=false"); - assertFalse(actual.useClasspathJar()); + public void shouldNotErrorWhenLegacyClasspathJarWhenFlagSet() { + assertThatCode(() -> parseAddingRequiredArgs("--useClasspathJar")).doesNotThrowAnyException(); } @Test diff --git a/pitest-entry/src/main/java/org/pitest/coverage/execute/CoverageProcess.java b/pitest-entry/src/main/java/org/pitest/coverage/execute/CoverageProcess.java index 22a9d863c..7644446c8 100644 --- a/pitest-entry/src/main/java/org/pitest/coverage/execute/CoverageProcess.java +++ b/pitest-entry/src/main/java/org/pitest/coverage/execute/CoverageProcess.java @@ -20,7 +20,7 @@ public class CoverageProcess { public CoverageProcess(final ProcessArgs processArgs, final CoverageOptions arguments, final ServerSocket socket, final List testClasses, final Consumer handler) { - this.process = new WrappingProcess(socket.getLocalPort(), processArgs, + this.process = WrappingProcess.create(socket.getLocalPort(), processArgs, CoverageMinion.class); this.crt = new CommunicationThread(socket, new SendData(arguments, testClasses), new Receive(handler)); diff --git a/pitest-entry/src/main/java/org/pitest/mutationtest/config/ReportOptions.java b/pitest-entry/src/main/java/org/pitest/mutationtest/config/ReportOptions.java index a4ec7f451..031e05d0c 100644 --- a/pitest-entry/src/main/java/org/pitest/mutationtest/config/ReportOptions.java +++ b/pitest-entry/src/main/java/org/pitest/mutationtest/config/ReportOptions.java @@ -145,7 +145,6 @@ public class ReportOptions { private String testPlugin = ""; - private boolean useClasspathJar; private Path projectBase; private Charset inputEncoding; @@ -625,14 +624,6 @@ public TestPluginArguments createMinionSettings() { this.getIncludedTestMethods(), this.skipFailingTests()); } - public boolean useClasspathJar() { - return useClasspathJar; - } - - public void setUseClasspathJar(boolean useClasspathJar) { - this.useClasspathJar = useClasspathJar; - } - public Path getProjectBase() { return projectBase; } @@ -729,7 +720,6 @@ public String toString() { .add("excludedRunners=" + excludedRunners) .add("includedTestMethods=" + includedTestMethods) .add("testPlugin='" + testPlugin + "'") - .add("useClasspathJar=" + useClasspathJar) .add("projectBase=" + projectBase) .add("inputEncoding=" + inputEncoding) .add("outputEncoding=" + outputEncoding) diff --git a/pitest-entry/src/main/java/org/pitest/mutationtest/execute/MutationTestProcess.java b/pitest-entry/src/main/java/org/pitest/mutationtest/execute/MutationTestProcess.java index 27b0d50e2..a79667c73 100644 --- a/pitest-entry/src/main/java/org/pitest/mutationtest/execute/MutationTestProcess.java +++ b/pitest-entry/src/main/java/org/pitest/mutationtest/execute/MutationTestProcess.java @@ -23,7 +23,7 @@ public class MutationTestProcess { public MutationTestProcess(final ServerSocket socket, final ProcessArgs processArgs, final MinionArguments arguments) { - this.process = new WrappingProcess(socket.getLocalPort(), processArgs, + this.process = WrappingProcess.create(socket.getLocalPort(), processArgs, MutationTestMinion.class); this.idMap = new ConcurrentHashMap<>(); diff --git a/pitest-entry/src/main/java/org/pitest/mutationtest/tooling/EntryPoint.java b/pitest-entry/src/main/java/org/pitest/mutationtest/tooling/EntryPoint.java index 75be0707f..7b7d46256 100644 --- a/pitest-entry/src/main/java/org/pitest/mutationtest/tooling/EntryPoint.java +++ b/pitest-entry/src/main/java/org/pitest/mutationtest/tooling/EntryPoint.java @@ -109,8 +109,7 @@ public AnalysisResult execute(File baseDir, ReportOptions data, final CoverageOptions coverageOptions = settings.createCoverageOptions(); final LaunchOptions launchOptions = new LaunchOptions(ja, - settings.getJavaExecutable(), createJvmArgs(data), environmentVariables) - .usingClassPathJar(data.useClasspathJar()); + settings.getJavaExecutable(), createJvmArgs(data), environmentVariables); final ProjectClassPaths cps = data.getMutationClassPaths(); diff --git a/pitest-entry/src/main/java/org/pitest/process/Java9Process.java b/pitest-entry/src/main/java/org/pitest/process/Java9Process.java new file mode 100644 index 000000000..abbcd5255 --- /dev/null +++ b/pitest-entry/src/main/java/org/pitest/process/Java9Process.java @@ -0,0 +1,164 @@ +package org.pitest.process; + +import static java.util.Arrays.asList; +import static org.pitest.functional.prelude.Prelude.or; +import java.io.File; +import java.io.IOException; +import java.lang.management.ManagementFactory; +import java.lang.management.RuntimeMXBean; +import java.nio.file.Files; +import java.nio.file.Path; +import java.util.ArrayList; +import java.util.List; +import java.util.Map; +import java.util.Optional; +import java.util.function.Predicate; + +import org.pitest.functional.FCollection; + +/** + * Process for java 9+, using file to pass all parameters + */ +public class Java9Process implements WrappingProcess { + + private final int port; + private final ProcessArgs processArgs; + private final Class minionClass; + private JavaProcess process; + + private final long pid = ProcessHandle.current().pid(); + + private static int counter = 0; + + public Java9Process(int port, ProcessArgs args, Class minionClass) { + this.port = port; + this.processArgs = args; + this.minionClass = minionClass; + } + + public void start() throws IOException { + String[] args = { "" + this.port }; + + ProcessBuilder processBuilder = createProcessBuilder( + this.processArgs.getJavaExecutable(), + this.processArgs.getJvmArgs(), + this.minionClass, asList(args), + this.processArgs.getJavaAgentFinder(), + this.processArgs.getLaunchClassPath()); + + + configureProcessBuilder(processBuilder, this.processArgs.getWorkingDir(), + this.processArgs.getEnvironmentVariables()); + + Process process = processBuilder.start(); + this.process = new JavaProcess(process, this.processArgs.getStdout(), + this.processArgs.getStdErr()); + } + + public boolean isAlive() { + return process.isAlive(); + } + + private void configureProcessBuilder(ProcessBuilder processBuilder, + File workingDirectory, Map environmentVariables) { + processBuilder.directory(workingDirectory); + Map environment = processBuilder.environment(); + + environment.putAll(environmentVariables); + } + + public void destroy() { + this.process.destroy(); + } + + public JavaProcess getProcess() { + return this.process; + } + + private ProcessBuilder createProcessBuilder(String javaProc, + List args, Class mainClass, List programArgs, + JavaAgent javaAgent, String classPath) { + List cmd = createLaunchArgs(javaAgent, args, mainClass, + programArgs, classPath); + + removeJacocoAgent(cmd); + + try { + // all arguments are passed via a temporary file, thereby avoiding command line length limits + Path argsFile = createArgsFile(cmd); + return new ProcessBuilder(asList(javaProc, "@" + argsFile.toFile().getAbsolutePath())); + } catch (IOException e) { + throw new RuntimeException(e); + } + + } + private void removeJacocoAgent(List cmd) { + removeFromClassPath(cmd, line -> line.startsWith("-javaagent") && line.contains("jacoco")); + } + + private static void removeFromClassPath(List cmd, Predicate match) { + for (int i = cmd.size() - 1; i >= 0; i--) { + if (match.test(cmd.get(i))) { + cmd.remove(i); + } + } + } + + private List createLaunchArgs(JavaAgent agentJarLocator, List args, Class mainClass, + List programArgs, String classPath) { + + List cmd = new ArrayList<>(); + + cmd.add("-classpath"); + cmd.add(classPath); + + addPITJavaAgent(agentJarLocator, cmd); + + cmd.addAll(args); + + addLaunchJavaAgents(cmd); + + cmd.add(mainClass.getName()); + cmd.addAll(programArgs); + return cmd; + } + + private Path createArgsFile(List cmd) throws IOException { + // To avoid conflicts with running analysis, we use the PID as part of the file name + // To prevent conflicts between multiple threads counter is used + // All files should be deleted on process exit, although some garbage may be left + // if the process is killed. Files are however created in the system temp directory + // so should be cleaned up on reboot + String name = "pitest-args-" + pid + "-" + nextCounter(); + Path args = Files.createTempFile(name, ".args"); + args.toFile().deleteOnExit(); + Files.write(args, cmd); + return args; + } + + private static void addPITJavaAgent(JavaAgent agentJarLocator, + List cmd) { + final Optional jarLocation = agentJarLocator.getJarLocation(); + jarLocation.ifPresent(l -> cmd.add("-javaagent:" + l)); + } + + private static void addLaunchJavaAgents(List cmd) { + RuntimeMXBean rt = ManagementFactory.getRuntimeMXBean(); + List agents = FCollection.filter(rt.getInputArguments(), + or(isJavaAgentParam(), isEnvironmentSetting())); + cmd.addAll(agents); + } + + private static Predicate isEnvironmentSetting() { + return a -> a.startsWith("-D"); + } + + private static Predicate isJavaAgentParam() { + return a -> a.toLowerCase().startsWith("-javaagent"); + } + + private static synchronized int nextCounter() { + return counter++; + } + +} diff --git a/pitest-entry/src/main/java/org/pitest/process/LaunchOptions.java b/pitest-entry/src/main/java/org/pitest/process/LaunchOptions.java index 170356728..fa1fc8bb1 100644 --- a/pitest-entry/src/main/java/org/pitest/process/LaunchOptions.java +++ b/pitest-entry/src/main/java/org/pitest/process/LaunchOptions.java @@ -25,30 +25,20 @@ public class LaunchOptions { private final List childJVMArgs; private final JavaExecutableLocator javaExecutable; private final Map environmentVariables; - private final boolean usingClassPathJar; public LaunchOptions(JavaAgent javaAgentFinder) { this(javaAgentFinder, new DefaultJavaExecutableLocator(), Collections .emptyList(), new HashMap<>()); } - - public LaunchOptions(JavaAgent javaAgentFinder, - JavaExecutableLocator javaExecutable, - List childJVMArgs, - Map environmentVariables) { - this(javaAgentFinder, javaExecutable, childJVMArgs, environmentVariables, false); - } public LaunchOptions(JavaAgent javaAgentFinder, JavaExecutableLocator javaExecutable, List childJVMArgs, - Map environmentVariables, - boolean usingClassPathJar) { + Map environmentVariables) { this.javaAgentFinder = javaAgentFinder; this.childJVMArgs = childJVMArgs; this.javaExecutable = javaExecutable; this.environmentVariables = environmentVariables; - this.usingClassPathJar = usingClassPathJar; } public JavaAgent getJavaAgentFinder() { @@ -67,11 +57,4 @@ public Map getEnvironmentVariables() { return this.environmentVariables; } - public LaunchOptions usingClassPathJar(boolean useJar) { - return new LaunchOptions(javaAgentFinder, javaExecutable, childJVMArgs, environmentVariables, useJar); - } - - public boolean useClasspathJar() { - return usingClassPathJar; - } } diff --git a/pitest-entry/src/main/java/org/pitest/process/ProcessArgs.java b/pitest-entry/src/main/java/org/pitest/process/ProcessArgs.java index 34aae0570..9bec81152 100644 --- a/pitest-entry/src/main/java/org/pitest/process/ProcessArgs.java +++ b/pitest-entry/src/main/java/org/pitest/process/ProcessArgs.java @@ -35,7 +35,6 @@ public final class ProcessArgs { private File workingDir = null; private String javaExecutable; private Map environmentVariables; - private boolean useClasspathJar = false; private ProcessArgs(final String launchClassPath) { this.launchClassPath = launchClassPath; @@ -92,16 +91,12 @@ public String getJavaExecutable() { return this.javaExecutable; } - public boolean useClasspathJar() { - return useClasspathJar; - } - + public ProcessArgs andLaunchOptions(final LaunchOptions launchOptions) { this.jvmArgs = launchOptions.getChildJVMArgs(); this.javaAgentFinder = launchOptions.getJavaAgentFinder(); this.javaExecutable = launchOptions.getJavaExecutable(); this.environmentVariables = launchOptions.getEnvironmentVariables(); - this.useClasspathJar = launchOptions.useClasspathJar(); return this; } diff --git a/pitest-entry/src/main/java/org/pitest/process/WrappingProcess.java b/pitest-entry/src/main/java/org/pitest/process/WrappingProcess.java index aa6aca8eb..72925abab 100644 --- a/pitest-entry/src/main/java/org/pitest/process/WrappingProcess.java +++ b/pitest-entry/src/main/java/org/pitest/process/WrappingProcess.java @@ -1,167 +1,18 @@ package org.pitest.process; -import static org.pitest.functional.prelude.Prelude.or; -import java.io.File; import java.io.IOException; -import java.lang.management.ManagementFactory; -import java.lang.management.RuntimeMXBean; -import java.util.ArrayList; -import java.util.Arrays; -import java.util.List; -import java.util.Map; -import java.util.Optional; -import java.util.function.Predicate; -import org.pitest.functional.FCollection; -import org.pitest.util.ManifestUtils; +public interface WrappingProcess { -public class WrappingProcess { - - private final int port; - private final ProcessArgs processArgs; - private final Class minionClass; - - private JavaProcess process; - - public WrappingProcess(int port, ProcessArgs args, Class minionClass) { - this.port = port; - this.processArgs = args; - this.minionClass = minionClass; - } - - public void start() throws IOException { - final String[] args = { "" + this.port }; - - final ProcessBuilder processBuilder = createProcessBuilder( - this.processArgs.getJavaExecutable(), - this.processArgs.getJvmArgs(), - this.minionClass, Arrays.asList(args), - this.processArgs.getJavaAgentFinder(), - this.processArgs.getLaunchClassPath()); - - - setClassPathInEnvironment(processBuilder); - - configureProcessBuilder(processBuilder, this.processArgs.getWorkingDir(), - this.processArgs.getEnvironmentVariables()); - - final Process process = processBuilder.start(); - this.process = new JavaProcess(process, this.processArgs.getStdout(), - this.processArgs.getStdErr()); - } - - public boolean isAlive() { - return process.isAlive(); - } - - - // Reportedly passing the classpath as an environment variable rather than on the command - // line increases the allowable size of the classpath, but this has not been confirmed - private void setClassPathInEnvironment(final ProcessBuilder processBuilder) { - if (!processArgs.useClasspathJar()) { - processBuilder.environment().put("CLASSPATH", this.processArgs.getLaunchClassPath()); - } - } - - private void configureProcessBuilder(ProcessBuilder processBuilder, - File workingDirectory, Map environmentVariables) { - processBuilder.directory(workingDirectory); - final Map environment = processBuilder.environment(); - - for (final Map.Entry entry : environmentVariables.entrySet()) { - environment.put(entry.getKey(), entry.getValue()); - } - } - - public void destroy() { - this.process.destroy(); - } - - private ProcessBuilder createProcessBuilder(String javaProc, - List args, Class mainClass, List programArgs, - JavaAgent javaAgent, String classPath) { - final List cmd = createLaunchArgs(javaProc, javaAgent, args, mainClass, - programArgs, classPath); - - // IBM jdk adds this, thereby breaking everything - removeClassPathProperties(cmd); - - removeJacocoAgent(cmd); - - return new ProcessBuilder(cmd); - } - - private void removeJacocoAgent(List cmd) { - removeFromClassPath(cmd, line -> line.startsWith("-javaagent") && line.contains("jacoco")); - } - - private static void removeClassPathProperties(List cmd) { - removeFromClassPath(cmd, s -> s.startsWith("-Djava.class.path")); - } - - private static void removeFromClassPath(List cmd, Predicate match) { - for (int i = cmd.size() - 1; i >= 0; i--) { - if (match.test(cmd.get(i))) { - cmd.remove(i); - } + static WrappingProcess create(int port, ProcessArgs args, Class minionClass) { + return new Java9Process(port, args, minionClass); } - } - - private List createLaunchArgs(String javaProcess, - JavaAgent agentJarLocator, List args, Class mainClass, - List programArgs, String classPath) { - - final List cmd = new ArrayList<>(); - cmd.add(javaProcess); - - createClasspathJar(classPath, cmd); - - addPITJavaAgent(agentJarLocator, cmd); - - cmd.addAll(args); - - addLaunchJavaAgents(cmd); - - cmd.add(mainClass.getName()); - cmd.addAll(programArgs); - return cmd; - } - - private void createClasspathJar(String classPath, final List cmd) { - if (this.processArgs.useClasspathJar()) { - try { - cmd.add("-classpath"); - cmd.add( - ManifestUtils.createClasspathJarFile(classPath).getAbsolutePath()); - } catch (Exception e) { - throw new RuntimeException("Unable to create jar to contain classpath", - e); - } - } - } - - private static void addPITJavaAgent(JavaAgent agentJarLocator, - List cmd) { - final Optional jarLocation = agentJarLocator.getJarLocation(); - jarLocation.ifPresent(l -> cmd.add("-javaagent:" + l)); - } - private static void addLaunchJavaAgents(List cmd) { - final RuntimeMXBean rt = ManagementFactory.getRuntimeMXBean(); - final List agents = FCollection.filter(rt.getInputArguments(), - or(isJavaAgentParam(), isEnvironmentSetting())); - cmd.addAll(agents); - } + void start() throws IOException; - private static Predicate isEnvironmentSetting() { - return a -> a.startsWith("-D"); - } + boolean isAlive(); - private static Predicate isJavaAgentParam() { - return a -> a.toLowerCase().startsWith("-javaagent"); - } + void destroy(); - public JavaProcess getProcess() { - return this.process; - } + JavaProcess getProcess(); } diff --git a/pitest-entry/src/test/java/org/pitest/process/WrappingProcessTest.java b/pitest-entry/src/test/java/org/pitest/process/WrappingProcessTest.java index 515889bea..2e43788ed 100644 --- a/pitest-entry/src/test/java/org/pitest/process/WrappingProcessTest.java +++ b/pitest-entry/src/test/java/org/pitest/process/WrappingProcessTest.java @@ -42,7 +42,7 @@ public void waitToDieShouldReturnProcessExitCode() throws IOException, .andLaunchOptions(launchOptions).andStdout(nullHandler()) .andStderr(nullHandler()); - final WrappingProcess wrappingProcess = new WrappingProcess(-1, processArgs, + final WrappingProcess wrappingProcess = WrappingProcess.create(-1, processArgs, getClass()); wrappingProcess.start(); final JavaProcess process = wrappingProcess.getProcess(); diff --git a/pitest-maven/src/main/java/org/pitest/maven/MojoToReportOptionsConverter.java b/pitest-maven/src/main/java/org/pitest/maven/MojoToReportOptionsConverter.java index a742fb635..1f9c98b8b 100644 --- a/pitest-maven/src/main/java/org/pitest/maven/MojoToReportOptionsConverter.java +++ b/pitest-maven/src/main/java/org/pitest/maven/MojoToReportOptionsConverter.java @@ -209,7 +209,6 @@ private ReportOptions parseReportOptions(final List classPath) { data.setCodePaths(codePaths); } - data.setUseClasspathJar(this.mojo.isUseClasspathJar()); data.setClassPathElements(classPath); data.setFailWhenNoMutations(shouldFailWhenNoMutations()); diff --git a/pitest-maven/src/main/java/org/pitest/maven/PitMojo.java b/pitest-maven/src/main/java/org/pitest/maven/PitMojo.java index c55b3560a..ae41bbd32 100644 --- a/pitest-maven/src/main/java/org/pitest/maven/PitMojo.java +++ b/pitest-maven/src/main/java/org/pitest/maven/PitMojo.java @@ -423,9 +423,7 @@ public final class PitMojo extends AbstractMojo { /** - * Communicate the classpath using a temporary jar with a classpath - * manifest. This allows support of very large classpaths but may cause - * issues with certain libraries. + * Unused since 1.18.0. Temporarily left in place */ @Parameter(property = "useClasspathJar", defaultValue = "false") private boolean useClasspathJar; @@ -824,10 +822,6 @@ public ArrayList getFeatures() { return consolidated; } - public boolean isUseClasspathJar() { - return this.useClasspathJar; - } - public String getVerbosity() { return verbosity; } diff --git a/pitest-maven/src/test/java/org/pitest/maven/MojoToReportOptionsConverterTest.java b/pitest-maven/src/test/java/org/pitest/maven/MojoToReportOptionsConverterTest.java index e9bd66925..5e20c7ac9 100644 --- a/pitest-maven/src/test/java/org/pitest/maven/MojoToReportOptionsConverterTest.java +++ b/pitest-maven/src/test/java/org/pitest/maven/MojoToReportOptionsConverterTest.java @@ -416,14 +416,11 @@ public void testParsesCustomProperties() { assertEquals("bar", actual.getFreeFormProperties().get("bar")); } - public void testDoesNotUseClasspathJarByDefault() { - final ReportOptions actual = parseConfig(""); - assertFalse(actual.useClasspathJar()); - } - - public void testParsesUseClasspathJar() { - final ReportOptions actual = parseConfig("true"); - assertTrue(actual.useClasspathJar()); + + public void testLegacyClasspathJarParamDoesNotCauseError() { + assertThatCode(() -> parseConfig("true")) + .doesNotThrowAnyException(); + } public void testFailsIfObsoleteMaxMutationsParameterUsed() {