diff --git a/src/main/java/org/codehaus/mojo/aspectj/AbstractAjcCompiler.java b/src/main/java/org/codehaus/mojo/aspectj/AbstractAjcCompiler.java index c228ebe..6fd242d 100644 --- a/src/main/java/org/codehaus/mojo/aspectj/AbstractAjcCompiler.java +++ b/src/main/java/org/codehaus/mojo/aspectj/AbstractAjcCompiler.java @@ -425,6 +425,18 @@ public abstract class AbstractAjcCompiler extends AbstractAjcMojo { @Parameter protected List additionalCompilerArgs = new ArrayList<>(); + /** + * Activates compiler preview features (e.g. sealed classes in Java 16) when used with a suitable JDK version + * + * @since 1.13 + */ + // TODO: + // Create tickets for at least Eclipse IDE and IntelliJ IDEA to recognise this switch and import it as a compiler + // and possibly runtime setting. As for AJDT, maybe we have to implement it ourselves, but actually I found no + // references to the Maven module there, so I guess the import is implemented somewhere else. + @Parameter( defaultValue = "false" ) + protected boolean enablePreview; + /** * Holder for ajc compiler options */ @@ -631,6 +643,10 @@ protected void assembleArguments() addModulesArgument("-aspectpath", ajcOptions, aspectLibraries, getAdditionalAspectPaths(), "an aspect library"); + // Add Java 9+ modules needed for compilation + addModulesArgument("--module-path", ajcOptions, javaModules, null, + "Java module"); + // Add xmlConfigured option and argument if (null != xmlConfigured) { ajcOptions.add("-xmlConfigured"); @@ -890,13 +906,23 @@ public void setShowWeaveInfo(boolean showWeaveInfo) { } public void setTarget(String target) { - ajcOptions.add("-target"); - ajcOptions.add(target); + if (AjcHelper.isValidComplianceLevel(target)) { + ajcOptions.add("-target"); + ajcOptions.add(target); + } } public void setSource(String source) { - ajcOptions.add("-source"); - ajcOptions.add(source); + if (AjcHelper.isValidComplianceLevel(source)) { + ajcOptions.add("-source"); + ajcOptions.add(source); + } + } + + public void setEnablePreview(boolean enablePreview) { + if (enablePreview) { + ajcOptions.add("--enable-preview"); + } } public void setVerbose(boolean verbose) { diff --git a/src/main/java/org/codehaus/mojo/aspectj/AbstractAjcMojo.java b/src/main/java/org/codehaus/mojo/aspectj/AbstractAjcMojo.java index 0ada583..f9ec48a 100644 --- a/src/main/java/org/codehaus/mojo/aspectj/AbstractAjcMojo.java +++ b/src/main/java/org/codehaus/mojo/aspectj/AbstractAjcMojo.java @@ -69,6 +69,15 @@ public abstract class AbstractAjcMojo extends AbstractMojo @Parameter protected String[] weaveDirectories; + /** + * Java 9+ modules to build the module path from. + * Corresponds to ajc --module-path option. + * + * @since 1.13 + */ + @Parameter + protected Module[] javaModules; + /** * Weave binary aspects from the jars. * The aspects should have been output by the same version of the compiler. diff --git a/src/main/java/org/codehaus/mojo/aspectj/AjcHelper.java b/src/main/java/org/codehaus/mojo/aspectj/AjcHelper.java index d99f375..475f112 100644 --- a/src/main/java/org/codehaus/mojo/aspectj/AjcHelper.java +++ b/src/main/java/org/codehaus/mojo/aspectj/AjcHelper.java @@ -92,7 +92,7 @@ public static String createClassPath( MavenProject project, List plugi String cp = ""; Set classPathElements = Collections.synchronizedSet( // LinkedHashSet preserves order by insertion for iteration - new LinkedHashSet<>() + new LinkedHashSet<>() ); Set dependencyArtifacts = project.getDependencyArtifacts(); // Set.addAll only adds if absent, so we want to add the project artifacts first @@ -141,7 +141,7 @@ public static String createClassPath( MavenProject project, List plugi public static Set getBuildFilesForAjdtFile( String ajdtBuildDefFile, File basedir ) throws MojoExecutionException { - Set result = new LinkedHashSet(); + Set result = new LinkedHashSet<>(); Properties ajdtBuildProperties = new Properties(); try @@ -176,7 +176,7 @@ public static Set getBuildFilesForAjdtFile( String ajdtBuildDefFile, Fil public static Set getBuildFilesForSourceDirs( List sourceDirs, String[] includes, String[] excludes ) throws MojoExecutionException { - Set result = new LinkedHashSet(); + Set result = new LinkedHashSet<>(); for ( String sourceDir : sourceDirs ) { @@ -225,7 +225,7 @@ public static Set getWeaveSourceFiles( String[] weaveDirs ) } catch ( IOException e ) { - throw new MojoExecutionException( "IO Error resolving weavedirs", e ); + throw new MojoExecutionException( "IO Error resolving weave directories", e ); } } } @@ -270,7 +270,7 @@ public static void writeBuildConfigToFile( List arguments, String fileNa public static List readBuildConfigFile( String fileName, File outputDir ) throws IOException { - List arguments = new ArrayList(); + List arguments = new ArrayList<>(); File argFile = new File( outputDir, fileName ); if ( FileUtils.fileExists( argFile.getAbsolutePath() ) ) { diff --git a/src/test/java/org/codehaus/mojo/aspectj/AbstractAjcCompilerTest.java b/src/test/java/org/codehaus/mojo/aspectj/AbstractAjcCompilerTest.java index add597b..7d03af6 100644 --- a/src/test/java/org/codehaus/mojo/aspectj/AbstractAjcCompilerTest.java +++ b/src/test/java/org/codehaus/mojo/aspectj/AbstractAjcCompilerTest.java @@ -315,7 +315,86 @@ public void testGetAjc_libraryArtifacts() assertTrue( weavePath.indexOf( mod1Artifact ) != -1 ); assertTrue( weavePath.indexOf( mod2Artifact ) != -1 ); } - + + /** + * Verifies that if not stated no --module-path or -p argument should + * be found in the ajc arguments + * {@link AbstractAjcCompiler#execute()} + * + * @throws Exception on test error + */ + public void testGetAjcArguments_noModulePath() + throws Exception + { + ajcCompMojo.assembleArguments(); + List args = ajcCompMojo.ajcOptions; + assertFalse( args.contains( "--module-path" ) ); + assertFalse( args.contains( "-p" ) ); + } + + /** + * Tests that the compiler fails as it should if told to weave a module artifact not listed in the project + * dependencies. + */ + public void testGetAjcArguments_moduleArtifactsNotProjectDependency() + { + Module module1 = new Module(); + String mod1Group = "dill.group"; + module1.setGroupId( mod1Group ); + String mod1Artifact = "dall.artifact"; + module1.setArtifactId( mod1Artifact ); + try + { + ajcCompMojo.javaModules = new Module[1]; + ajcCompMojo.javaModules[0] = module1; + ajcCompMojo.assembleArguments(); + fail( "Should fail quite miserably" ); + } + catch ( MojoExecutionException e ) + { + // good thing + } + } + + /** + * Tests that Java 9+ module path works as expected if listed modules also exist as dependencies + * + * @throws MojoExecutionException if the mojo fails to execute + */ + public void testGetAjc_moduleArtifacts() throws MojoExecutionException + { + ajcCompMojo.javaModules = new Module[2]; + Module module1 = new Module(); + String mod1Group = "dill.group"; + module1.setGroupId( mod1Group ); + String mod1Artifact = "dall.artifact"; + module1.setArtifactId( mod1Artifact ); + ajcCompMojo.javaModules[0] = module1; + Module module2 = new Module(); + String mod2Group = "foooup"; + module2.setGroupId( mod2Group ); + String mod2Artifact = "bartifact"; + module2.setArtifactId( mod2Artifact ); + ajcCompMojo.javaModules[1] = module2; + // Modify project to include depencies + Set artifacts = new HashSet(); + artifacts.add( new MockArtifact( mod1Group, mod1Artifact ) ); + artifacts.add( new MockArtifact( mod2Group, mod2Artifact ) ); + ajcCompMojo.project.setArtifacts( artifacts ); + ajcCompMojo.assembleArguments(); + List args = ajcCompMojo.ajcOptions; + assertTrue( args.contains( "--module-path" ) ); + Iterator it = args.iterator(); + while ( !it.next().equals( "--module-path" ) ) + { + // don't do nothing + } + String modulePath = (String) it.next(); + assertTrue( modulePath.indexOf( File.pathSeparator ) != -1 ); + assertTrue( modulePath.indexOf( mod1Artifact ) != -1 ); + assertTrue( modulePath.indexOf( mod2Artifact ) != -1 ); + } + // MASPECTJ-103 public void testGetAJc_EmptyClassifier() throws Exception {