add dependency handling, and make bugfixes to the assemble plugin

git-svn-id: https://svn.apache.org/repos/asf/maven/components/trunk@163798 13f79535-47bb-0310-9956-ffa450edef68
This commit is contained in:
Brett Leslie Porter 2005-04-06 05:11:00 +00:00
parent 9c4a483c6d
commit a7e2faccfa
5 changed files with 319 additions and 97 deletions

View File

@ -10,6 +10,11 @@
<name>Maven Assemble Plugin</name> <name>Maven Assemble Plugin</name>
<version>1.0-SNAPSHOT</version> <version>1.0-SNAPSHOT</version>
<dependencies> <dependencies>
<dependency>
<groupId>org.apache.maven</groupId>
<artifactId>maven-artifact</artifactId>
<version>2.0-SNAPSHOT</version>
</dependency>
<dependency> <dependency>
<groupId>plexus</groupId> <groupId>plexus</groupId>
<artifactId>plexus-archiver</artifactId> <artifactId>plexus-archiver</artifactId>

View File

@ -16,12 +16,17 @@ package org.apache.maven.plugin.assemble;
* limitations under the License. * limitations under the License.
*/ */
import org.apache.maven.artifact.Artifact;
import org.apache.maven.artifact.resolver.filter.ArtifactFilter;
import org.apache.maven.artifact.resolver.filter.ScopeArtifactFilter;
import org.apache.maven.plugin.AbstractPlugin; import org.apache.maven.plugin.AbstractPlugin;
import org.apache.maven.plugin.PluginExecutionException; import org.apache.maven.plugin.PluginExecutionException;
import org.apache.maven.plugins.assemble.model.Assembly; import org.apache.maven.plugins.assemble.model.Assembly;
import org.apache.maven.plugins.assemble.model.DependencySet;
import org.apache.maven.plugins.assemble.model.FileSet; import org.apache.maven.plugins.assemble.model.FileSet;
import org.apache.maven.plugins.assemble.model.io.xpp3.AssemblyXpp3Reader; import org.apache.maven.plugins.assemble.model.io.xpp3.AssemblyXpp3Reader;
import org.codehaus.plexus.archiver.Archiver; import org.codehaus.plexus.archiver.Archiver;
import org.codehaus.plexus.archiver.ArchiverException;
import org.codehaus.plexus.archiver.jar.JarArchiver; import org.codehaus.plexus.archiver.jar.JarArchiver;
import org.codehaus.plexus.archiver.tar.TarArchiver; import org.codehaus.plexus.archiver.tar.TarArchiver;
import org.codehaus.plexus.archiver.zip.ZipArchiver; import org.codehaus.plexus.archiver.zip.ZipArchiver;
@ -32,18 +37,23 @@ import java.io.FileReader;
import java.io.InputStream; import java.io.InputStream;
import java.io.InputStreamReader; import java.io.InputStreamReader;
import java.io.Reader; import java.io.Reader;
import java.util.ArrayList;
import java.util.Iterator; import java.util.Iterator;
import java.util.List;
import java.util.Set;
/** /**
* @author <a href="mailto:brett@apache.org">Brett Porter</a> * @author <a href="mailto:brett@apache.org">Brett Porter</a>
* @version $Id$ * @version $Id$
* @goal assemble * @goal assemble
* @requiresDependencyResolution test
* @description assemble an application bundle or distribution * @description assemble an application bundle or distribution
* @parameter name="basedir" type="String" required="true" validator="" expression="#basedir" description="" * @parameter name="basedir" type="String" required="true" validator="" expression="#basedir" description=""
* @parameter name="outputDirectory" type="java.io.File" required="true" validator="" expression="#project.build.directory" description="" * @parameter name="outputDirectory" type="java.io.File" required="true" validator="" expression="#project.build.directory" description=""
* @parameter name="descriptor" type="java.io.File" required="false" validator="" expression="#maven.assemble.descriptor" description="" * @parameter name="descriptor" type="java.io.File" required="false" validator="" expression="#maven.assemble.descriptor" description=""
* @parameter name="finalName" type="String" required="true" validator="" expression="#project.build.finalName" description="" * @parameter name="finalName" type="String" required="true" validator="" expression="#project.build.finalName" description=""
* @parameter name="descriptorId" type="String" required="false" validator="" expression="#maven.assemble.descriptorId" description="" * @parameter name="descriptorId" type="String" required="false" validator="" expression="#maven.assemble.descriptorId" description=""
* @parameter name="dependencies" type="java.util.Set" required="false" validator="" expression="#project.artifacts" description=""
*/ */
public class AssembleMojo public class AssembleMojo
extends AbstractPlugin extends AbstractPlugin
@ -63,6 +73,8 @@ public class AssembleMojo
private String finalName; private String finalName;
private Set dependencies;
public void execute() public void execute()
throws PluginExecutionException throws PluginExecutionException
{ {
@ -108,7 +120,7 @@ public class AssembleMojo
Assembly assembly = reader.read( r ); Assembly assembly = reader.read( r );
// TODO: include dependencies marked for distribution under certain formats // TODO: include dependencies marked for distribution under certain formats
// TODO: how, might we plugin this into an installer, such as NSIS? // TODO: how, might we plug this into an installer, such as NSIS?
// TODO: allow file mode specifications? // TODO: allow file mode specifications?
String fullName = finalName + "-" + assembly.getId(); String fullName = finalName + "-" + assembly.getId();
@ -120,88 +132,10 @@ public class AssembleMojo
String filename = fullName + "." + format; String filename = fullName + "." + format;
// TODO: use component roles? Can we do that in a mojo? // TODO: use component roles? Can we do that in a mojo?
Archiver archiver; Archiver archiver = createArchiver( format );
if ( format.startsWith( "tar" ) )
{
TarArchiver tarArchiver = new TarArchiver();
archiver = tarArchiver;
int index = format.indexOf( '.' );
if ( index >= 0 )
{
// TODO: this needs a cleanup in plexus archiver - use a real typesafe enum
TarArchiver.TarCompressionMethod tarCompressionMethod = new TarArchiver.TarCompressionMethod();
// TODO: this should accept gz and bz2 as well so we can skip over the switch
String compression = format.substring( index + 1 );
if ( compression.equals( "gz" ) )
{
tarCompressionMethod.setValue( "gzip" );
}
else if ( compression.equals( "bz2" ) )
{
tarCompressionMethod.setValue( "bzip2" );
}
else
{
// TODO: better handling
throw new IllegalArgumentException( "Unknown compression format: " + compression );
}
tarArchiver.setCompression( tarCompressionMethod );
}
}
else if ( format.startsWith( "zip" ) )
{
archiver = new ZipArchiver();
}
else if ( format.startsWith( "jar" ) )
{
// TODO: use MavenArchiver for manifest?
archiver = new JarArchiver();
}
else
{
// TODO: better handling
throw new IllegalArgumentException( "Unknown format: " + format );
}
for ( Iterator j = assembly.getFilesets().iterator(); j.hasNext(); ) processFileSets( archiver, assembly.getFileSets() );
{ processDependencySets( archiver, assembly.getDependencySets() );
FileSet fileset = (FileSet) j.next();
String directory = fileset.getDirectory();
String output = fileset.getOutputDirectory();
if ( directory == null )
{
directory = basedir;
if ( output == null )
{
output = "/";
}
}
else
{
if ( output == null )
{
output = directory;
}
}
if ( !output.endsWith( "/" ) && !output.endsWith( "\\" ) )
{
// TODO: shouldn't archiver do this?
output += '/';
}
String[] includes = (String[]) fileset.getIncludes().toArray( EMPTY_STRING_ARRAY );
if ( includes.length == 0 )
{
includes = null;
}
String[] excludes = null;
if ( !fileset.getExcludes().isEmpty() )
{
excludes = (String[]) fileset.getExcludes().toArray( EMPTY_STRING_ARRAY );
}
// TODO: default excludes?
archiver.addDirectory( new File( directory ), output, includes, excludes );
}
archiver.setDestFile( new File( outputDirectory, filename ) ); archiver.setDestFile( new File( outputDirectory, filename ) );
archiver.createArchive(); archiver.createArchive();
@ -212,4 +146,246 @@ public class AssembleMojo
IOUtil.close( r ); IOUtil.close( r );
} }
} }
private void processDependencySets( Archiver archiver, List dependencySets )
throws ArchiverException
{
for ( Iterator i = dependencySets.iterator(); i.hasNext(); )
{
DependencySet depedencySet = (DependencySet) i.next();
String output = depedencySet.getOutputDirectory();
output = getOutputDirectory( output );
AndArtifactFilter filter = new AndArtifactFilter();
filter.add( new ScopeArtifactFilter( depedencySet.getScope() ) );
if ( !depedencySet.getIncludes().isEmpty() )
{
filter.add( new IncludesArtifactFilter( depedencySet.getIncludes() ) );
}
if ( !depedencySet.getExcludes().isEmpty() )
{
filter.add( new ExcludesArtifactFilter( depedencySet.getExcludes() ) );
}
// TODO: includes and excludes
for ( Iterator j = dependencies.iterator(); j.hasNext(); )
{
Artifact artifact = (Artifact) j.next();
if ( filter.include( artifact ) )
{
archiver.addFile( artifact.getFile(), output + artifact.getFile().getName() );
}
}
}
}
private String getOutputDirectory( String output )
{
if ( output == null )
{
output = "";
}
if ( !output.endsWith( "/" ) && !output.endsWith( "\\" ) )
{
// TODO: shouldn't archiver do this?
output += '/';
}
if ( output.startsWith( "/" ) )
{
output = finalName + output;
}
else
{
output = finalName + "/" + output;
}
return output;
}
private Archiver createArchiver( String format )
throws ArchiverException
{
Archiver archiver;
if ( format.startsWith( "tar" ) )
{
TarArchiver tarArchiver = new TarArchiver();
archiver = tarArchiver;
int index = format.indexOf( '.' );
if ( index >= 0 )
{
// TODO: this needs a cleanup in plexus archiver - use a real typesafe enum
TarArchiver.TarCompressionMethod tarCompressionMethod = new TarArchiver.TarCompressionMethod();
// TODO: this should accept gz and bz2 as well so we can skip over the switch
String compression = format.substring( index + 1 );
if ( compression.equals( "gz" ) )
{
tarCompressionMethod.setValue( "gzip" );
}
else if ( compression.equals( "bz2" ) )
{
tarCompressionMethod.setValue( "bzip2" );
}
else
{
// TODO: better handling
throw new IllegalArgumentException( "Unknown compression format: " + compression );
}
tarArchiver.setCompression( tarCompressionMethod );
}
}
else if ( format.startsWith( "zip" ) )
{
archiver = new ZipArchiver();
}
else if ( format.startsWith( "jar" ) )
{
// TODO: use MavenArchiver for manifest?
archiver = new JarArchiver();
}
else
{
// TODO: better handling
throw new IllegalArgumentException( "Unknown format: " + format );
}
return archiver;
}
private void processFileSets( Archiver archiver, java.util.List fileSets )
throws ArchiverException
{
for ( Iterator i = fileSets.iterator(); i.hasNext(); )
{
FileSet fileSet = (FileSet) i.next();
String directory = fileSet.getDirectory();
String output = fileSet.getOutputDirectory();
if ( directory == null )
{
directory = basedir;
if ( output == null )
{
output = "";
}
}
else
{
if ( output == null )
{
output = directory;
}
}
output = getOutputDirectory( output );
String[] includes = (String[]) fileSet.getIncludes().toArray( EMPTY_STRING_ARRAY );
if ( includes.length == 0 )
{
includes = null;
}
List excludesList = fileSet.getExcludes();
excludesList.addAll( getDefaultExcludes() );
String[] excludes = (String[]) excludesList.toArray( EMPTY_STRING_ARRAY );
// TODO: default excludes should be in the archiver?
archiver.addDirectory( new File( directory ), output, includes, excludes );
}
}
public List getDefaultExcludes()
{
List defaultExcludes = new ArrayList();
defaultExcludes.add( "**/*~" );
defaultExcludes.add( "**/#*#" );
defaultExcludes.add( "**/.#*" );
defaultExcludes.add( "**/%*%" );
defaultExcludes.add( "**/._*" );
// CVS
defaultExcludes.add( "**/CVS" );
defaultExcludes.add( "**/CVS/**" );
defaultExcludes.add( "**/.cvsignore" );
// SCCS
defaultExcludes.add( "**/SCCS" );
defaultExcludes.add( "**/SCCS/**" );
// Visual SourceSafe
defaultExcludes.add( "**/vssver.scc" );
// Subversion
defaultExcludes.add( "**/.svn" );
defaultExcludes.add( "**/.svn/**" );
// Mac
defaultExcludes.add( "**/.DS_Store" );
return defaultExcludes;
}
// TODO: move to maven-artifact - generally useful
private static class AndArtifactFilter
implements ArtifactFilter
{
private final List filters = new ArrayList();
public boolean include( Artifact artifact )
{
boolean include = true;
for ( Iterator i = filters.iterator(); i.hasNext() && include; )
{
ArtifactFilter filter = (ArtifactFilter) i.next();
if ( !filter.include( artifact ) )
{
include = false;
}
}
return include;
}
public void add( ArtifactFilter artifactFilter )
{
filters.add( artifactFilter );
}
}
private static class IncludesArtifactFilter
implements ArtifactFilter
{
private final List patterns;
public IncludesArtifactFilter( List patterns )
{
this.patterns = patterns;
}
public boolean include( Artifact artifact )
{
String id = artifact.getGroupId() + ":" + artifact.getArtifactId();
boolean matched = false;
for ( Iterator i = patterns.iterator(); i.hasNext() & !matched; )
{
// TODO: what about wildcards? Just specifying groups? versions?
if ( id.equals( i.next() ) )
{
matched = true;
}
}
return matched;
}
}
private static class ExcludesArtifactFilter
extends IncludesArtifactFilter
{
public ExcludesArtifactFilter( List patterns )
{
super( patterns );
}
public boolean include( Artifact artifact )
{
return !super.include( artifact );
}
}
} }

