blob: 31318b0f3821d27f6344633e297b91e814cfc56a [file] [log] [blame]
package org.apache.maven.plugins.assembly.repository;
/*
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership. The ASF licenses this file
* to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
* under the License.
*/
import java.io.File;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Collection;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Set;
import org.apache.maven.artifact.Artifact;
import org.apache.maven.artifact.resolver.filter.AndArtifactFilter;
import org.apache.maven.artifact.resolver.filter.ArtifactFilter;
import org.apache.maven.model.Dependency;
import org.apache.maven.plugins.assembly.repository.model.GroupVersionAlignment;
import org.apache.maven.plugins.assembly.repository.model.RepositoryInfo;
import org.apache.maven.project.MavenProject;
import org.apache.maven.project.ProjectBuildingRequest;
import org.apache.maven.shared.artifact.TransferUtils;
import org.apache.maven.shared.artifact.filter.PatternExcludesArtifactFilter;
import org.apache.maven.shared.artifact.filter.PatternIncludesArtifactFilter;
import org.apache.maven.shared.artifact.filter.ScopeArtifactFilter;
import org.apache.maven.shared.artifact.resolve.ArtifactResolver;
import org.apache.maven.shared.artifact.resolve.ArtifactResolverException;
import org.apache.maven.shared.artifact.resolve.ArtifactResult;
import org.apache.maven.shared.dependencies.resolve.DependencyResolver;
import org.apache.maven.shared.dependencies.resolve.DependencyResolverException;
import org.apache.maven.shared.repository.RepositoryManager;
import org.apache.maven.shared.utils.io.FileUtils;
import org.codehaus.plexus.component.annotations.Component;
import org.codehaus.plexus.component.annotations.Requirement;
import org.codehaus.plexus.logging.AbstractLogEnabled;
import org.codehaus.plexus.logging.Logger;
/**
* @author Jason van Zyl
*/
// todo will need to pop the processed project cache using reflection
@Component( role = RepositoryAssembler.class )
public class DefaultRepositoryAssembler
extends AbstractLogEnabled
implements RepositoryAssembler
{
@Requirement
protected ArtifactResolver artifactResolver;
@Requirement
private DependencyResolver dependencyResolver;
@Requirement
private RepositoryManager repositoryManager;
public void buildRemoteRepository( File repositoryDirectory, RepositoryInfo repository,
RepositoryBuilderConfigSource configSource )
throws RepositoryAssemblyException
{
MavenProject project = configSource.getProject();
ProjectBuildingRequest buildingRequest = configSource.getProjectBuildingRequest();
Iterable<ArtifactResult> result = null;
Collection<Dependency> dependencies = project.getDependencies();
if ( dependencies == null )
{
Logger logger = getLogger();
if ( logger.isDebugEnabled() )
{
logger.debug( "dependency-artifact set for project: " + project.getId()
+ " is null. Skipping repository processing." );
}
return;
}
Collection<Dependency> managedDependencies = null;
if ( project.getDependencyManagement() != null )
{
managedDependencies = project.getDependencyManagement().getDependencies();
}
// Older Aether versions use an cache which can't be cleared. So can't delete repoDir and use it again.
// Instead create a temporary repository, delete it at end (should be in a finally-block)
File tempRepo = new File( repositoryDirectory.getParentFile(), repositoryDirectory.getName() + "_tmp" );
buildingRequest = repositoryManager.setLocalRepositoryBasedir( buildingRequest, tempRepo );
try
{
result = dependencyResolver.resolveDependencies( buildingRequest, dependencies, managedDependencies, null );
}
catch ( DependencyResolverException e )
{
throw new RepositoryAssemblyException( "Error resolving artifacts: " + e.getMessage(), e );
}
ArtifactFilter filter = buildRepositoryFilter( repository, project );
buildingRequest = repositoryManager.setLocalRepositoryBasedir( buildingRequest, repositoryDirectory );
Map<String, GroupVersionAlignment> groupVersionAlignments =
createGroupVersionAlignments( repository.getGroupVersionAlignments() );
assembleRepositoryArtifacts( buildingRequest, result, filter, groupVersionAlignments );
if ( repository.isIncludeMetadata() )
{
// assembleRepositoryMetadata( result, filter, centralRepository, targetRepository );
}
try
{
FileUtils.deleteDirectory( tempRepo );
}
catch ( IOException e )
{
// noop
}
}
private ArtifactFilter buildRepositoryFilter( RepositoryInfo repository, MavenProject project )
{
AndArtifactFilter filter = new AndArtifactFilter();
ArtifactFilter scopeFilter = new ScopeArtifactFilter( repository.getScope() );
filter.add( scopeFilter );
// ----------------------------------------------------------------------------
// Includes
//
// We'll take everything if no includes are specified to try and make
// this
// process more maintainable. Don't want to have to update the assembly
// descriptor everytime the POM is updated.
// ----------------------------------------------------------------------------
List<String> includes = repository.getIncludes();
if ( ( includes == null ) || includes.isEmpty() )
{
List<String> patterns = new ArrayList<>();
Set<Artifact> projectArtifacts = project.getDependencyArtifacts();
if ( projectArtifacts != null )
{
for ( Artifact artifact : projectArtifacts )
{
patterns.add( artifact.getDependencyConflictId() );
}
}
PatternIncludesArtifactFilter includeFilter = new PatternIncludesArtifactFilter( patterns, true );
filter.add( includeFilter );
}
else
{
filter.add( new PatternIncludesArtifactFilter( repository.getIncludes(), true ) );
}
// ----------------------------------------------------------------------------
// Excludes
//
// We still want to make it easy to exclude a few things even if we
// slurp
// up everything.
// ----------------------------------------------------------------------------
List<String> excludes = repository.getExcludes();
if ( ( excludes != null ) && !excludes.isEmpty() )
{
filter.add( new PatternExcludesArtifactFilter( repository.getExcludes(), true ) );
}
return filter;
}
private void assembleRepositoryArtifacts( ProjectBuildingRequest buildingRequest, Iterable<ArtifactResult> result,
ArtifactFilter filter,
Map<String, GroupVersionAlignment> groupVersionAlignments )
throws RepositoryAssemblyException
{
try
{
for ( ArtifactResult ar : result )
{
Artifact a = ar.getArtifact();
if ( filter.include( a ) )
{
getLogger().debug( "Re-resolving: " + a + " for repository assembly." );
setAlignment( a, groupVersionAlignments );
artifactResolver.resolveArtifact( buildingRequest, TransferUtils.toArtifactCoordinate( a ) );
a.setVersion( a.getBaseVersion() );
File targetFile = new File( repositoryManager.getLocalRepositoryBasedir( buildingRequest ),
repositoryManager.getPathForLocalArtifact( buildingRequest, a ) );
FileUtils.copyFile( a.getFile(), targetFile );
// writeChecksums( targetFile );
}
}
}
catch ( ArtifactResolverException e )
{
throw new RepositoryAssemblyException( "Error resolving artifacts: " + e.getMessage(), e );
}
catch ( IOException e )
{
throw new RepositoryAssemblyException( "Error writing artifact metdata.", e );
}
}
// CHECKSTYLE_OFF: LineLength
protected Map<String, GroupVersionAlignment> createGroupVersionAlignments( List<GroupVersionAlignment> versionAlignments )
// CHECKSTYLE_ON: LineLength
{
Map<String, GroupVersionAlignment> groupVersionAlignments = new HashMap<>();
if ( versionAlignments != null )
{
for ( GroupVersionAlignment alignment : versionAlignments )
{
groupVersionAlignments.put( alignment.getId(), alignment );
}
}
return groupVersionAlignments;
}
private void setAlignment( Artifact artifact, Map<String, GroupVersionAlignment> groupVersionAlignments )
{
GroupVersionAlignment alignment = groupVersionAlignments.get( artifact.getGroupId() );
if ( alignment != null )
{
if ( !alignment.getExcludes().contains( artifact.getArtifactId() ) )
{
artifact.setVersion( alignment.getVersion() );
}
}
}
}