View Javadoc
1   package org.apache.maven.bridge;
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.net.MalformedURLException;
24  import java.net.URL;
25  import java.util.ArrayList;
26  import java.util.Collection;
27  import java.util.Collections;
28  import java.util.HashSet;
29  import java.util.LinkedHashMap;
30  import java.util.List;
31  import java.util.Map;
32  import java.util.Set;
33  
34  import org.apache.maven.RepositoryUtils;
35  import org.apache.maven.artifact.Artifact;
36  import org.apache.maven.artifact.DefaultArtifact;
37  import org.apache.maven.artifact.InvalidRepositoryException;
38  import org.apache.maven.artifact.handler.ArtifactHandler;
39  import org.apache.maven.artifact.handler.manager.ArtifactHandlerManager;
40  import org.apache.maven.artifact.repository.ArtifactRepository;
41  import org.apache.maven.artifact.repository.ArtifactRepositoryPolicy;
42  import org.apache.maven.artifact.repository.Authentication;
43  import org.apache.maven.artifact.repository.MavenArtifactRepository;
44  import org.apache.maven.artifact.repository.layout.ArtifactRepositoryLayout;
45  import org.apache.maven.artifact.repository.layout.ArtifactRepositoryLayout2;
46  import org.apache.maven.artifact.repository.layout.DefaultRepositoryLayout;
47  import org.apache.maven.artifact.resolver.filter.ExcludesArtifactFilter;
48  import org.apache.maven.artifact.versioning.InvalidVersionSpecificationException;
49  import org.apache.maven.artifact.versioning.VersionRange;
50  import org.apache.maven.execution.MavenExecutionRequest;
51  import org.apache.maven.model.Dependency;
52  import org.apache.maven.model.Exclusion;
53  import org.apache.maven.model.Plugin;
54  import org.apache.maven.repository.Proxy;
55  import org.apache.maven.repository.RepositorySystem;
56  import org.apache.maven.settings.Mirror;
57  import org.codehaus.plexus.component.annotations.Component;
58  import org.codehaus.plexus.component.annotations.Requirement;
59  import org.codehaus.plexus.util.StringUtils;
60  import org.eclipse.aether.RepositorySystemSession;
61  import org.eclipse.aether.repository.AuthenticationContext;
62  import org.eclipse.aether.repository.AuthenticationSelector;
63  import org.eclipse.aether.repository.ProxySelector;
64  import org.eclipse.aether.repository.RemoteRepository;
65  
66  /**
67   * @author Jason van Zyl
68   */
69  @Component( role = MavenRepositorySystem.class, hint = "default" )
70  public class MavenRepositorySystem
71  {
72      @Requirement
73      private ArtifactHandlerManager artifactHandlerManager;
74  
75      @Requirement( role = ArtifactRepositoryLayout.class )
76      private Map<String, ArtifactRepositoryLayout> layouts;
77  
78      // DefaultProjectBuilder
79      public Artifact createArtifact( String groupId, String artifactId, String version, String scope, String type )
80      {
81          return createArtifactX( groupId, artifactId, version, scope, type );
82      }
83  
84      // DefaultProjectBuilder
85      public Artifact createProjectArtifact( String groupId, String artifactId, String metaVersionId )
86      {
87          return createProjectArtifactX( groupId, artifactId, metaVersionId );
88      }
89  
90      // DefaultProjectBuilder
91      public Artifact createDependencyArtifact( Dependency d )
92      {
93          if ( d.getVersion() == null )
94          {
95              return null;
96          }
97  
98          VersionRange versionRange;
99          try
100         {
101             versionRange = VersionRange.createFromVersionSpec( d.getVersion() );
102         }
103         catch ( InvalidVersionSpecificationException e )
104         {
105             return null;
106         }
107 
108         Artifact artifact =
109             createDependencyArtifactX( d.getGroupId(), d.getArtifactId(), versionRange, d.getType(),
110                                                       d.getClassifier(), d.getScope(), d.isOptional() );
111 
112         if ( Artifact.SCOPE_SYSTEM.equals( d.getScope() ) && d.getSystemPath() != null )
113         {
114             artifact.setFile( new File( d.getSystemPath() ) );
115         }
116 
117         if ( !d.getExclusions().isEmpty() )
118         {
119             List<String> exclusions = new ArrayList<>();
120 
121             for ( Exclusion exclusion : d.getExclusions() )
122             {
123                 exclusions.add( exclusion.getGroupId() + ':' + exclusion.getArtifactId() );
124             }
125 
126             artifact.setDependencyFilter( new ExcludesArtifactFilter( exclusions ) );
127         }
128 
129         return artifact;
130     }
131 
132     // DefaultProjectBuilder
133     public Artifact createExtensionArtifact( String groupId, String artifactId, String version )
134     {
135         VersionRange versionRange;
136         try
137         {
138             versionRange = VersionRange.createFromVersionSpec( version );
139         }
140         catch ( InvalidVersionSpecificationException e )
141         {
142             return null;
143         }
144 
145         return createExtensionArtifactX( groupId, artifactId, versionRange );
146     }
147 
148     // DefaultProjectBuilder
149     public Artifact createParentArtifact( String groupId, String artifactId, String version )
150     {
151         return createParentArtifactX( groupId, artifactId, version );
152     }
153 
154     // DefaultProjectBuilder
155     public Artifact createPluginArtifact( Plugin plugin )
156     {
157         VersionRange versionRange;
158         try
159         {
160             String version = plugin.getVersion();
161             if ( StringUtils.isEmpty( version ) )
162             {
163                 version = "RELEASE";
164             }
165             versionRange = VersionRange.createFromVersionSpec( version );
166         }
167         catch ( InvalidVersionSpecificationException e )
168         {
169             return null;
170         }
171 
172         return createPluginArtifactX( plugin.getGroupId(), plugin.getArtifactId(), versionRange );
173     }
174 
175     public void injectMirror( List<ArtifactRepository> repositories, List<Mirror> mirrors )
176     {
177         if ( repositories != null && mirrors != null )
178         {
179             for ( ArtifactRepository repository : repositories )
180             {
181                 Mirror mirror = getMirror( repository, mirrors );
182                 injectMirror( repository, mirror );
183             }
184         }
185     }
186 
187     private Mirror getMirror( RepositorySystemSession session, ArtifactRepository repository )
188     {
189         if ( session != null )
190         {
191             org.eclipse.aether.repository.MirrorSelector selector = session.getMirrorSelector();
192             if ( selector != null )
193             {
194                 RemoteRepository repo = selector.getMirror( RepositoryUtils.toRepo( repository ) );
195                 if ( repo != null )
196                 {
197                     Mirror mirror = new Mirror();
198                     mirror.setId( repo.getId() );
199                     mirror.setUrl( repo.getUrl() );
200                     mirror.setLayout( repo.getContentType() );
201                     return mirror;
202                 }
203             }
204         }
205         return null;
206     }
207 
208     public void injectMirror( RepositorySystemSession session, List<ArtifactRepository> repositories )
209     {
210         if ( repositories != null && session != null )
211         {
212             for ( ArtifactRepository repository : repositories )
213             {
214                 Mirror mirror = getMirror( session, repository );
215                 injectMirror( repository, mirror );
216             }
217         }
218     }
219 
220     private void injectMirror( ArtifactRepository repository, Mirror mirror )
221     {
222         if ( mirror != null )
223         {
224             ArtifactRepository original =
225                 createArtifactRepository( repository.getId(), repository.getUrl(), repository.getLayout(),
226                                           repository.getSnapshots(), repository.getReleases() );
227 
228             repository.setMirroredRepositories( Collections.singletonList( original ) );
229 
230             repository.setId( mirror.getId() );
231             repository.setUrl( mirror.getUrl() );
232 
233             if ( StringUtils.isNotEmpty( mirror.getLayout() ) )
234             {
235                 repository.setLayout( getLayout( mirror.getLayout() ) );
236             }
237         }
238     }
239 
240     private Authentication getAuthentication( RepositorySystemSession session, ArtifactRepository repository )
241     {
242         if ( session != null )
243         {
244             AuthenticationSelector selector = session.getAuthenticationSelector();
245             if ( selector != null )
246             {
247                 RemoteRepository repo = RepositoryUtils.toRepo( repository );
248                 org.eclipse.aether.repository.Authentication auth = selector.getAuthentication( repo );
249                 if ( auth != null )
250                 {
251                     repo = new RemoteRepository.Builder( repo ).setAuthentication( auth ).build();
252                     AuthenticationContext authCtx = AuthenticationContext.forRepository( session, repo );
253                     Authentication result =
254                         new Authentication( authCtx.get( AuthenticationContext.USERNAME ),
255                                             authCtx.get( AuthenticationContext.PASSWORD ) );
256                     result.setPrivateKey( authCtx.get( AuthenticationContext.PRIVATE_KEY_PATH ) );
257                     result.setPassphrase( authCtx.get( AuthenticationContext.PRIVATE_KEY_PASSPHRASE ) );
258                     authCtx.close();
259                     return result;
260                 }
261             }
262         }
263         return null;
264     }
265 
266     public void injectAuthentication( RepositorySystemSession session, List<ArtifactRepository> repositories )
267     {
268         if ( repositories != null && session != null )
269         {
270             for ( ArtifactRepository repository : repositories )
271             {
272                 repository.setAuthentication( getAuthentication( session, repository ) );
273             }
274         }
275     }
276 
277     private Proxy getProxy( RepositorySystemSession session, ArtifactRepository repository )
278     {
279         if ( session != null )
280         {
281             ProxySelector selector = session.getProxySelector();
282             if ( selector != null )
283             {
284                 RemoteRepository repo = RepositoryUtils.toRepo( repository );
285                 org.eclipse.aether.repository.Proxy proxy = selector.getProxy( repo );
286                 if ( proxy != null )
287                 {
288                     Proxy p = new Proxy();
289                     p.setHost( proxy.getHost() );
290                     p.setProtocol( proxy.getType() );
291                     p.setPort( proxy.getPort() );
292                     if ( proxy.getAuthentication() != null )
293                     {
294                         repo = new RemoteRepository.Builder( repo ).setProxy( proxy ).build();
295                         AuthenticationContext authCtx = AuthenticationContext.forProxy( session, repo );
296                         p.setUserName( authCtx.get( AuthenticationContext.USERNAME ) );
297                         p.setPassword( authCtx.get( AuthenticationContext.PASSWORD ) );
298                         p.setNtlmDomain( authCtx.get( AuthenticationContext.NTLM_DOMAIN ) );
299                         p.setNtlmHost( authCtx.get( AuthenticationContext.NTLM_WORKSTATION ) );
300                         authCtx.close();
301                     }
302                     return p;
303                 }
304             }
305         }
306         return null;
307     }
308 
309     public void injectProxy( RepositorySystemSession session, List<ArtifactRepository> repositories )
310     {
311         if ( repositories != null && session != null )
312         {
313             for ( ArtifactRepository repository : repositories )
314             {
315                 repository.setProxy( getProxy( session, repository ) );
316             }
317         }
318     }
319 
320     private ArtifactRepositoryLayout getLayout( String id )
321     {
322         ArtifactRepositoryLayout layout = layouts.get( id );
323 
324         return layout;
325     }
326 
327 
328     //
329     // Taken from LegacyRepositorySystem
330     //
331 
332     public static org.apache.maven.model.Repository fromSettingsRepository( org.apache.maven.settings.Repository
333                                                                             settingsRepository )
334     {
335         org.apache.maven.model.Repository modelRepository = new org.apache.maven.model.Repository();
336         modelRepository.setId( settingsRepository.getId() );
337         modelRepository.setLayout( settingsRepository.getLayout() );
338         modelRepository.setName( settingsRepository.getName() );
339         modelRepository.setUrl( settingsRepository.getUrl() );
340         modelRepository.setReleases( fromSettingsRepositoryPolicy( settingsRepository.getReleases() ) );
341         modelRepository.setSnapshots( fromSettingsRepositoryPolicy( settingsRepository.getSnapshots() ) );
342         return modelRepository;
343     }
344 
345     public static org.apache.maven.model.RepositoryPolicy fromSettingsRepositoryPolicy(
346                                                  org.apache.maven.settings.RepositoryPolicy settingsRepositoryPolicy )
347     {
348         org.apache.maven.model.RepositoryPolicy modelRepositoryPolicy = new org.apache.maven.model.RepositoryPolicy();
349         if ( settingsRepositoryPolicy != null )
350         {
351             modelRepositoryPolicy.setEnabled( settingsRepositoryPolicy.isEnabled() );
352             modelRepositoryPolicy.setUpdatePolicy( settingsRepositoryPolicy.getUpdatePolicy() );
353             modelRepositoryPolicy.setChecksumPolicy( settingsRepositoryPolicy.getChecksumPolicy() );
354         }
355         return modelRepositoryPolicy;
356     }
357 
358     public static ArtifactRepository buildArtifactRepository( org.apache.maven.settings.Repository repo )
359         throws InvalidRepositoryException
360     {
361         return buildArtifactRepository( fromSettingsRepository( repo ) );
362     }
363 
364     public static ArtifactRepository buildArtifactRepository( org.apache.maven.model.Repository repo )
365         throws InvalidRepositoryException
366     {
367         if ( repo != null )
368         {
369             String id = repo.getId();
370 
371             if ( StringUtils.isEmpty( id ) )
372             {
373                 throw new InvalidRepositoryException( "Repository identifier missing", "" );
374             }
375 
376             String url = repo.getUrl();
377 
378             if ( StringUtils.isEmpty( url ) )
379             {
380                 throw new InvalidRepositoryException( "URL missing for repository " + id, id );
381             }
382 
383             ArtifactRepositoryPolicy snapshots = buildArtifactRepositoryPolicy( repo.getSnapshots() );
384 
385             ArtifactRepositoryPolicy releases = buildArtifactRepositoryPolicy( repo.getReleases() );
386 
387             ArtifactRepositoryLayout layout = new DefaultRepositoryLayout();
388 
389             return createArtifactRepository( id, url, layout, snapshots, releases );
390         }
391         else
392         {
393             return null;
394         }
395     }
396 
397     public static ArtifactRepositoryPolicy buildArtifactRepositoryPolicy( org.apache.maven.model.RepositoryPolicy
398                                                                           policy )
399     {
400         boolean enabled = true;
401 
402         String updatePolicy = null;
403 
404         String checksumPolicy = null;
405 
406         if ( policy != null )
407         {
408             enabled = policy.isEnabled();
409 
410             if ( policy.getUpdatePolicy() != null )
411             {
412                 updatePolicy = policy.getUpdatePolicy();
413             }
414             if ( policy.getChecksumPolicy() != null )
415             {
416                 checksumPolicy = policy.getChecksumPolicy();
417             }
418         }
419 
420         return new ArtifactRepositoryPolicy( enabled, updatePolicy, checksumPolicy );
421     }    
422     
423     public ArtifactRepository createArtifactRepository( String id, String url, String layoutId,
424                                                         ArtifactRepositoryPolicy snapshots,
425                                                         ArtifactRepositoryPolicy releases )
426         throws Exception
427     {
428         ArtifactRepositoryLayout layout = layouts.get( layoutId );
429 
430         checkLayout( id, layoutId, layout );
431 
432         return createArtifactRepository( id, url, layout, snapshots, releases );
433     }
434 
435     private void checkLayout( String repositoryId, String layoutId, ArtifactRepositoryLayout layout )
436         throws Exception
437     {
438         if ( layout == null )
439         {
440             throw new Exception( String.format( "Cannot find ArtifactRepositoryLayout instance for: %s %s", layoutId,
441                                                 repositoryId ) );
442         }
443     }
444     
445     public static ArtifactRepository createArtifactRepository( String id, String url,
446                                                         ArtifactRepositoryLayout repositoryLayout,
447                                                         ArtifactRepositoryPolicy snapshots,
448                                                         ArtifactRepositoryPolicy releases )
449     {
450         if ( snapshots == null )
451         {
452             snapshots = new ArtifactRepositoryPolicy();
453         }
454 
455         if ( releases == null )
456         {
457             releases = new ArtifactRepositoryPolicy();
458         }
459 
460         ArtifactRepository repository;
461         if ( repositoryLayout instanceof ArtifactRepositoryLayout2 )
462         {
463             repository =
464                 ( (ArtifactRepositoryLayout2) repositoryLayout ).newMavenArtifactRepository( id, url, snapshots,
465                                                                                              releases );
466         }
467         else
468         {
469             repository = new MavenArtifactRepository( id, url, repositoryLayout, snapshots, releases );
470         }
471 
472         return repository;
473     }
474 
475     // ArtifactFactory
476     private Artifact createArtifactX( String groupId, String artifactId, String version, String scope, String type )
477     {
478         return createArtifactX( groupId, artifactId, version, scope, type, null, null );
479     }
480 
481     private Artifact createDependencyArtifactX( String groupId, String artifactId, VersionRange versionRange,
482                                                String type, String classifier, String scope, boolean optional )
483     {
484         return createArtifactX( groupId, artifactId, versionRange, type, classifier, scope, null, optional );
485     }
486 
487     private Artifact createProjectArtifactX( String groupId, String artifactId, String version )
488     {
489         return createProjectArtifactX( groupId, artifactId, version, null );
490     }
491 
492     private Artifact createParentArtifactX( String groupId, String artifactId, String version )
493     {
494         return createProjectArtifactX( groupId, artifactId, version );
495     }
496 
497     private Artifact createPluginArtifactX( String groupId, String artifactId, VersionRange versionRange )
498     {
499         return createArtifactX( groupId, artifactId, versionRange, "maven-plugin", null, Artifact.SCOPE_RUNTIME, null );
500     }
501 
502     private Artifact createProjectArtifactX( String groupId, String artifactId, String version, String scope )
503     {
504         return createArtifactX( groupId, artifactId, version, scope, "pom" );
505     }
506 
507     private Artifact createExtensionArtifactX( String groupId, String artifactId, VersionRange versionRange )
508     {
509         return createArtifactX( groupId, artifactId, versionRange, "jar", null, Artifact.SCOPE_RUNTIME, null );
510     }
511 
512     private Artifact createArtifactX( String groupId, String artifactId, String version, String scope, String type,
513                                      String classifier, String inheritedScope )
514     {
515         VersionRange versionRange = null;
516         if ( version != null )
517         {
518             versionRange = VersionRange.createFromVersion( version );
519         }
520         return createArtifactX( groupId, artifactId, versionRange, type, classifier, scope, inheritedScope );
521     }
522 
523     private Artifact createArtifactX( String groupId, String artifactId, VersionRange versionRange, String type,
524                                      String classifier, String scope, String inheritedScope )
525     {
526         return createArtifactX( groupId, artifactId, versionRange, type, classifier, scope, inheritedScope, false );
527     }
528 
529     @SuppressWarnings( "checkstyle:parameternumber" )
530     private Artifact createArtifactX( String groupId, String artifactId, VersionRange versionRange, String type,
531                                      String classifier, String scope, String inheritedScope, boolean optional )
532     {
533         String desiredScope = Artifact.SCOPE_RUNTIME;
534 
535         if ( inheritedScope == null )
536         {
537             desiredScope = scope;
538         }
539         else if ( Artifact.SCOPE_TEST.equals( scope ) || Artifact.SCOPE_PROVIDED.equals( scope ) )
540         {
541             return null;
542         }
543         else if ( Artifact.SCOPE_COMPILE.equals( scope ) && Artifact.SCOPE_COMPILE.equals( inheritedScope ) )
544         {
545             // added to retain compile artifactScope. Remove if you want compile inherited as runtime
546             desiredScope = Artifact.SCOPE_COMPILE;
547         }
548 
549         if ( Artifact.SCOPE_TEST.equals( inheritedScope ) )
550         {
551             desiredScope = Artifact.SCOPE_TEST;
552         }
553 
554         if ( Artifact.SCOPE_PROVIDED.equals( inheritedScope ) )
555         {
556             desiredScope = Artifact.SCOPE_PROVIDED;
557         }
558 
559         if ( Artifact.SCOPE_SYSTEM.equals( scope ) )
560         {
561             // system scopes come through unchanged...
562             desiredScope = Artifact.SCOPE_SYSTEM;
563         }
564 
565         ArtifactHandler handler = artifactHandlerManager.getArtifactHandler( type );
566 
567         return new DefaultArtifact( groupId, artifactId, versionRange, desiredScope, type, classifier, handler,
568                                     optional );
569     }
570     
571     //
572     // Code taken from LegacyRepositorySystem
573     //
574         
575     public ArtifactRepository createDefaultRemoteRepository( MavenExecutionRequest request )
576         throws Exception
577     {
578         return createRepository( RepositorySystem.DEFAULT_REMOTE_REPO_URL, RepositorySystem.DEFAULT_REMOTE_REPO_ID,
579                                  true, ArtifactRepositoryPolicy.UPDATE_POLICY_DAILY, false,
580                                  ArtifactRepositoryPolicy.UPDATE_POLICY_DAILY,
581                                  ArtifactRepositoryPolicy.CHECKSUM_POLICY_WARN );
582     }
583     
584     public ArtifactRepository createRepository( String url, String repositoryId, boolean releases,
585                                                  String releaseUpdates, boolean snapshots, String snapshotUpdates,
586                                                  String checksumPolicy ) throws Exception
587     {
588         ArtifactRepositoryPolicy snapshotsPolicy =
589             new ArtifactRepositoryPolicy( snapshots, snapshotUpdates, checksumPolicy );
590 
591         ArtifactRepositoryPolicy releasesPolicy =
592             new ArtifactRepositoryPolicy( releases, releaseUpdates, checksumPolicy );
593 
594         return createArtifactRepository( repositoryId, url, "default", snapshotsPolicy, releasesPolicy );
595     }
596         
597     public Set<String> getRepoIds( List<ArtifactRepository> repositories )
598     {
599         Set<String> repoIds = new HashSet<>();
600 
601         if ( repositories != null )
602         {
603             for ( ArtifactRepository repository : repositories )
604             {
605                 repoIds.add( repository.getId() );
606             }
607         }
608 
609         return repoIds;
610     }
611 
612     /**
613      * Source from org.apache.maven.repository.legacy.LegacyRepositorySystem#getEffectiveRepositories
614      *
615      * @param repositories
616      * @return
617      * @since 3.6.1
618      */
619     public List<ArtifactRepository> getEffectiveRepositories( List<ArtifactRepository> repositories )
620     {
621         if ( repositories == null )
622         {
623             return null;
624         }
625 
626         Map<String, List<ArtifactRepository>> reposByKey = new LinkedHashMap<>();
627 
628         for ( ArtifactRepository repository : repositories )
629         {
630             String key = repository.getId();
631 
632             List<ArtifactRepository> aliasedRepos = reposByKey.get( key );
633 
634             if ( aliasedRepos == null )
635             {
636                 aliasedRepos = new ArrayList<>();
637                 reposByKey.put( key, aliasedRepos );
638             }
639 
640             aliasedRepos.add( repository );
641         }
642 
643         List<ArtifactRepository> effectiveRepositories = new ArrayList<>();
644 
645         for ( List<ArtifactRepository> aliasedRepos : reposByKey.values() )
646         {
647             List<ArtifactRepository> mirroredRepos = new ArrayList<>();
648 
649             List<ArtifactRepositoryPolicy> releasePolicies =
650                     new ArrayList<>( aliasedRepos.size() );
651 
652             for ( ArtifactRepository aliasedRepo : aliasedRepos )
653             {
654                 releasePolicies.add( aliasedRepo.getReleases() );
655                 mirroredRepos.addAll( aliasedRepo.getMirroredRepositories() );
656             }
657 
658             ArtifactRepositoryPolicy releasePolicy = getEffectivePolicy( releasePolicies );
659 
660             List<ArtifactRepositoryPolicy> snapshotPolicies =
661                     new ArrayList<>( aliasedRepos.size() );
662 
663             for ( ArtifactRepository aliasedRepo : aliasedRepos )
664             {
665                 snapshotPolicies.add( aliasedRepo.getSnapshots() );
666             }
667 
668             ArtifactRepositoryPolicy snapshotPolicy = getEffectivePolicy( snapshotPolicies );
669 
670             ArtifactRepository aliasedRepo = aliasedRepos.get( 0 );
671 
672             ArtifactRepository effectiveRepository =
673                     createArtifactRepository( aliasedRepo.getId(), aliasedRepo.getUrl(), aliasedRepo.getLayout(),
674                             snapshotPolicy, releasePolicy );
675 
676             effectiveRepository.setAuthentication( aliasedRepo.getAuthentication() );
677 
678             effectiveRepository.setProxy( aliasedRepo.getProxy() );
679 
680             effectiveRepository.setMirroredRepositories( mirroredRepos );
681 
682             effectiveRepositories.add( effectiveRepository );
683         }
684 
685         return effectiveRepositories;
686     }
687 
688     private ArtifactRepositoryPolicy getEffectivePolicy( Collection<ArtifactRepositoryPolicy> policies )
689     {
690         ArtifactRepositoryPolicy effectivePolicy = null;
691 
692         for ( ArtifactRepositoryPolicy policy : policies )
693         {
694             if ( effectivePolicy == null )
695             {
696                 effectivePolicy = new ArtifactRepositoryPolicy( policy );
697             }
698             else
699             {
700                 effectivePolicy.merge( policy );
701             }
702         }
703 
704         return effectivePolicy;
705     }
706 
707     public ArtifactRepository createLocalRepository( MavenExecutionRequest request, File localRepository )
708         throws Exception
709     {
710         return createRepository( "file://" + localRepository.toURI().getRawPath(),
711                                  RepositorySystem.DEFAULT_LOCAL_REPO_ID, true,
712                                  ArtifactRepositoryPolicy.UPDATE_POLICY_ALWAYS, true,
713                                  ArtifactRepositoryPolicy.UPDATE_POLICY_ALWAYS,
714                                  ArtifactRepositoryPolicy.CHECKSUM_POLICY_IGNORE );
715     }    
716     
717     private static final String WILDCARD = "*";
718 
719     private static final String EXTERNAL_WILDCARD = "external:*";
720 
721     public static Mirror getMirror( ArtifactRepository repository, List<Mirror> mirrors )
722     {
723         String repoId = repository.getId();
724 
725         if ( repoId != null && mirrors != null )
726         {
727             for ( Mirror mirror : mirrors )
728             {
729                 if ( repoId.equals( mirror.getMirrorOf() ) && matchesLayout( repository, mirror ) )
730                 {
731                     return mirror;
732                 }
733             }
734 
735             for ( Mirror mirror : mirrors )
736             {
737                 if ( matchPattern( repository, mirror.getMirrorOf() ) && matchesLayout( repository, mirror ) )
738                 {
739                     return mirror;
740                 }
741             }
742         }
743 
744         return null;
745     }
746 
747     /**
748      * This method checks if the pattern matches the originalRepository. Valid patterns: * = everything external:* =
749      * everything not on the localhost and not file based. repo,repo1 = repo or repo1 *,!repo1 = everything except repo1
750      *
751      * @param originalRepository to compare for a match.
752      * @param pattern used for match. Currently only '*' is supported.
753      * @return true if the repository is a match to this pattern.
754      */
755     static boolean matchPattern( ArtifactRepository originalRepository, String pattern )
756     {
757         boolean result = false;
758         String originalId = originalRepository.getId();
759 
760         // simple checks first to short circuit processing below.
761         if ( WILDCARD.equals( pattern ) || pattern.equals( originalId ) )
762         {
763             result = true;
764         }
765         else
766         {
767             // process the list
768             String[] repos = pattern.split( "," );
769             for ( String repo : repos )
770             {
771                 // see if this is a negative match
772                 if ( repo.length() > 1 && repo.startsWith( "!" ) )
773                 {
774                     if ( repo.substring( 1 ).equals( originalId ) )
775                     {
776                         // explicitly exclude. Set result and stop processing.
777                         result = false;
778                         break;
779                     }
780                 }
781                 // check for exact match
782                 else if ( repo.equals( originalId ) )
783                 {
784                     result = true;
785                     break;
786                 }
787                 // check for external:*
788                 else if ( EXTERNAL_WILDCARD.equals( repo ) && isExternalRepo( originalRepository ) )
789                 {
790                     result = true;
791                     // don't stop processing in case a future segment explicitly excludes this repo
792                 }
793                 else if ( WILDCARD.equals( repo ) )
794                 {
795                     result = true;
796                     // don't stop processing in case a future segment explicitly excludes this repo
797                 }
798             }
799         }
800         return result;
801     }
802 
803     /**
804      * Checks the URL to see if this repository refers to an external repository
805      *
806      * @param originalRepository
807      * @return true if external.
808      */
809     static boolean isExternalRepo( ArtifactRepository originalRepository )
810     {
811         try
812         {
813             URL url = new URL( originalRepository.getUrl() );
814             return !( url.getHost().equals( "localhost" ) || url.getHost().equals( "127.0.0.1" )
815                             || url.getProtocol().equals( "file" ) );
816         }
817         catch ( MalformedURLException e )
818         {
819             // bad url just skip it here. It should have been validated already, but the wagon lookup will deal with it
820             return false;
821         }
822     }
823 
824     static boolean matchesLayout( ArtifactRepository repository, Mirror mirror )
825     {
826         return matchesLayout( RepositoryUtils.getLayout( repository ), mirror.getMirrorOfLayouts() );
827     }
828 
829     /**
830      * Checks whether the layouts configured for a mirror match with the layout of the repository.
831      *
832      * @param repoLayout The layout of the repository, may be {@code null}.
833      * @param mirrorLayout The layouts supported by the mirror, may be {@code null}.
834      * @return {@code true} if the layouts associated with the mirror match the layout of the original repository,
835      *         {@code false} otherwise.
836      */
837     static boolean matchesLayout( String repoLayout, String mirrorLayout )
838     {
839         boolean result = false;
840 
841         // simple checks first to short circuit processing below.
842         if ( StringUtils.isEmpty( mirrorLayout ) || WILDCARD.equals( mirrorLayout ) )
843         {
844             result = true;
845         }
846         else if ( mirrorLayout.equals( repoLayout ) )
847         {
848             result = true;
849         }
850         else
851         {
852             // process the list
853             String[] layouts = mirrorLayout.split( "," );
854             for ( String layout : layouts )
855             {
856                 // see if this is a negative match
857                 if ( layout.length() > 1 && layout.startsWith( "!" ) )
858                 {
859                     if ( layout.substring( 1 ).equals( repoLayout ) )
860                     {
861                         // explicitly exclude. Set result and stop processing.
862                         result = false;
863                         break;
864                     }
865                 }
866                 // check for exact match
867                 else if ( layout.equals( repoLayout ) )
868                 {
869                     result = true;
870                     break;
871                 }
872                 else if ( WILDCARD.equals( layout ) )
873                 {
874                     result = true;
875                     // don't stop processing in case a future segment explicitly excludes this repo
876                 }
877             }
878         }
879 
880         return result;
881     }    
882 }