View Javadoc
1   package org.apache.maven.project;
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.File;
23  import java.io.IOException;
24  import java.util.AbstractMap;
25  import java.util.ArrayList;
26  import java.util.Arrays;
27  import java.util.Collection;
28  import java.util.Collections;
29  import java.util.HashMap;
30  import java.util.HashSet;
31  import java.util.LinkedHashSet;
32  import java.util.List;
33  import java.util.Map;
34  import java.util.Set;
35  
36  import org.apache.maven.RepositoryUtils;
37  import org.apache.maven.artifact.Artifact;
38  import org.apache.maven.artifact.InvalidArtifactRTException;
39  import org.apache.maven.artifact.InvalidRepositoryException;
40  import org.apache.maven.artifact.repository.ArtifactRepository;
41  import org.apache.maven.artifact.repository.LegacyLocalRepositoryManager;
42  import org.apache.maven.bridge.MavenRepositorySystem;
43  import org.apache.maven.model.Build;
44  import org.apache.maven.model.Dependency;
45  import org.apache.maven.model.DependencyManagement;
46  import org.apache.maven.model.DeploymentRepository;
47  import org.apache.maven.model.Extension;
48  import org.apache.maven.model.Model;
49  import org.apache.maven.model.Plugin;
50  import org.apache.maven.model.Profile;
51  import org.apache.maven.model.ReportPlugin;
52  import org.apache.maven.model.building.DefaultModelBuildingRequest;
53  import org.apache.maven.model.building.DefaultModelProblem;
54  import org.apache.maven.model.building.FileModelSource;
55  import org.apache.maven.model.building.ModelBuilder;
56  import org.apache.maven.model.building.ModelBuildingException;
57  import org.apache.maven.model.building.ModelBuildingRequest;
58  import org.apache.maven.model.building.ModelBuildingResult;
59  import org.apache.maven.model.building.ModelProblem;
60  import org.apache.maven.model.building.ModelProcessor;
61  import org.apache.maven.model.building.ModelSource;
62  import org.apache.maven.model.building.StringModelSource;
63  import org.apache.maven.model.resolution.ModelResolver;
64  import org.apache.maven.repository.internal.ArtifactDescriptorUtils;
65  import org.codehaus.plexus.component.annotations.Component;
66  import org.codehaus.plexus.component.annotations.Requirement;
67  import org.codehaus.plexus.logging.Logger;
68  import org.codehaus.plexus.util.Os;
69  import org.codehaus.plexus.util.StringUtils;
70  import org.eclipse.aether.RepositorySystemSession;
71  import org.eclipse.aether.RequestTrace;
72  import org.eclipse.aether.impl.RemoteRepositoryManager;
73  import org.eclipse.aether.repository.LocalRepositoryManager;
74  import org.eclipse.aether.repository.RemoteRepository;
75  import org.eclipse.aether.repository.WorkspaceRepository;
76  import org.eclipse.aether.resolution.ArtifactRequest;
77  import org.eclipse.aether.resolution.ArtifactResult;
78  
79  /**
80   * DefaultProjectBuilder
81   */
82  @Component( role = ProjectBuilder.class )
83  public class DefaultProjectBuilder
84      implements ProjectBuilder
85  {
86  
87      public static final String DISABLE_GLOBAL_MODEL_CACHE_SYSTEM_PROPERTY =
88              "maven.defaultProjectBuilder.disableGlobalModelCache";
89  
90      @Requirement
91      private Logger logger;
92  
93      @Requirement
94      private ModelBuilder modelBuilder;
95  
96      @Requirement
97      private ModelProcessor modelProcessor;
98  
99      @Requirement
100     private ProjectBuildingHelper projectBuildingHelper;
101 
102     @Requirement
103     private MavenRepositorySystem repositorySystem;
104 
105     @Requirement
106     private org.eclipse.aether.RepositorySystem repoSystem;
107 
108     @Requirement
109     private RemoteRepositoryManager repositoryManager;
110 
111     @Requirement
112     private ProjectDependenciesResolver dependencyResolver;
113 
114     private final ReactorModelCache modelCache = new ReactorModelCache();
115 
116     // ----------------------------------------------------------------------
117     // MavenProjectBuilder Implementation
118     // ----------------------------------------------------------------------
119 
120     @Override
121     public ProjectBuildingResult build( File pomFile, ProjectBuildingRequest request )
122         throws ProjectBuildingException
123     {
124         return build( pomFile, new FileModelSource( pomFile ),
125                 new InternalConfig( request, null, useGlobalModelCache() ? getModelCache() : null ) );
126     }
127 
128     private boolean useGlobalModelCache()
129     {
130         return !Boolean.getBoolean( DISABLE_GLOBAL_MODEL_CACHE_SYSTEM_PROPERTY );
131     }
132 
133     @Override
134     public ProjectBuildingResult build( ModelSource modelSource, ProjectBuildingRequest request )
135         throws ProjectBuildingException
136     {
137         return build( null, modelSource,
138                  new InternalConfig( request, null, useGlobalModelCache() ? getModelCache() : null ) );
139     }
140 
141     private ProjectBuildingResult build( File pomFile, ModelSource modelSource, InternalConfig config )
142         throws ProjectBuildingException
143     {
144         ClassLoader oldContextClassLoader = Thread.currentThread().getContextClassLoader();
145 
146         try
147         {
148             ProjectBuildingRequest projectBuildingRequest = config.request;
149 
150             MavenProject project = projectBuildingRequest.getProject();
151 
152             List<ModelProblem> modelProblems = null;
153             Throwable error = null;
154 
155             if ( project == null )
156             {
157                 ModelBuildingRequest request = getModelBuildingRequest( config );
158 
159                 project = new MavenProject();
160                 project.setFile( pomFile );
161 
162                 DefaultModelBuildingListener listener =
163                     new DefaultModelBuildingListener( project, projectBuildingHelper, projectBuildingRequest );
164                 request.setModelBuildingListener( listener );
165 
166                 request.setPomFile( pomFile );
167                 request.setModelSource( modelSource );
168                 request.setLocationTracking( true );
169 
170                 ModelBuildingResult result;
171                 try
172                 {
173                     result = modelBuilder.build( request );
174                 }
175                 catch ( ModelBuildingException e )
176                 {
177                     result = e.getResult();
178                     if ( result == null || result.getEffectiveModel() == null )
179                     {
180                         throw new ProjectBuildingException( e.getModelId(), e.getMessage(), pomFile, e );
181                     }
182                     // validation error, continue project building and delay failing to help IDEs
183                     error = e;
184                 }
185 
186                 modelProblems = result.getProblems();
187 
188                 initProject( project, Collections.<String, MavenProject>emptyMap(), true,
189                              result, new HashMap<File, Boolean>(), projectBuildingRequest );
190             }
191             else if ( projectBuildingRequest.isResolveDependencies() )
192             {
193                 projectBuildingHelper.selectProjectRealm( project );
194             }
195 
196             DependencyResolutionResult resolutionResult = null;
197 
198             if ( projectBuildingRequest.isResolveDependencies() )
199             {
200                 resolutionResult = resolveDependencies( project, config.session );
201             }
202 
203             ProjectBuildingResult result = new DefaultProjectBuildingResult( project, modelProblems, resolutionResult );
204 
205             if ( error != null )
206             {
207                 ProjectBuildingException e = new ProjectBuildingException( Arrays.asList( result ) );
208                 e.initCause( error );
209                 throw e;
210             }
211 
212             return result;
213         }
214         finally
215         {
216             Thread.currentThread().setContextClassLoader( oldContextClassLoader );
217         }
218     }
219 
220     private DependencyResolutionResult resolveDependencies( MavenProject project, RepositorySystemSession session )
221     {
222         DependencyResolutionResult resolutionResult;
223 
224         try
225         {
226             DefaultDependencyResolutionRequest resolution = new DefaultDependencyResolutionRequest( project, session );
227             resolutionResult = dependencyResolver.resolve( resolution );
228         }
229         catch ( DependencyResolutionException e )
230         {
231             resolutionResult = e.getResult();
232         }
233 
234         Set<Artifact> artifacts = new LinkedHashSet<>();
235         if ( resolutionResult.getDependencyGraph() != null )
236         {
237             RepositoryUtils.toArtifacts( artifacts, resolutionResult.getDependencyGraph().getChildren(),
238                                          Collections.singletonList( project.getArtifact().getId() ), null );
239 
240             // Maven 2.x quirk: an artifact always points at the local repo, regardless whether resolved or not
241             LocalRepositoryManager lrm = session.getLocalRepositoryManager();
242             for ( Artifact artifact : artifacts )
243             {
244                 if ( !artifact.isResolved() )
245                 {
246                     String path = lrm.getPathForLocalArtifact( RepositoryUtils.toArtifact( artifact ) );
247                     artifact.setFile( new File( lrm.getRepository().getBasedir(), path ) );
248                 }
249             }
250         }
251         project.setResolvedArtifacts( artifacts );
252         project.setArtifacts( artifacts );
253 
254         return resolutionResult;
255     }
256 
257     private List<String> getProfileIds( List<Profile> profiles )
258     {
259         List<String> ids = new ArrayList<>( profiles.size() );
260 
261         for ( Profile profile : profiles )
262         {
263             ids.add( profile.getId() );
264         }
265 
266         return ids;
267     }
268 
269     private ModelBuildingRequest getModelBuildingRequest( InternalConfig config )
270     {
271         ProjectBuildingRequest configuration = config.request;
272 
273         ModelBuildingRequest request = new DefaultModelBuildingRequest();
274 
275         RequestTrace trace = RequestTrace.newChild( null, configuration ).newChild( request );
276 
277         ModelResolver resolver =
278             new ProjectModelResolver( config.session, trace, repoSystem, repositoryManager, config.repositories,
279                                       configuration.getRepositoryMerging(), config.modelPool );
280 
281         request.setValidationLevel( configuration.getValidationLevel() );
282         request.setProcessPlugins( configuration.isProcessPlugins() );
283         request.setProfiles( configuration.getProfiles() );
284         request.setActiveProfileIds( configuration.getActiveProfileIds() );
285         request.setInactiveProfileIds( configuration.getInactiveProfileIds() );
286         request.setSystemProperties( configuration.getSystemProperties() );
287         request.setUserProperties( configuration.getUserProperties() );
288         request.setBuildStartTime( configuration.getBuildStartTime() );
289         request.setModelResolver( resolver );
290         request.setModelCache( config.modelCache );
291 
292         return request;
293     }
294 
295     @Override
296     public ProjectBuildingResult build( Artifact artifact, ProjectBuildingRequest request )
297         throws ProjectBuildingException
298     {
299         return build( artifact, false, request );
300     }
301 
302     @Override
303     public ProjectBuildingResult build( Artifact artifact, boolean allowStubModel, ProjectBuildingRequest request )
304         throws ProjectBuildingException
305     {
306         org.eclipse.aether.artifact.Artifact pomArtifact = RepositoryUtils.toArtifact( artifact );
307         pomArtifact = ArtifactDescriptorUtils.toPomArtifact( pomArtifact );
308 
309         InternalConfig config = new InternalConfig( request, null, useGlobalModelCache() ? getModelCache() : null );
310 
311         boolean localProject;
312 
313         try
314         {
315             ArtifactRequest pomRequest = new ArtifactRequest();
316             pomRequest.setArtifact( pomArtifact );
317             pomRequest.setRepositories( config.repositories );
318             ArtifactResult pomResult = repoSystem.resolveArtifact( config.session, pomRequest );
319 
320             pomArtifact = pomResult.getArtifact();
321             localProject = pomResult.getRepository() instanceof WorkspaceRepository;
322         }
323         catch ( org.eclipse.aether.resolution.ArtifactResolutionException e )
324         {
325             if ( e.getResults().get( 0 ).isMissing() && allowStubModel )
326             {
327                 return build( null, createStubModelSource( artifact ), config );
328             }
329             throw new ProjectBuildingException( artifact.getId(),
330                                                 "Error resolving project artifact: " + e.getMessage(), e );
331         }
332 
333         File pomFile = pomArtifact.getFile();
334 
335         if ( "pom".equals( artifact.getType() ) )
336         {
337             artifact.selectVersion( pomArtifact.getVersion() );
338             artifact.setFile( pomFile );
339             artifact.setResolved( true );
340         }
341 
342         return build( localProject ? pomFile : null, new FileModelSource( pomFile ), config );
343     }
344 
345     private ModelSource createStubModelSource( Artifact artifact )
346     {
347         StringBuilder buffer = new StringBuilder( 1024 );
348 
349         buffer.append( "<?xml version='1.0'?>" );
350         buffer.append( "<project>" );
351         buffer.append( "<modelVersion>4.0.0</modelVersion>" );
352         buffer.append( "<groupId>" ).append( artifact.getGroupId() ).append( "</groupId>" );
353         buffer.append( "<artifactId>" ).append( artifact.getArtifactId() ).append( "</artifactId>" );
354         buffer.append( "<version>" ).append( artifact.getBaseVersion() ).append( "</version>" );
355         buffer.append( "<packaging>" ).append( artifact.getType() ).append( "</packaging>" );
356         buffer.append( "</project>" );
357 
358         return new StringModelSource( buffer, artifact.getId() );
359     }
360 
361     @Override
362     public List<ProjectBuildingResult> build( List<File> pomFiles, boolean recursive, ProjectBuildingRequest request )
363         throws ProjectBuildingException
364     {
365         List<ProjectBuildingResult> results = new ArrayList<>();
366 
367         List<InterimResult> interimResults = new ArrayList<>();
368 
369         ReactorModelPool modelPool = new ReactorModelPool();
370 
371         InternalConfig config = new InternalConfig( request, modelPool,
372                 useGlobalModelCache() ? getModelCache() : new ReactorModelCache() );
373 
374         Map<String, MavenProject> projectIndex = new HashMap<>( 256 );
375 
376         boolean noErrors =
377             build( results, interimResults, projectIndex, pomFiles, new LinkedHashSet<File>(), true, recursive,
378                    config );
379 
380         populateReactorModelPool( modelPool, interimResults );
381 
382         ClassLoader oldContextClassLoader = Thread.currentThread().getContextClassLoader();
383 
384         try
385         {
386             noErrors =
387                 build( results, new ArrayList<MavenProject>(), projectIndex, interimResults, request,
388                        new HashMap<File, Boolean>(), config.session ) && noErrors;
389         }
390         finally
391         {
392             Thread.currentThread().setContextClassLoader( oldContextClassLoader );
393         }
394 
395         if ( !noErrors )
396         {
397             throw new ProjectBuildingException( results );
398         }
399 
400         return results;
401     }
402 
403     @SuppressWarnings( "checkstyle:parameternumber" )
404     private boolean build( List<ProjectBuildingResult> results, List<InterimResult> interimResults,
405                            Map<String, MavenProject> projectIndex, List<File> pomFiles, Set<File> aggregatorFiles,
406                            boolean isRoot, boolean recursive, InternalConfig config )
407     {
408         boolean noErrors = true;
409 
410         for ( File pomFile : pomFiles )
411         {
412             aggregatorFiles.add( pomFile );
413 
414             if ( !build( results, interimResults, projectIndex, pomFile, aggregatorFiles, isRoot, recursive, config ) )
415             {
416                 noErrors = false;
417             }
418 
419             aggregatorFiles.remove( pomFile );
420         }
421 
422         return noErrors;
423     }
424 
425     @SuppressWarnings( "checkstyle:parameternumber" )
426     private boolean build( List<ProjectBuildingResult> results, List<InterimResult> interimResults,
427                            Map<String, MavenProject> projectIndex, File pomFile, Set<File> aggregatorFiles,
428                            boolean isRoot, boolean recursive, InternalConfig config )
429     {
430         boolean noErrors = true;
431 
432         ModelBuildingRequest request = getModelBuildingRequest( config );
433 
434         MavenProject project = new MavenProject();
435         project.setFile( pomFile );
436 
437         request.setPomFile( pomFile );
438         request.setTwoPhaseBuilding( true );
439         request.setLocationTracking( true );
440 
441         DefaultModelBuildingListener listener =
442             new DefaultModelBuildingListener( project, projectBuildingHelper, config.request );
443         request.setModelBuildingListener( listener );
444 
445         ModelBuildingResult result;
446         try
447         {
448             result = modelBuilder.build( request );
449         }
450         catch ( ModelBuildingException e )
451         {
452             result = e.getResult();
453             if ( result == null || result.getEffectiveModel() == null )
454             {
455                  results.add( new DefaultProjectBuildingResult( e.getModelId(), pomFile, e.getProblems() ) );
456 
457                  return false;
458             }
459             // validation error, continue project building and delay failing to help IDEs
460             // result.getProblems().addAll(e.getProblems()) ?
461             noErrors = false;
462         }
463 
464         Model model = result.getEffectiveModel();
465         try
466         {
467             // first pass: build without building parent.
468             initProject( project, projectIndex, false, result, new HashMap<File, Boolean>( 0 ), config.request );
469         }
470         catch ( InvalidArtifactRTException iarte )
471         {
472             result.getProblems().add( new DefaultModelProblem( null, ModelProblem.Severity.ERROR, null, model, -1, -1,
473                   iarte ) );
474         }
475 
476         projectIndex.put( result.getModelIds().get( 0 ), project );
477 
478         InterimResult interimResult = new InterimResult( pomFile, request, result, listener, isRoot );
479         interimResults.add( interimResult );
480 
481         if ( recursive && !model.getModules().isEmpty() )
482         {
483             File basedir = pomFile.getParentFile();
484 
485             List<File> moduleFiles = new ArrayList<>();
486 
487             for ( String module : model.getModules() )
488             {
489                 if ( StringUtils.isEmpty( module ) )
490                 {
491                     continue;
492                 }
493 
494                 module = module.replace( '\\', File.separatorChar ).replace( '/', File.separatorChar );
495 
496                 File moduleFile = new File( basedir, module );
497 
498                 if ( moduleFile.isDirectory() )
499                 {
500                     moduleFile = modelProcessor.locatePom( moduleFile );
501                 }
502 
503                 if ( !moduleFile.isFile() )
504                 {
505                     ModelProblem problem =
506                         new DefaultModelProblem( "Child module " + moduleFile + " of " + pomFile
507                             + " does not exist", ModelProblem.Severity.ERROR, ModelProblem.Version.BASE, model, -1,
508                                                  -1, null );
509                     result.getProblems().add( problem );
510 
511                     noErrors = false;
512 
513                     continue;
514                 }
515 
516                 if ( Os.isFamily( Os.FAMILY_WINDOWS ) )
517                 {
518                     // we don't canonicalize on unix to avoid interfering with symlinks
519                     try
520                     {
521                         moduleFile = moduleFile.getCanonicalFile();
522                     }
523                     catch ( IOException e )
524                     {
525                         moduleFile = moduleFile.getAbsoluteFile();
526                     }
527                 }
528                 else
529                 {
530                     moduleFile = new File( moduleFile.toURI().normalize() );
531                 }
532 
533                 if ( aggregatorFiles.contains( moduleFile ) )
534                 {
535                     StringBuilder buffer = new StringBuilder( 256 );
536                     for ( File aggregatorFile : aggregatorFiles )
537                     {
538                         buffer.append( aggregatorFile ).append( " -> " );
539                     }
540                     buffer.append( moduleFile );
541 
542                     ModelProblem problem =
543                         new DefaultModelProblem( "Child module " + moduleFile + " of " + pomFile
544                             + " forms aggregation cycle " + buffer, ModelProblem.Severity.ERROR,
545                                                  ModelProblem.Version.BASE, model, -1, -1, null );
546                     result.getProblems().add( problem );
547 
548                     noErrors = false;
549 
550                     continue;
551                 }
552 
553                 moduleFiles.add( moduleFile );
554             }
555 
556             interimResult.modules = new ArrayList<>();
557 
558             if ( !build( results, interimResult.modules, projectIndex, moduleFiles, aggregatorFiles, false,
559                          recursive, config ) )
560             {
561                 noErrors = false;
562             }
563         }
564 
565         return noErrors;
566     }
567 
568     static class InterimResult
569     {
570 
571         File pomFile;
572 
573         ModelBuildingRequest request;
574 
575         ModelBuildingResult result;
576 
577         DefaultModelBuildingListener listener;
578 
579         boolean root;
580 
581         List<InterimResult> modules = Collections.emptyList();
582 
583         InterimResult( File pomFile, ModelBuildingRequest request, ModelBuildingResult result,
584                        DefaultModelBuildingListener listener, boolean root )
585         {
586             this.pomFile = pomFile;
587             this.request = request;
588             this.result = result;
589             this.listener = listener;
590             this.root = root;
591         }
592 
593     }
594 
595     private void populateReactorModelPool( ReactorModelPool reactorModelPool, List<InterimResult> interimResults )
596     {
597         for ( InterimResult interimResult : interimResults )
598         {
599             Model model = interimResult.result.getEffectiveModel();
600             reactorModelPool.put( model.getGroupId(), model.getArtifactId(), model.getVersion(), model.getPomFile() );
601 
602             populateReactorModelPool( reactorModelPool, interimResult.modules );
603         }
604     }
605 
606     private boolean build( List<ProjectBuildingResult> results, List<MavenProject> projects,
607                            Map<String, MavenProject> projectIndex, List<InterimResult> interimResults,
608                            ProjectBuildingRequest request, Map<File, Boolean> profilesXmls,
609                            RepositorySystemSession session )
610     {
611         boolean noErrors = true;
612 
613         for ( InterimResult interimResult : interimResults )
614         {
615             MavenProject project = interimResult.listener.getProject();
616             try
617             {
618                 ModelBuildingResult result = modelBuilder.build( interimResult.request, interimResult.result );
619 
620                 // 2nd pass of initialization: resolve and build parent if necessary
621                 try
622                 {
623                     initProject( project, projectIndex, true, result, profilesXmls, request );
624                 }
625                 catch ( InvalidArtifactRTException iarte )
626                 {
627                     result.getProblems().add( new DefaultModelProblem( null, ModelProblem.Severity.ERROR, null,
628                             result.getEffectiveModel(), -1, -1, iarte ) );
629                 }
630 
631                 List<MavenProject> modules = new ArrayList<>();
632                 noErrors =
633                     build( results, modules, projectIndex, interimResult.modules, request, profilesXmls, session )
634                     && noErrors;
635 
636                 projects.addAll( modules );
637                 projects.add( project );
638 
639                 project.setExecutionRoot( interimResult.root );
640                 project.setCollectedProjects( modules );
641                 DependencyResolutionResult resolutionResult = null;
642                 if ( request.isResolveDependencies() )
643                 {
644                     resolutionResult = resolveDependencies( project, session );
645                 }
646 
647                 results.add( new DefaultProjectBuildingResult( project, result.getProblems(), resolutionResult ) );
648             }
649             catch ( ModelBuildingException e )
650             {
651                 DefaultProjectBuildingResult result = null;
652                 if ( project == null )
653                 {
654                     result = new DefaultProjectBuildingResult( e.getModelId(), interimResult.pomFile, e.getProblems() );
655                 }
656                 else
657                 {
658                     result = new DefaultProjectBuildingResult( project, e.getProblems(), null );
659                 }
660                 results.add( result );
661 
662                 noErrors = false;
663             }
664         }
665 
666         return noErrors;
667     }
668 
669     @SuppressWarnings( "checkstyle:methodlength" )
670     private void initProject( MavenProject project, Map<String, MavenProject> projects,
671                               boolean buildParentIfNotExisting, ModelBuildingResult result,
672                               Map<File, Boolean> profilesXmls, ProjectBuildingRequest projectBuildingRequest )
673     {
674         Model model = result.getEffectiveModel();
675 
676         project.setModel( model );
677         project.setOriginalModel( result.getRawModel() );
678         project.setFile( model.getPomFile() );
679 
680         initParent( project, projects, buildParentIfNotExisting, result, projectBuildingRequest );
681 
682         Artifact projectArtifact =
683             repositorySystem.createArtifact( project.getGroupId(), project.getArtifactId(), project.getVersion(), null,
684                                              project.getPackaging() );
685         project.setArtifact( projectArtifact );
686 
687         if ( project.getFile() != null && buildParentIfNotExisting ) // only set those on 2nd phase, ignore on 1st pass
688         {
689             Build build = project.getBuild();
690             project.addScriptSourceRoot( build.getScriptSourceDirectory() );
691             project.addCompileSourceRoot( build.getSourceDirectory() );
692             project.addTestCompileSourceRoot( build.getTestSourceDirectory() );
693         }
694 
695         List<Profile> activeProfiles = new ArrayList<>();
696         activeProfiles.addAll( result.getActivePomProfiles( result.getModelIds().get( 0 ) ) );
697         activeProfiles.addAll( result.getActiveExternalProfiles() );
698         project.setActiveProfiles( activeProfiles );
699 
700         project.setInjectedProfileIds( "external", getProfileIds( result.getActiveExternalProfiles() ) );
701         for ( String modelId : result.getModelIds() )
702         {
703             project.setInjectedProfileIds( modelId, getProfileIds( result.getActivePomProfiles( modelId ) ) );
704         }
705 
706         String modelId = findProfilesXml( result, profilesXmls );
707         if ( modelId != null )
708         {
709             ModelProblem problem =
710                 new DefaultModelProblem( "Detected profiles.xml alongside " + modelId
711                     + ", this file is no longer supported and was ignored" + ", please use the settings.xml instead",
712                                          ModelProblem.Severity.WARNING, ModelProblem.Version.V30, model, -1, -1, null );
713             result.getProblems().add( problem );
714         }
715 
716         //
717         // All the parts that were taken out of MavenProject for Maven 4.0.0
718         //
719 
720         project.setProjectBuildingRequest( projectBuildingRequest );
721 
722         // pluginArtifacts
723         Set<Artifact> pluginArtifacts = new HashSet<>();
724         for ( Plugin plugin : project.getBuildPlugins() )
725         {
726             Artifact artifact = repositorySystem.createPluginArtifact( plugin );
727 
728             if ( artifact != null )
729             {
730                 pluginArtifacts.add( artifact );
731             }
732         }
733         project.setPluginArtifacts( pluginArtifacts );
734 
735         // reportArtifacts
736         Set<Artifact> reportArtifacts = new HashSet<>();
737         for ( ReportPlugin report : project.getReportPlugins() )
738         {
739             Plugin pp = new Plugin();
740             pp.setGroupId( report.getGroupId() );
741             pp.setArtifactId( report.getArtifactId() );
742             pp.setVersion( report.getVersion() );
743 
744             Artifact artifact = repositorySystem.createPluginArtifact( pp );
745 
746             if ( artifact != null )
747             {
748                 reportArtifacts.add( artifact );
749             }
750         }
751         project.setReportArtifacts( reportArtifacts );
752 
753         // extensionArtifacts
754         Set<Artifact> extensionArtifacts = new HashSet<>();
755         List<Extension> extensions = project.getBuildExtensions();
756         if ( extensions != null )
757         {
758             for ( Extension ext : extensions )
759             {
760                 String version;
761                 if ( StringUtils.isEmpty( ext.getVersion() ) )
762                 {
763                     version = "RELEASE";
764                 }
765                 else
766                 {
767                     version = ext.getVersion();
768                 }
769 
770                 Artifact artifact =
771                     repositorySystem.createArtifact( ext.getGroupId(), ext.getArtifactId(), version, null, "jar" );
772 
773                 if ( artifact != null )
774                 {
775                     extensionArtifacts.add( artifact );
776                 }
777             }
778         }
779         project.setExtensionArtifacts( extensionArtifacts );
780 
781         // managedVersionMap
782         Map<String, Artifact> map = null;
783         if ( repositorySystem != null )
784         {
785             final DependencyManagement dependencyManagement = project.getDependencyManagement();
786             if ( ( dependencyManagement != null ) && ( ( dependencyManagement.getDependencies() ) != null )
787                 && ( dependencyManagement.getDependencies().size() > 0 ) )
788             {
789                 map = new AbstractMap<String, Artifact>()
790                 {
791                     HashMap<String, Artifact> delegate;
792 
793                     @Override
794                     public Set<Entry<String, Artifact>> entrySet()
795                     {
796                         return Collections.unmodifiableSet( compute().entrySet() );
797                     }
798 
799                     @Override
800                     public Set<String> keySet()
801                     {
802                         return Collections.unmodifiableSet( compute().keySet() );
803                     }
804 
805                     @Override
806                     public Collection<Artifact> values()
807                     {
808                         return Collections.unmodifiableCollection( compute().values() );
809                     }
810 
811                     @Override
812                     public boolean containsValue( Object value )
813                     {
814                         return compute().containsValue( value );
815                     }
816 
817                     @Override
818                     public boolean containsKey( Object key )
819                     {
820                         return compute().containsKey( key );
821                     }
822 
823                     @Override
824                     public Artifact get( Object key )
825                     {
826                         return compute().get( key );
827                     }
828 
829                     HashMap<String, Artifact> compute()
830                     {
831                         if ( delegate == null )
832                         {
833                             delegate = new HashMap<>();
834                             for ( Dependency d : dependencyManagement.getDependencies() )
835                             {
836                                 Artifact artifact = repositorySystem.createDependencyArtifact( d );
837 
838                                 if ( artifact != null )
839                                 {
840                                     delegate.put( d.getManagementKey(), artifact );
841                                 }
842                             }
843                         }
844 
845                         return delegate;
846                     }
847                 };
848             }
849             else
850             {
851                 map = Collections.emptyMap();
852             }
853         }
854         project.setManagedVersionMap( map );
855 
856         // release artifact repository
857         if ( project.getDistributionManagement() != null
858                         && project.getDistributionManagement().getRepository() != null )
859         {
860             try
861             {
862                 DeploymentRepository r = project.getDistributionManagement().getRepository();
863                 if ( !StringUtils.isEmpty( r.getId() ) && !StringUtils.isEmpty( r.getUrl() ) )
864                 {
865                     ArtifactRepository repo = repositorySystem.buildArtifactRepository( r );
866                     repositorySystem.injectProxy( projectBuildingRequest.getRepositorySession(),
867                                                   Arrays.asList( repo ) );
868                     repositorySystem.injectAuthentication( projectBuildingRequest.getRepositorySession(),
869                                                            Arrays.asList( repo ) );
870                     project.setReleaseArtifactRepository( repo );
871                 }
872             }
873             catch ( InvalidRepositoryException e )
874             {
875                 throw new IllegalStateException( "Failed to create release distribution repository for "
876                     + project.getId(), e );
877             }
878         }
879 
880         // snapshot artifact repository
881         if ( project.getDistributionManagement() != null
882             && project.getDistributionManagement().getSnapshotRepository() != null )
883         {
884             try
885             {
886                 DeploymentRepository r = project.getDistributionManagement().getSnapshotRepository();
887                 if ( !StringUtils.isEmpty( r.getId() ) && !StringUtils.isEmpty( r.getUrl() ) )
888                 {
889                     ArtifactRepository repo = repositorySystem.buildArtifactRepository( r );
890                     repositorySystem.injectProxy( projectBuildingRequest.getRepositorySession(),
891                                                   Arrays.asList( repo ) );
892                     repositorySystem.injectAuthentication( projectBuildingRequest.getRepositorySession(),
893                                                            Arrays.asList( repo ) );
894                     project.setSnapshotArtifactRepository( repo );
895                 }
896             }
897             catch ( InvalidRepositoryException e )
898             {
899                 throw new IllegalStateException( "Failed to create snapshot distribution repository for "
900                     + project.getId(), e );
901             }
902         }
903     }
904 
905     private void initParent( MavenProject project, Map<String, MavenProject> projects, boolean buildParentIfNotExisting,
906                              ModelBuildingResult result, ProjectBuildingRequest projectBuildingRequest )
907     {
908         Model parentModel = result.getModelIds().size() > 1 && !result.getModelIds().get( 1 ).isEmpty()
909                                 ? result.getRawModel( result.getModelIds().get( 1 ) )
910                                 : null;
911 
912         if ( parentModel != null )
913         {
914             final String parentGroupId = inheritedGroupId( result, 1 );
915             final String parentVersion = inheritedVersion( result, 1 );
916 
917             project.setParentArtifact( repositorySystem.createProjectArtifact( parentGroupId,
918                                                                                parentModel.getArtifactId(),
919                                                                                parentVersion ) );
920 
921             // org.apache.maven.its.mng4834:parent:0.1
922             String parentModelId = result.getModelIds().get( 1 );
923             File parentPomFile = result.getRawModel( parentModelId ).getPomFile();
924             MavenProject parent = projects.get( parentModelId );
925             if ( parent == null && buildParentIfNotExisting )
926             {
927                 //
928                 // At this point the DefaultModelBuildingListener has fired and it populates the
929                 // remote repositories with those found in the pom.xml, along with the existing externally
930                 // defined repositories.
931                 //
932                 projectBuildingRequest.setRemoteRepositories( project.getRemoteArtifactRepositories() );
933                 if ( parentPomFile != null )
934                 {
935                     project.setParentFile( parentPomFile );
936                     try
937                     {
938                         parent = build( parentPomFile, projectBuildingRequest ).getProject();
939                     }
940                     catch ( ProjectBuildingException e )
941                     {
942                         // MNG-4488 where let invalid parents slide on by
943                         if ( logger.isDebugEnabled() )
944                         {
945                             // Message below is checked for in the MNG-2199 core IT.
946                             logger.warn( "Failed to build parent project for " + project.getId(), e );
947                         }
948                         else
949                         {
950                             // Message below is checked for in the MNG-2199 core IT.
951                             logger.warn( "Failed to build parent project for " + project.getId() );
952                         }
953                     }
954                 }
955                 else
956                 {
957                     Artifact parentArtifact = project.getParentArtifact();
958                     try
959                     {
960                         parent = build( parentArtifact, projectBuildingRequest ).getProject();
961                     }
962                     catch ( ProjectBuildingException e )
963                     {
964                         // MNG-4488 where let invalid parents slide on by
965                         if ( logger.isDebugEnabled() )
966                         {
967                             // Message below is checked for in the MNG-2199 core IT.
968                             logger.warn( "Failed to build parent project for " + project.getId(), e );
969                         }
970                         else
971                         {
972                             // Message below is checked for in the MNG-2199 core IT.
973                             logger.warn( "Failed to build parent project for " + project.getId() );
974                         }
975                     }
976                 }
977             }
978             project.setParent( parent );
979             if ( project.getParentFile() == null && parent != null )
980             {
981                 project.setParentFile( parent.getFile() );
982             }
983         }
984     }
985 
986     private static String inheritedGroupId( final ModelBuildingResult result, final int modelIndex )
987     {
988         String groupId = null;
989         final String modelId = result.getModelIds().get( modelIndex );
990 
991         if ( !modelId.isEmpty() )
992         {
993             final Model model = result.getRawModel( modelId );
994             groupId = model.getGroupId() != null
995                           ? model.getGroupId()
996                           : inheritedGroupId( result, modelIndex + 1 );
997 
998         }
999 
1000         return groupId;
1001     }
1002 
1003     private static String inheritedVersion( final ModelBuildingResult result, final int modelIndex )
1004     {
1005         String version = null;
1006         final String modelId = result.getModelIds().get( modelIndex );
1007 
1008         if ( !modelId.isEmpty() )
1009         {
1010             final Model model = result.getRawModel( modelId );
1011             version = model.getVersion() != null
1012                           ? model.getVersion()
1013                           : inheritedVersion( result, modelIndex + 1 );
1014 
1015         }
1016 
1017         return version;
1018     }
1019 
1020     private String findProfilesXml( ModelBuildingResult result, Map<File, Boolean> profilesXmls )
1021     {
1022         for ( String modelId : result.getModelIds() )
1023         {
1024             Model model = result.getRawModel( modelId );
1025 
1026             File basedir = model.getProjectDirectory();
1027             if ( basedir == null )
1028             {
1029                 break;
1030             }
1031 
1032             Boolean profilesXml = profilesXmls.get( basedir );
1033             if ( profilesXml == null )
1034             {
1035                 profilesXml = new File( basedir, "profiles.xml" ).exists();
1036                 profilesXmls.put( basedir, profilesXml );
1037             }
1038             if ( profilesXml )
1039             {
1040                 return modelId;
1041             }
1042         }
1043 
1044         return null;
1045     }
1046 
1047     /**
1048      * InternalConfig
1049      */
1050     class InternalConfig
1051     {
1052 
1053         private final ProjectBuildingRequest request;
1054 
1055         private final RepositorySystemSession session;
1056 
1057         private final List<RemoteRepository> repositories;
1058 
1059         private final ReactorModelPool modelPool;
1060 
1061         private final ReactorModelCache modelCache;
1062 
1063         InternalConfig( ProjectBuildingRequest request, ReactorModelPool modelPool, ReactorModelCache modelCache )
1064         {
1065             this.request = request;
1066             this.modelPool = modelPool;
1067             this.modelCache = modelCache;
1068             session =
1069                 LegacyLocalRepositoryManager.overlay( request.getLocalRepository(), request.getRepositorySession(),
1070                                                       repoSystem );
1071             repositories = RepositoryUtils.toRepos( request.getRemoteRepositories() );
1072         }
1073 
1074     }
1075 
1076     private ReactorModelCache getModelCache()
1077     {
1078         return this.modelCache;
1079     }
1080 
1081 }