View Javadoc
1   package org.apache.maven.artifact.repository;
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.util.Collections;
24  import java.util.List;
25  import java.util.Objects;
26  
27  import org.apache.maven.RepositoryUtils;
28  import org.apache.maven.artifact.metadata.ArtifactMetadata;
29  import org.apache.maven.artifact.repository.layout.ArtifactRepositoryLayout;
30  import org.apache.maven.artifact.repository.layout.DefaultRepositoryLayout;
31  import org.apache.maven.artifact.repository.metadata.RepositoryMetadataStoreException;
32  import org.apache.maven.repository.Proxy;
33  import org.eclipse.aether.DefaultRepositorySystemSession;
34  import org.eclipse.aether.RepositorySystem;
35  import org.eclipse.aether.RepositorySystemSession;
36  import org.eclipse.aether.artifact.Artifact;
37  import org.eclipse.aether.metadata.Metadata;
38  import org.eclipse.aether.repository.LocalArtifactRegistration;
39  import org.eclipse.aether.repository.LocalArtifactRequest;
40  import org.eclipse.aether.repository.LocalArtifactResult;
41  import org.eclipse.aether.repository.LocalMetadataRegistration;
42  import org.eclipse.aether.repository.LocalMetadataRequest;
43  import org.eclipse.aether.repository.LocalMetadataResult;
44  import org.eclipse.aether.repository.LocalRepository;
45  import org.eclipse.aether.repository.LocalRepositoryManager;
46  import org.eclipse.aether.repository.RemoteRepository;
47  
48  /**
49   * <strong>Warning:</strong> This is an internal utility class that is only public for technical reasons, it is not part
50   * of the public API. In particular, this class can be changed or deleted without prior notice.
51   *
52   * @author Benjamin Bentmann
53   */
54  public class LegacyLocalRepositoryManager
55      implements LocalRepositoryManager
56  {
57  
58      private final ArtifactRepository delegate;
59  
60      private final LocalRepository repo;
61  
62      private final boolean realLocalRepo;
63  
64      public static RepositorySystemSession overlay( ArtifactRepository repository, RepositorySystemSession session,
65                                                     RepositorySystem system )
66      {
67          if ( repository == null || repository.getBasedir() == null )
68          {
69              return session;
70          }
71  
72          if ( session != null )
73          {
74              LocalRepositoryManager lrm = session.getLocalRepositoryManager();
75              if ( lrm != null && lrm.getRepository().getBasedir().equals( new File( repository.getBasedir() ) ) )
76              {
77                  return session;
78              }
79          }
80          else
81          {
82              session = new DefaultRepositorySystemSession();
83          }
84  
85          final LocalRepositoryManager llrm = new LegacyLocalRepositoryManager( repository );
86  
87          return new DefaultRepositorySystemSession( session ).setLocalRepositoryManager( llrm );
88      }
89  
90      private LegacyLocalRepositoryManager( ArtifactRepository delegate )
91      {
92          this.delegate = Objects.requireNonNull( delegate, "delegate cannot be null" );
93  
94          ArtifactRepositoryLayout layout = delegate.getLayout();
95          repo =
96              new LocalRepository( new File( delegate.getBasedir() ),
97                                   ( layout != null ) ? layout.getClass().getSimpleName() : "legacy" );
98  
99          /*
100          * NOTE: "invoker:install" vs "appassembler:assemble": Both mojos use the artifact installer to put an artifact
101          * into a repository. In the first case, the result needs to be a proper local repository that one can use for
102          * local artifact resolution. In the second case, the result needs to precisely obey the path information of the
103          * repository's layout to allow pointing at artifacts within the repository. Unfortunately,
104          * DefaultRepositoryLayout does not correctly describe the layout of a local repository which unlike a remote
105          * repository never uses timestamps in the filename of a snapshot artifact. The discrepancy gets notable when a
106          * remotely resolved snapshot artifact gets passed into pathOf(). So producing a proper local artifact path
107          * using DefaultRepositoryLayout requires us to enforce usage of the artifact's base version. This
108          * transformation however contradicts the other use case of precisely obeying the repository's layout. The below
109          * flag tries to detect which use case applies to make both plugins happy.
110          */
111         realLocalRepo = ( layout instanceof DefaultRepositoryLayout ) && "local".equals( delegate.getId() );
112     }
113 
114     public LocalRepository getRepository()
115     {
116         return repo;
117     }
118 
119     public String getPathForLocalArtifact( Artifact artifact )
120     {
121         if ( realLocalRepo )
122         {
123             return delegate.pathOf( RepositoryUtils.toArtifact( artifact.setVersion( artifact.getBaseVersion() ) ) );
124         }
125         return delegate.pathOf( RepositoryUtils.toArtifact( artifact ) );
126     }
127 
128     public String getPathForRemoteArtifact( Artifact artifact, RemoteRepository repository, String context )
129     {
130         return delegate.pathOf( RepositoryUtils.toArtifact( artifact ) );
131     }
132 
133     public String getPathForLocalMetadata( Metadata metadata )
134     {
135         return delegate.pathOfLocalRepositoryMetadata( new ArtifactMetadataAdapter( metadata ), delegate );
136     }
137 
138     public String getPathForRemoteMetadata( Metadata metadata, RemoteRepository repository, String context )
139     {
140         return delegate.pathOfLocalRepositoryMetadata( new ArtifactMetadataAdapter( metadata ),
141                                                        new ArtifactRepositoryAdapter( repository ) );
142     }
143 
144     public LocalArtifactResult find( RepositorySystemSession session, LocalArtifactRequest request )
145     {
146         String path = getPathForLocalArtifact( request.getArtifact() );
147         File file = new File( getRepository().getBasedir(), path );
148 
149         LocalArtifactResult result = new LocalArtifactResult( request );
150         if ( file.isFile() )
151         {
152             result.setFile( file );
153             result.setAvailable( true );
154         }
155 
156         return result;
157     }
158 
159     public LocalMetadataResult find( RepositorySystemSession session, LocalMetadataRequest request )
160     {
161         Metadata metadata = request.getMetadata();
162 
163         String path;
164         if ( request.getRepository() == null )
165         {
166             path = getPathForLocalMetadata( metadata );
167         }
168         else
169         {
170             path = getPathForRemoteMetadata( metadata, request.getRepository(), request.getContext() );
171         }
172 
173         File file = new File( getRepository().getBasedir(), path );
174 
175         LocalMetadataResult result = new LocalMetadataResult( request );
176         if ( file.isFile() )
177         {
178             result.setFile( file );
179         }
180 
181         return result;
182     }
183 
184     public void add( RepositorySystemSession session, LocalArtifactRegistration request )
185     {
186         // noop
187     }
188 
189     public void add( RepositorySystemSession session, LocalMetadataRegistration request )
190     {
191         // noop
192     }
193 
194     static class ArtifactMetadataAdapter
195         implements ArtifactMetadata
196     {
197 
198         private final Metadata metadata;
199 
200         ArtifactMetadataAdapter( Metadata metadata )
201         {
202             this.metadata = metadata;
203         }
204 
205         public boolean storedInArtifactVersionDirectory()
206         {
207             return metadata.getVersion().length() > 0;
208         }
209 
210         public boolean storedInGroupDirectory()
211         {
212             return metadata.getArtifactId().length() <= 0;
213         }
214 
215         public String getGroupId()
216         {
217             return nullify( metadata.getGroupId() );
218         }
219 
220         public String getArtifactId()
221         {
222             return nullify( metadata.getArtifactId() );
223         }
224 
225         public String getBaseVersion()
226         {
227             return nullify( metadata.getVersion() );
228         }
229 
230         private String nullify( String str )
231         {
232             return ( str == null || str.length() <= 0 ) ? null : str;
233         }
234 
235         public Object getKey()
236         {
237             return metadata.toString();
238         }
239 
240         public String getRemoteFilename()
241         {
242             return metadata.getType();
243         }
244 
245         public String getLocalFilename( ArtifactRepository repository )
246         {
247             return insertRepositoryKey( getRemoteFilename(), repository.getKey() );
248         }
249 
250         private String insertRepositoryKey( String filename, String repositoryKey )
251         {
252             String result;
253             int idx = filename.indexOf( '.' );
254             if ( idx < 0 )
255             {
256                 result = filename + '-' + repositoryKey;
257             }
258             else
259             {
260                 result = filename.substring( 0, idx ) + '-' + repositoryKey + filename.substring( idx );
261             }
262             return result;
263         }
264 
265         public void merge( org.apache.maven.repository.legacy.metadata.ArtifactMetadata metadata )
266         {
267             // not used
268         }
269 
270         public void merge( ArtifactMetadata metadata )
271         {
272             // not used
273         }
274 
275         public void storeInLocalRepository( ArtifactRepository localRepository, ArtifactRepository remoteRepository )
276             throws RepositoryMetadataStoreException
277         {
278             // not used
279         }
280 
281         public String extendedToString()
282         {
283             return metadata.toString();
284         }
285 
286     }
287 
288     static class ArtifactRepositoryAdapter
289         implements ArtifactRepository
290     {
291 
292         private final RemoteRepository repository;
293 
294         ArtifactRepositoryAdapter( RemoteRepository repository )
295         {
296             this.repository = repository;
297         }
298 
299         public String pathOf( org.apache.maven.artifact.Artifact artifact )
300         {
301             return null;
302         }
303 
304         public String pathOfRemoteRepositoryMetadata( ArtifactMetadata artifactMetadata )
305         {
306             return null;
307         }
308 
309         public String pathOfLocalRepositoryMetadata( ArtifactMetadata metadata, ArtifactRepository repository )
310         {
311             return null;
312         }
313 
314         public String getUrl()
315         {
316             return repository.getUrl();
317         }
318 
319         public void setUrl( String url )
320         {
321         }
322 
323         public String getBasedir()
324         {
325             return null;
326         }
327 
328         public String getProtocol()
329         {
330             return repository.getProtocol();
331         }
332 
333         public String getId()
334         {
335             return repository.getId();
336         }
337 
338         public void setId( String id )
339         {
340         }
341 
342         public ArtifactRepositoryPolicy getSnapshots()
343         {
344             return null;
345         }
346 
347         public void setSnapshotUpdatePolicy( ArtifactRepositoryPolicy policy )
348         {
349         }
350 
351         public ArtifactRepositoryPolicy getReleases()
352         {
353             return null;
354         }
355 
356         public void setReleaseUpdatePolicy( ArtifactRepositoryPolicy policy )
357         {
358         }
359 
360         public ArtifactRepositoryLayout getLayout()
361         {
362             return null;
363         }
364 
365         public void setLayout( ArtifactRepositoryLayout layout )
366         {
367         }
368 
369         public String getKey()
370         {
371             return getId();
372         }
373 
374         public boolean isUniqueVersion()
375         {
376             return true;
377         }
378 
379         public boolean isBlacklisted()
380         {
381             return false;
382         }
383 
384         public void setBlacklisted( boolean blackListed )
385         {
386         }
387 
388         public org.apache.maven.artifact.Artifact find( org.apache.maven.artifact.Artifact artifact )
389         {
390             return null;
391         }
392 
393         public List<String> findVersions( org.apache.maven.artifact.Artifact artifact )
394         {
395             return Collections.emptyList();
396         }
397 
398         public boolean isProjectAware()
399         {
400             return false;
401         }
402 
403         public void setAuthentication( Authentication authentication )
404         {
405         }
406 
407         public Authentication getAuthentication()
408         {
409             return null;
410         }
411 
412         public void setProxy( Proxy proxy )
413         {
414         }
415 
416         public Proxy getProxy()
417         {
418             return null;
419         }
420 
421         public List<ArtifactRepository> getMirroredRepositories()
422         {
423             return Collections.emptyList();
424         }
425 
426         public void setMirroredRepositories( List<ArtifactRepository> mirroredRepositories )
427         {
428         }
429 
430     }
431 
432 }