1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20 package org.apache.maven.archetype.ui;
21
22 import org.apache.maven.archetype.ArchetypeGenerationRequest;
23 import org.apache.maven.archetype.common.ArchetypeArtifactManager;
24 import org.apache.maven.archetype.common.ArchetypeConfiguration;
25 import org.apache.maven.archetype.common.ArchetypeDefinition;
26 import org.apache.maven.archetype.common.ArchetypeRegistryManager;
27 import org.apache.maven.archetype.common.Constants;
28 import org.apache.maven.archetype.exception.ArchetypeGenerationConfigurationFailure;
29 import org.apache.maven.archetype.exception.ArchetypeNotConfigured;
30 import org.apache.maven.archetype.exception.ArchetypeNotDefined;
31 import org.apache.maven.archetype.exception.UnknownArchetype;
32 import org.apache.maven.archetype.old.OldArchetype;
33 import org.apache.maven.artifact.repository.ArtifactRepository;
34
35 import org.codehaus.plexus.components.interactivity.PrompterException;
36 import org.codehaus.plexus.logging.AbstractLogEnabled;
37
38 import java.io.IOException;
39
40 import java.util.ArrayList;
41 import java.util.Collections;
42 import java.util.Comparator;
43 import java.util.Iterator;
44 import java.util.List;
45 import java.util.Properties;
46 import org.codehaus.plexus.util.StringUtils;
47
48
49
50
51
52 public class DefaultArchetypeGenerationConfigurator
53 extends AbstractLogEnabled
54 implements ArchetypeGenerationConfigurator
55 {
56
57
58
59 OldArchetype oldArchetype;
60
61
62
63
64 private ArchetypeArtifactManager archetypeArtifactManager;
65
66
67
68
69 private ArchetypeFactory archetypeFactory;
70
71
72
73
74 private ArchetypeGenerationQueryer archetypeGenerationQueryer;
75
76
77
78
79 private ArchetypeRegistryManager archetypeRegistryManager;
80
81 public void setArchetypeArtifactManager( ArchetypeArtifactManager archetypeArtifactManager )
82 {
83 this.archetypeArtifactManager = archetypeArtifactManager;
84 }
85
86 public void configureArchetype( ArchetypeGenerationRequest request, Boolean interactiveMode,
87 Properties executionProperties )
88 throws ArchetypeNotDefined, UnknownArchetype, ArchetypeNotConfigured, IOException, PrompterException,
89 ArchetypeGenerationConfigurationFailure
90 {
91 ArtifactRepository localRepository = request.getLocalRepository();
92
93 ArtifactRepository archetypeRepository = null;
94
95 List repositories = new ArrayList();
96
97 Properties properties = new Properties( executionProperties );
98
99 ArchetypeDefinition ad = new ArchetypeDefinition();
100
101 ad.setGroupId( request.getArchetypeGroupId() );
102
103 ad.setArtifactId( request.getArchetypeArtifactId() );
104
105 ad.setVersion( request.getArchetypeVersion() );
106
107 if ( !ad.isDefined() )
108 {
109 if ( !interactiveMode.booleanValue() )
110 {
111 throw new ArchetypeNotDefined( "No archetype was chosen" );
112 }
113 else
114 {
115 throw new ArchetypeNotDefined( "The archetype is not defined" );
116 }
117 }
118 if ( request.getArchetypeRepository() != null )
119 {
120 archetypeRepository =
121 archetypeRegistryManager.createRepository( request.getArchetypeRepository(),
122 ad.getArtifactId() + "-repo" );
123 repositories.add( archetypeRepository );
124 }
125 if ( request.getRemoteArtifactRepositories() != null )
126 {
127 repositories.addAll( request.getRemoteArtifactRepositories() );
128 }
129
130 if ( !archetypeArtifactManager.exists( ad.getGroupId(), ad.getArtifactId(), ad.getVersion(),
131 archetypeRepository, localRepository, repositories ) )
132 {
133 throw new UnknownArchetype( "The desired archetype does not exist (" + ad.getGroupId() + ":"
134 + ad.getArtifactId() + ":" + ad.getVersion() + ")" );
135 }
136
137 request.setArchetypeVersion( ad.getVersion() );
138
139 ArchetypeConfiguration archetypeConfiguration;
140
141 if ( archetypeArtifactManager.isFileSetArchetype( ad.getGroupId(), ad.getArtifactId(), ad.getVersion(),
142 archetypeRepository, localRepository, repositories ) )
143 {
144 org.apache.maven.archetype.metadata.ArchetypeDescriptor archetypeDescriptor =
145 archetypeArtifactManager.getFileSetArchetypeDescriptor( ad.getGroupId(), ad.getArtifactId(),
146 ad.getVersion(), archetypeRepository,
147 localRepository, repositories );
148
149 archetypeConfiguration = archetypeFactory.createArchetypeConfiguration( archetypeDescriptor, properties );
150 }
151 else if ( archetypeArtifactManager.isOldArchetype( ad.getGroupId(), ad.getArtifactId(), ad.getVersion(),
152 archetypeRepository, localRepository, repositories ) )
153 {
154 org.apache.maven.archetype.old.descriptor.ArchetypeDescriptor archetypeDescriptor =
155 archetypeArtifactManager.getOldArchetypeDescriptor( ad.getGroupId(), ad.getArtifactId(),
156 ad.getVersion(), archetypeRepository,
157 localRepository, repositories );
158
159 archetypeConfiguration = archetypeFactory.createArchetypeConfiguration( archetypeDescriptor, properties );
160 }
161 else
162 {
163 throw new ArchetypeGenerationConfigurationFailure( "The defined artifact is not an archetype" );
164 }
165
166 if ( interactiveMode.booleanValue() )
167 {
168 boolean confirmed = false;
169
170 while ( !confirmed )
171 {
172 List propertiesRequired = archetypeConfiguration.getRequiredProperties();
173 getLogger().debug( "Required properties before content sort: " + propertiesRequired );
174 Collections.sort( propertiesRequired, new RequiredPropertyComparator( archetypeConfiguration ) );
175 getLogger().debug( "Required properties after content sort: " + propertiesRequired );
176
177 if ( !archetypeConfiguration.isConfigured() )
178 {
179 for ( Iterator requiredProperties = propertiesRequired.iterator(); requiredProperties.hasNext(); )
180 {
181 String requiredProperty = (String) requiredProperties.next();
182
183 if ( !archetypeConfiguration.isConfigured( requiredProperty ) )
184 {
185 if ( "package".equals( requiredProperty ) )
186 {
187
188
189
190 String packageDefault = archetypeConfiguration.getDefaultValue( requiredProperty );
191 packageDefault =
192 ( null == packageDefault || "".equals( packageDefault ) ) ? archetypeConfiguration.getProperty( "groupId" )
193 : archetypeConfiguration.getDefaultValue( requiredProperty );
194
195 archetypeConfiguration.setProperty(
196 requiredProperty,
197 archetypeGenerationQueryer.getPropertyValue(
198 requiredProperty,
199 getTransitiveDefaultValue(
200 packageDefault,
201 archetypeConfiguration ) ) );
202 }
203 else
204 {
205 archetypeConfiguration.setProperty(
206 requiredProperty,
207 archetypeGenerationQueryer.getPropertyValue(
208 requiredProperty,
209 getTransitiveDefaultValue(
210 archetypeConfiguration.getDefaultValue( requiredProperty ),
211 archetypeConfiguration ) ) );
212 }
213 }
214 else
215 {
216 getLogger().info(
217 "Using property: " + requiredProperty + " = "
218 + archetypeConfiguration.getProperty( requiredProperty ) );
219 }
220 }
221 }
222 else
223 {
224
225 for ( Iterator requiredProperties = propertiesRequired.iterator(); requiredProperties.hasNext(); )
226 {
227 String requiredProperty = (String) requiredProperties.next();
228
229 getLogger().info(
230 "Using property: " + requiredProperty + " = "
231 + archetypeConfiguration.getProperty( requiredProperty ) );
232 }
233 }
234
235 if ( !archetypeConfiguration.isConfigured() )
236 {
237 getLogger().warn( "Archetype is not fully configured" );
238 }
239 else if ( !archetypeGenerationQueryer.confirmConfiguration( archetypeConfiguration ) )
240 {
241 getLogger().debug( "Archetype generation configuration not confirmed" );
242 archetypeConfiguration.reset();
243 restoreCommandLineProperties( archetypeConfiguration, executionProperties );
244 }
245 else
246 {
247 getLogger().debug( "Archetype generation configuration confirmed" );
248
249 confirmed = true;
250 }
251 }
252 }
253 else
254 {
255 if ( !archetypeConfiguration.isConfigured() )
256 {
257 for ( Iterator requiredProperties = archetypeConfiguration.getRequiredProperties().iterator();
258 requiredProperties.hasNext(); )
259 {
260 String requiredProperty = (String) requiredProperties.next();
261
262 if ( !archetypeConfiguration.isConfigured( requiredProperty )
263 && ( archetypeConfiguration.getDefaultValue( requiredProperty ) != null ) )
264 {
265 archetypeConfiguration.setProperty( requiredProperty,
266 archetypeConfiguration.getDefaultValue( requiredProperty ) );
267 }
268 }
269
270
271 if ( !archetypeConfiguration.isConfigured() )
272 {
273 StringBuffer exceptionMessage = new StringBuffer();
274 exceptionMessage.append( "Archetype " );
275 exceptionMessage.append( request.getArchetypeGroupId() );
276 exceptionMessage.append( ":" );
277 exceptionMessage.append( request.getArchetypeArtifactId() );
278 exceptionMessage.append( ":" );
279 exceptionMessage.append( request.getArchetypeVersion() );
280 exceptionMessage.append( " is not configured" );
281
282 List missingProperties = new ArrayList( 0 );
283 for ( Iterator requiredProperties = archetypeConfiguration.getRequiredProperties().iterator();
284 requiredProperties.hasNext(); )
285 {
286 String requiredProperty = (String) requiredProperties.next();
287
288 if ( !archetypeConfiguration.isConfigured( requiredProperty ) )
289 {
290 exceptionMessage.append( "\n\tProperty " );
291 exceptionMessage.append( requiredProperty );
292 missingProperties.add( requiredProperty );
293 exceptionMessage.append( " is missing." );
294 getLogger().warn(
295 "Property " + requiredProperty + " is missing. Add -D" + requiredProperty
296 + "=someValue" );
297 }
298 }
299
300 throw new ArchetypeNotConfigured( exceptionMessage.toString(), missingProperties );
301 }
302 }
303 }
304
305 request.setGroupId( archetypeConfiguration.getProperty( Constants.GROUP_ID ) );
306
307 request.setArtifactId( archetypeConfiguration.getProperty( Constants.ARTIFACT_ID ) );
308
309 request.setVersion( archetypeConfiguration.getProperty( Constants.VERSION ) );
310
311 request.setPackage( archetypeConfiguration.getProperty( Constants.PACKAGE ) );
312
313 properties = archetypeConfiguration.getProperties();
314
315 request.setProperties( properties );
316 }
317
318 private String getTransitiveDefaultValue( String defaultValue, ArchetypeConfiguration archetypeConfiguration )
319 {
320 String result = defaultValue;
321 if ( null == result )
322 {
323 return null;
324 }
325 for ( Iterator requiredProperties = archetypeConfiguration.getRequiredProperties().iterator();
326 requiredProperties.hasNext(); )
327 {
328 String property = (String) requiredProperties.next();
329
330 if ( result.indexOf( "${" + property + "}" ) >= 0 )
331 {
332 result = StringUtils.replace( result, "${" + property + "}",
333 archetypeConfiguration.getProperty(property) );
334 }
335 }
336 return result;
337 }
338
339 private void restoreCommandLineProperties( ArchetypeConfiguration archetypeConfiguration,
340 Properties executionProperties )
341 {
342 getLogger().debug( "Restoring command line properties" );
343
344 for ( Iterator properties = archetypeConfiguration.getRequiredProperties().iterator(); properties.hasNext(); )
345 {
346 String property = (String) properties.next();
347
348 if ( executionProperties.containsKey( property ) )
349 {
350 archetypeConfiguration.setProperty( property, executionProperties.getProperty( property ) );
351 getLogger().debug( "Restored " + property + "=" + archetypeConfiguration.getProperty( property ) );
352 }
353 }
354 }
355
356 public static class RequiredPropertyComparator implements Comparator
357 {
358 private final ArchetypeConfiguration archetypeConfiguration;
359
360 public RequiredPropertyComparator( ArchetypeConfiguration archetypeConfiguration )
361 {
362 this.archetypeConfiguration = archetypeConfiguration;
363 }
364
365 public int compare( Object left, Object right )
366 {
367 if ( !( left instanceof String ) || !( right instanceof String ) )
368 {
369 return 0;
370 }
371 else
372 {
373 String leftDefault = archetypeConfiguration.getDefaultValue( (String) left );
374 String rightDefault = archetypeConfiguration.getDefaultValue( (String) right );
375 if ( null == leftDefault || null == rightDefault )
376 {
377 return comparePropertyName( (String) left, (String) right );
378 }
379 else if ( leftDefault.indexOf( "${" + right + "}" ) >= 0 )
380 {
381 return 1;
382 }
383 else if ( rightDefault.indexOf( "${" + left + "}" ) >= 0 )
384 {
385 return -1;
386 }
387 else
388 {
389 return comparePropertyName( (String) left, (String) right );
390 }
391 }
392 }
393
394 private int comparePropertyName( String left, String right )
395 {
396 if ( "groupId".equals( left ) )
397 {
398 return -1;
399 }
400 if ( "groupId".equals( right ) )
401 {
402 return 1;
403 }
404 if ( "artifactId".equals( left ) )
405 {
406 return -1;
407 }
408 if ( "artifactId".equals( right ) )
409 {
410 return 1;
411 }
412 if ( "version".equals( left ) )
413 {
414 return -1;
415 }
416 if ( "version".equals( right ) )
417 {
418 return 1;
419 }
420 if ( "package".equals( left ) )
421 {
422 return -1;
423 }
424 if ( "package".equals( right ) )
425 {
426 return 1;
427 }
428 return left.compareTo( right );
429 }
430 }
431 }