From 1841a8e9e30fd35f8aa079e08a75070cece6c9d1 Mon Sep 17 00:00:00 2001 From: Slawomir Jaranowski Date: Wed, 29 Dec 2021 21:23:27 +0100 Subject: [PATCH] [MSHARED-1007] Add MavenHome and MavenExecutable options to InvocationRequest --- .../invoker/DefaultInvocationRequest.java | 42 +++++++ .../shared/invoker/InvocationRequest.java | 41 +++++++ .../invoker/MavenCommandLineBuilder.java | 106 ++++++++---------- .../invoker/MavenCommandLineBuilderTest.java | 75 +++++++++++-- 4 files changed, 197 insertions(+), 67 deletions(-) diff --git a/src/main/java/org/apache/maven/shared/invoker/DefaultInvocationRequest.java b/src/main/java/org/apache/maven/shared/invoker/DefaultInvocationRequest.java index 93be2ba..0f6d516 100644 --- a/src/main/java/org/apache/maven/shared/invoker/DefaultInvocationRequest.java +++ b/src/main/java/org/apache/maven/shared/invoker/DefaultInvocationRequest.java @@ -107,6 +107,10 @@ public class DefaultInvocationRequest private boolean quiet; + private File mavenHome; + + private File mavenExecutable; + /** *

getBaseDirectory.

* @@ -724,4 +728,42 @@ public InvocationRequest setQuiet( boolean quiet ) this.quiet = quiet; return this; } + + /** + * {@inheritDoc} + */ + @Override + public File getMavenHome() + { + return mavenHome; + } + + /** + * {@inheritDoc} + */ + @Override + public InvocationRequest setMavenHome( File mavenHome ) + { + this.mavenHome = mavenHome; + return this; + } + + /** + * {@inheritDoc} + */ + @Override + public File getMavenExecutable() + { + return mavenExecutable; + } + + /** + * {@inheritDoc} + */ + @Override + public InvocationRequest setMavenExecutable( File mavenExecutable ) + { + this.mavenExecutable = mavenExecutable; + return this; + } } diff --git a/src/main/java/org/apache/maven/shared/invoker/InvocationRequest.java b/src/main/java/org/apache/maven/shared/invoker/InvocationRequest.java index 91c98d3..fd603a2 100644 --- a/src/main/java/org/apache/maven/shared/invoker/InvocationRequest.java +++ b/src/main/java/org/apache/maven/shared/invoker/InvocationRequest.java @@ -763,4 +763,45 @@ enum CheckSumPolicy */ void setTimeoutInSeconds( int timeoutInSeconds ); + /** + * Gets the path to the base directory of the Maven installation used to invoke Maven. + * + * @return The path to the base directory of the Maven installation or null if using the default + * Maven installation. + * + * @since 3.1.1 + */ + File getMavenHome(); + + /** + * Sets the path to the base directory of the Maven installation used to invoke Maven. This parameter may be left + * unspecified to use the default Maven installation which will be discovered by evaluating the system property + * maven.home and the environment variable M2_HOME. + * + * @param mavenHome The path to the base directory of the Maven installation, may be null to use the + * default Maven installation. + * @return This invocation request + * + * @since 3.1.1 + */ + InvocationRequest setMavenHome( File mavenHome ); + + /** + * Get the customized File of the Maven executable. + * + * @return the custom Maven executable, otherwise {@code null} + * + * @since 3.1.1 + */ + File getMavenExecutable(); + + /** + * {@code mavenExecutable} can either be a file relative to ${maven.home}/bin/ or an absolute file. + * + * @param mavenExecutable the executable + * @return This invocation request + * + * @since 3.1.1 + */ + InvocationRequest setMavenExecutable( File mavenExecutable ); } diff --git a/src/main/java/org/apache/maven/shared/invoker/MavenCommandLineBuilder.java b/src/main/java/org/apache/maven/shared/invoker/MavenCommandLineBuilder.java index 205ed05..5767a4b 100644 --- a/src/main/java/org/apache/maven/shared/invoker/MavenCommandLineBuilder.java +++ b/src/main/java/org/apache/maven/shared/invoker/MavenCommandLineBuilder.java @@ -64,26 +64,22 @@ public class MavenCommandLineBuilder public Commandline build( InvocationRequest request ) throws CommandLineConfigurationException { + + setupMavenHome( request ); + checkRequiredState(); + try { - checkRequiredState(); - } - catch ( IOException e ) - { - throw new CommandLineConfigurationException( e.getMessage(), e ); - } - File mvn; - try - { - mvn = findMavenExecutable(); + setupMavenExecutable( request ); } catch ( IOException e ) { throw new CommandLineConfigurationException( e.getMessage(), e ); } + Commandline cli = new Commandline(); - cli.setExecutable( mvn.getAbsolutePath() ); + cli.setExecutable( mavenExecutable.getAbsolutePath() ); // handling for OS-level envars setShellEnvironment( request, cli ); @@ -119,28 +115,13 @@ public Commandline build( InvocationRequest request ) /** *

checkRequiredState.

- * - * @throws java.io.IOException if any. */ protected void checkRequiredState() - throws IOException { if ( logger == null ) { throw new IllegalStateException( "A logger instance is required." ); } - - if ( ( mavenHome == null ) && ( System.getProperty( "maven.home" ) == null ) ) - // can be restored with 1.5 - // && ( System.getenv( "M2_HOME" ) != null ) ) - { - if ( !getSystemEnvVars().containsKey( "M2_HOME" ) ) - { - throw new IllegalStateException( "Maven application directory was not " - + "specified, and ${maven.home} is not provided in the system " - + "properties. Specify at least one of these." ); - } - } } /** @@ -221,10 +202,8 @@ protected void setToolchainsLocation( InvocationRequest request, Commandline cli * * @param request a {@link org.apache.maven.shared.invoker.InvocationRequest} object. * @param cli a {@link org.apache.maven.shared.utils.cli.Commandline} object. - * @throws org.apache.maven.shared.invoker.CommandLineConfigurationException if any. */ protected void setShellEnvironment( InvocationRequest request, Commandline cli ) - throws CommandLineConfigurationException { if ( request.isShellEnvironmentInherited() ) { @@ -600,46 +579,61 @@ protected void setThreads( InvocationRequest request, Commandline cli ) } - /** - *

findMavenExecutable.

- * - * @return a {@link java.io.File} object. - * @throws org.apache.maven.shared.invoker.CommandLineConfigurationException if any. - * @throws java.io.IOException if any. - */ - protected File findMavenExecutable() - throws CommandLineConfigurationException, IOException + void setupMavenHome( InvocationRequest request ) { + if ( request.getMavenHome() != null ) + { + mavenHome = request.getMavenHome(); + } + if ( mavenHome == null ) { String mavenHomeProperty = System.getProperty( "maven.home" ); + if ( mavenHomeProperty == null && getSystemEnvVars().getProperty( "M2_HOME" ) != null ) + { + mavenHomeProperty = getSystemEnvVars().getProperty( "M2_HOME" ); + } + if ( mavenHomeProperty != null ) { mavenHome = new File( mavenHomeProperty ); - if ( !mavenHome.isDirectory() ) - { - File binDir = mavenHome.getParentFile(); - if ( binDir != null && "bin".equals( binDir.getName() ) ) - { - // ah, they specified the mvn - // executable instead... - mavenHome = binDir.getParentFile(); - } - else - { - throw new IllegalStateException( "${maven.home} is not specified as a directory: '" - + mavenHomeProperty + "'." ); - } - } } + } - if ( ( mavenHome == null ) && ( getSystemEnvVars().getProperty( "M2_HOME" ) != null ) ) + if ( mavenHome != null && !mavenHome.isDirectory() ) + { + File binDir = mavenHome.getParentFile(); + if ( binDir != null && "bin".equals( binDir.getName() ) ) { - mavenHome = new File( getSystemEnvVars().getProperty( "M2_HOME" ) ); + // ah, they specified the mvn + // executable instead... + mavenHome = binDir.getParentFile(); } } - logger.debug( "Using ${maven.home} of: '" + mavenHome + "'." ); + if ( mavenHome != null && !mavenHome.isDirectory() ) + { + throw new IllegalStateException( "maven home is not specified as a directory: '" + mavenHome + "'." ); + } + + logger.debug( "Using maven.home of: '" + mavenHome + "'." ); + } + + + /** + *

setupMavenExecutable.

+ * + * @param request a Invoker request + * @throws org.apache.maven.shared.invoker.CommandLineConfigurationException if any. + * @throws java.io.IOException if any. + */ + protected void setupMavenExecutable( InvocationRequest request ) + throws CommandLineConfigurationException, IOException + { + if ( request.getMavenExecutable() != null ) + { + mavenExecutable = request.getMavenExecutable(); + } if ( mavenExecutable == null || !mavenExecutable.isAbsolute() ) { @@ -680,8 +674,6 @@ else if ( Os.isFamily( "windows" ) ) throw new CommandLineConfigurationException( "Maven executable not found at: " + mavenExecutable ); } } - - return mavenExecutable; } private Properties getSystemEnvVars() diff --git a/src/test/java/org/apache/maven/shared/invoker/MavenCommandLineBuilderTest.java b/src/test/java/org/apache/maven/shared/invoker/MavenCommandLineBuilderTest.java index 32fcdc6..f7b2b0c 100644 --- a/src/test/java/org/apache/maven/shared/invoker/MavenCommandLineBuilderTest.java +++ b/src/test/java/org/apache/maven/shared/invoker/MavenCommandLineBuilderTest.java @@ -45,7 +45,7 @@ import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertTrue; import static org.junit.Assert.fail; -import static org.junit.Assume.assumeThat; +import static org.junit.Assume.assumeTrue; public class MavenCommandLineBuilderTest { @@ -228,7 +228,7 @@ private File setupTempMavenHomeIfMissing( boolean forceDummy ) } @Test - public void testShouldFailIfLoggerSetToNull() throws Exception + public void testShouldFailIfLoggerSetToNull() { mclb.setLogger( null ); @@ -259,10 +259,32 @@ public void testShouldFindDummyMavenExecutable() } mclb.setMavenHome( dummyMavenHomeBin.getParentFile() ); + mclb.setupMavenExecutable( newRequest() ); - File mavenExe = mclb.findMavenExecutable(); + assertEquals( check.getCanonicalPath(), mclb.getMavenExecutable().getCanonicalPath() ); + } + + @Test + public void testShouldFindDummyMavenExecutableWithMavenHomeFromRequest() + throws Exception + { + File dummyMavenHomeBin = temporaryFolder.newFolder( "invoker-tests", "dummy-maven-home", "bin" ); + + File check; + if ( Os.isFamily( Os.FAMILY_WINDOWS ) ) + { + check = createDummyFile( dummyMavenHomeBin, "mvn.bat" ); + } + else + { + check = createDummyFile( dummyMavenHomeBin, "mvn" ); + } - assertEquals( check.getCanonicalPath(), mavenExe.getCanonicalPath() ); + // default value should be not used + mclb.setMavenHome( new File( "not-present-1234" ) ); + mclb.build( newRequest().setMavenHome( dummyMavenHomeBin.getParentFile() ) ); + + assertEquals( check.getCanonicalPath(), mclb.getMavenExecutable().getCanonicalPath() ); } @Test @@ -869,16 +891,49 @@ public void testShouldSetEnvVar_M2_HOME() } @Test - public void testMvnCommand() + public void testMvnExecutableFromInvoker() throws Exception { - assumeThat( "Test only works when called with surefire", System.getProperty( "maven.home" ), - is( notNullValue() ) ); + assumeTrue( "Test only works when maven home can be assigned", + System.getProperty( "maven.home" ) != null || System.getenv( "M2_HOME" ) != null ); + File mavenExecutable = new File( "mvnDebug" ); + mclb.setMavenExecutable( mavenExecutable ); - File executable = mclb.findMavenExecutable(); - assertTrue( "Expected executable to exist", executable.exists() ); - assertTrue( "Expected executable to be absolute", executable.isAbsolute() ); + mclb.build( newRequest() ); + + assertTrue( "Expected executable to exist", mclb.getMavenExecutable().exists() ); + assertTrue( "Expected executable to be absolute", mclb.getMavenExecutable().isAbsolute() ); + assertTrue( "Expected mvnDebug as command mvnDebug", mclb.getMavenExecutable().getName().contains( "mvnDebug" ) ); + } + + @Test + public void testMvnExecutableFormRequest() + throws Exception + { + assumeTrue( "Test only works when maven home can be assigned", + System.getProperty( "maven.home" ) != null || System.getenv( "M2_HOME" ) != null ); + + File mavenExecutable = new File( "mvnDebug" ); + + mclb.build( newRequest().setMavenExecutable( mavenExecutable ) ); + + assertTrue( "Expected executable to exist", mclb.getMavenExecutable().exists() ); + assertTrue( "Expected executable to be absolute", mclb.getMavenExecutable().isAbsolute() ); + assertTrue( "Expected mvnDebug as command", mclb.getMavenExecutable().getName().contains( "mvnDebug" ) ); + } + + @Test + public void testDefaultMavenCommand() + throws Exception + { + assumeTrue( "Test only works when maven home can be assigned", + System.getProperty( "maven.home" ) != null || System.getenv( "M2_HOME" ) != null ); + + mclb.build( newRequest() ); + + assertTrue( "Expected executable to exist", mclb.getMavenExecutable().exists() ); + assertTrue( "Expected executable to be absolute", mclb.getMavenExecutable().isAbsolute() ); } @Test