View File

@ -30,14 +30,21 @@
</association> </association>
</field> </field>
<field> <field>
<name>filesets</name> <name>fileSets</name>
<version>1.0.0</version> <version>1.0.0</version>
<required>true</required>
<association> <association>
<type>FileSet</type> <type>FileSet</type>
<multiplicity>*</multiplicity> <multiplicity>*</multiplicity>
</association> </association>
</field> </field>
<field>
<name>dependencySets</name>
<version>1.0.0</version>
<association>
<type>DependencySet</type>
<multiplicity>*</multiplicity>
</association>
</field>
</fields> </fields>
</class> </class>
<class> <class>
@ -73,6 +80,40 @@
</field> </field>
</fields> </fields>
</class> </class>
<class>
<name>DependencySet</name>
<version>1.0.0</version>
<fields>
<field>
<name>outputDirectory</name>
<version>1.0.0</version>
<type>String</type>
</field>
<field>
<name>scope</name>
<version>1.0.0</version>
<type>String</type>
<defaultValue>runtime</defaultValue>
<required>true</required>
</field>
<field>
<name>includes</name>
<version>1.0.0</version>
<association>
<type>String</type>
<multiplicity>*</multiplicity>
</association>
</field>
<field>
<name>excludes</name>
<version>1.0.0</version>
<association>
<type>String</type>
<multiplicity>*</multiplicity>
</association>
</field>
</fields>
</class>
</classes> </classes>
</model> </model>

