View Javadoc
1   package org.apache.maven.wrapper;
2   
3   /*
4    * Licensed to the Apache Software Foundation (ASF) under one
5    * or more contributor license agreements.  See the NOTICE file
6    * distributed with this work for additional information
7    * regarding copyright ownership.  The ASF licenses this file
8    * to you under the Apache License, Version 2.0 (the
9    * "License"); you may not use this file except in compliance
10   * with the License.  You may obtain a copy of the License at
11   *
12   *  http://www.apache.org/licenses/LICENSE-2.0
13   *
14   * Unless required by applicable law or agreed to in writing,
15   * software distributed under the License is distributed on an
16   * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
17   * KIND, either express or implied.  See the License for the
18   * specific language governing permissions and limitations
19   * under the License.
20   */
21  
22  import java.io.IOException;
23  import java.io.InputStream;
24  import java.net.URI;
25  import java.net.URISyntaxException;
26  import java.nio.file.Files;
27  import java.nio.file.Path;
28  import java.nio.file.Paths;
29  import java.util.Locale;
30  import java.util.Properties;
31  
32  /**
33   * Wrapper executor, running {@link Installer} to get a Maven distribution ready, followed by
34   * {@link BootstrapMainStarter} to launch the Maven bootstrap.
35   *
36   * @author Hans Dockter
37   */
38  public class WrapperExecutor
39  {
40      public static final String DISTRIBUTION_URL_PROPERTY = "distributionUrl";
41  
42      public static final String DISTRIBUTION_BASE_PROPERTY = "distributionBase";
43  
44      public static final String ZIP_STORE_BASE_PROPERTY = "zipStoreBase";
45  
46      public static final String DISTRIBUTION_PATH_PROPERTY = "distributionPath";
47  
48      public static final String ZIP_STORE_PATH_PROPERTY = "zipStorePath";
49  
50      private final Properties properties;
51  
52      private final Path propertiesFile;
53  
54      private final WrapperConfiguration config = new WrapperConfiguration();
55  
56      public static WrapperExecutor forProjectDirectory( Path projectDir )
57      {
58          return new WrapperExecutor( projectDir.resolve( "maven/wrapper/maven-wrapper.properties" ), new Properties() );
59      }
60  
61      public static WrapperExecutor forWrapperPropertiesFile( Path propertiesFile )
62      {
63          if ( Files.notExists( propertiesFile ) )
64          {
65              throw new RuntimeException( String.format( Locale.ROOT, "Wrapper properties file '%s' does not exist.",
66                                                         propertiesFile ) );
67          }
68          return new WrapperExecutor( propertiesFile, new Properties() );
69      }
70  
71      WrapperExecutor( Path propertiesFile, Properties properties )
72      {
73          this.properties = properties;
74          this.propertiesFile = propertiesFile;
75          if ( Files.exists( propertiesFile ) )
76          {
77              try
78              {
79                  loadProperties( propertiesFile, properties );
80                  config.setDistribution( prepareDistributionUri() );
81                  config.setDistributionBase( getProperty( DISTRIBUTION_BASE_PROPERTY, config.getDistributionBase() ) );
82                  config.setDistributionPath( Paths.get( getProperty( DISTRIBUTION_PATH_PROPERTY,
83                                                                      config.getDistributionPath().toString() ) ) );
84                  config.setZipBase( getProperty( ZIP_STORE_BASE_PROPERTY, config.getZipBase() ) );
85                  config.setZipPath( Paths.get( getProperty( ZIP_STORE_PATH_PROPERTY,
86                                                             config.getZipPath().toString() ) ) );
87              }
88              catch ( Exception e )
89              {
90                  throw new RuntimeException( String.format( Locale.ROOT, "Could not load wrapper properties from '%s'.",
91                                                             propertiesFile ),
92                                              e );
93              }
94          }
95      }
96  
97      private URI prepareDistributionUri()
98          throws URISyntaxException
99      {
100         URI source = readDistroUrl();
101         if ( source.getScheme() == null )
102         {
103             // no scheme means someone passed a relative url. In our context only file relative urls make sense.
104             return propertiesFile.getParent().resolve( source.getSchemeSpecificPart() ).toUri();
105         }
106         else
107         {
108             return source;
109         }
110     }
111 
112     private URI readDistroUrl()
113         throws URISyntaxException
114     {
115         return new URI( getProperty( DISTRIBUTION_URL_PROPERTY ) );
116     }
117 
118     private static void loadProperties( Path propertiesFile, Properties properties )
119         throws IOException
120     {
121         try ( InputStream inStream = Files.newInputStream( propertiesFile ) )
122         {
123             properties.load( inStream );
124         }
125     }
126 
127     /**
128      * Returns the Maven distribution which this wrapper will use. Returns null if no wrapper meta-data was found in the
129      * specified project directory.
130      *
131      * @return the Maven distribution which this wrapper will use
132      */
133     public URI getDistribution()
134     {
135         return config.getDistribution();
136     }
137 
138     /**
139      * Returns the configuration for this wrapper.
140      *
141      * @return the configuration for this wrapper
142      */
143     public WrapperConfiguration getConfiguration()
144     {
145         return config;
146     }
147 
148     public void execute( String[] args, Installer install, BootstrapMainStarter bootstrapMainStarter )
149         throws Exception
150     {
151         Path mavenHome = install.createDist( config );
152         bootstrapMainStarter.start( args, mavenHome );
153     }
154 
155     private String getProperty( String propertyName )
156     {
157         return getProperty( propertyName, null );
158     }
159 
160     private String getProperty( String propertyName, String defaultValue )
161     {
162         String value = properties.getProperty( propertyName, defaultValue );
163         if ( value == null )
164         {
165             reportMissingProperty( propertyName );
166         }
167         return value;
168     }
169 
170     private void reportMissingProperty( String propertyName )
171     {
172         throw new RuntimeException( String.format( Locale.ROOT,
173                                                    "No value with key '%s' specified in wrapper properties file '%s'.",
174                                                    propertyName, propertiesFile ) );
175     }
176 }