View File

@ -5,22 +5,22 @@
<format>tar.bz2</format> <format>tar.bz2</format>
<format>zip</format> <format>zip</format>
</formats> </formats>
<filesets> <fileSets>
<fileset> <fileSet>
<includes> <includes>
<include>README*</include> <include>README*</include>
<include>LICENSE*</include> <include>LICENSE*</include>
<include>NOTICE*</include> <include>NOTICE*</include>
</includes> </includes>
</fileset> </fileSet>
<!-- TODO: docs? --> <!-- TODO: docs? -->
<fileset> <fileSet>
<!-- TODO: use expresssions instead: ${project.build.directory}, ${project.build.finalName} --> <!-- TODO: use expresssions instead: ${project.build.directory}, ${project.build.finalName} -->
<directory>target</directory> <directory>target</directory>
<outputDirectory>/</outputDirectory> <outputDirectory></outputDirectory>
<includes> <includes>
<include>*.jar</include> <include>*.jar</include>
</includes> </includes>
</fileset> </fileSet>
</filesets> </fileSets>
</assembly> </assembly>

View File

@ -5,18 +5,18 @@
<format>tar.bz2</format> <format>tar.bz2</format>
<format>zip</format> <format>zip</format>
</formats> </formats>
<filesets> <fileSets>
<fileset> <fileSet>
<includes> <includes>
<include>README*</include> <include>README*</include>
<include>LICENSE*</include> <include>LICENSE*</include>
<include>NOTICE*</include> <include>NOTICE*</include>
<include>pom.xml</include> <include>pom.xml</include>
</includes> </includes>
</fileset> </fileSet>
<fileset> <fileSet>
<!-- TODO: use expresssions instead: ${project.build.sourceDirectory}, etc --> <!-- TODO: use expresssions instead: ${project.build.sourceDirectory}, etc -->
<directory>src</directory> <directory>src</directory>
</fileset> </fileSet>
</filesets> </fileSets>
</assembly> </assembly>