View Javadoc
1   package org.apache.maven.plugins.assembly.archive.task;
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.ArrayList;
24  import java.util.Arrays;
25  import java.util.HashSet;
26  import java.util.List;
27  
28  import org.apache.maven.plugins.assembly.AssemblerConfigurationSource;
29  import org.apache.maven.plugins.assembly.archive.ArchiveCreationException;
30  import org.apache.maven.plugins.assembly.format.AssemblyFormattingException;
31  import org.apache.maven.plugins.assembly.format.ReaderFormatter;
32  import org.apache.maven.plugins.assembly.model.FileSet;
33  import org.apache.maven.plugins.assembly.utils.AssemblyFileUtils;
34  import org.apache.maven.plugins.assembly.utils.AssemblyFormatUtils;
35  import org.apache.maven.plugins.assembly.utils.TypeConversionUtils;
36  import org.apache.maven.project.MavenProject;
37  import org.codehaus.plexus.archiver.Archiver;
38  import org.codehaus.plexus.components.io.functions.InputStreamTransformer;
39  import org.slf4j.Logger;
40  import org.slf4j.LoggerFactory;
41  
42  /**
43   *
44   */
45  public class AddFileSetsTask
46  {
47      private static final Logger LOGGER = LoggerFactory.getLogger( AddFileSetsTask.class );
48  
49      private final List<FileSet> fileSets;
50  
51      private MavenProject project;
52  
53      private MavenProject moduleProject;
54  
55      public AddFileSetsTask( final List<FileSet> fileSets )
56      {
57          this.fileSets = fileSets;
58      }
59  
60      public AddFileSetsTask( final FileSet... fileSets )
61      {
62          this.fileSets = new ArrayList<>( Arrays.asList( fileSets ) );
63      }
64  
65      public void execute( final Archiver archiver, final AssemblerConfigurationSource configSource )
66          throws ArchiveCreationException, AssemblyFormattingException
67      {
68          // don't need this check here. it's more efficient here, but the logger is not actually
69          // used until addFileSet(..)...and the check should be there in case someone extends the
70          // class.
71          // checkLogger();
72  
73          final File archiveBaseDir = configSource.getArchiveBaseDirectory();
74  
75          if ( archiveBaseDir != null )
76          {
77              if ( !archiveBaseDir.exists() )
78              {
79                  throw new ArchiveCreationException(
80                      "The archive base directory '" + archiveBaseDir.getAbsolutePath() + "' does not exist" );
81              }
82              else if ( !archiveBaseDir.isDirectory() )
83              {
84                  throw new ArchiveCreationException( "The archive base directory '" + archiveBaseDir.getAbsolutePath()
85                                                          + "' exists, but it is not a directory" );
86              }
87          }
88  
89          for ( final FileSet fileSet : fileSets )
90          {
91              addFileSet( fileSet, archiver, configSource, archiveBaseDir );
92          }
93      }
94  
95      void addFileSet( final FileSet fileSet, final Archiver archiver, final AssemblerConfigurationSource configSource,
96                       final File archiveBaseDir )
97          throws AssemblyFormattingException, ArchiveCreationException
98      {
99          if ( project == null )
100         {
101             project = configSource.getProject();
102         }
103 
104         final File basedir = project.getBasedir();
105 
106         String destDirectory = fileSet.getOutputDirectory();
107 
108         if ( destDirectory == null )
109         {
110             destDirectory = fileSet.getDirectory();
111 
112             AssemblyFormatUtils.warnForPlatformSpecifics( LOGGER, destDirectory );
113         }
114 
115 
116         destDirectory =
117             AssemblyFormatUtils.getOutputDirectory( destDirectory, configSource.getFinalName(), configSource,
118                                                     AssemblyFormatUtils.moduleProjectInterpolator( moduleProject ),
119                                                     AssemblyFormatUtils.artifactProjectInterpolator( project ) );
120 
121         if ( LOGGER.isDebugEnabled() )
122         {
123             LOGGER.debug( "FileSet[" + destDirectory + "]" + " dir perms: " + Integer.toString(
124                 archiver.getOverrideDirectoryMode(), 8 ) + " file perms: " + Integer.toString(
125                 archiver.getOverrideFileMode(), 8 ) + ( fileSet.getLineEnding() == null
126                 ? ""
127                 : " lineEndings: " + fileSet.getLineEnding() ) );
128         }
129 
130         LOGGER.debug( "The archive base directory is '" + archiveBaseDir + "'" );
131 
132         File fileSetDir = getFileSetDirectory( fileSet, basedir, archiveBaseDir );
133 
134         if ( fileSetDir.exists() )
135         {
136             InputStreamTransformer fileSetTransformers =
137                 ReaderFormatter.getFileSetTransformers( configSource, 
138                                                         fileSet.isFiltered(),
139                                                         new HashSet<>( fileSet.getNonFilteredFileExtensions() ),
140                                                         fileSet.getLineEnding() );
141             if ( fileSetTransformers == null )
142             {
143                 LOGGER.debug( "NOT reformatting any files in " + fileSetDir );
144             }
145 
146             if ( fileSetDir.getPath().equals( File.separator ) )
147             {
148                 throw new AssemblyFormattingException(
149                     "Your assembly descriptor specifies a directory of " + File.separator
150                         + ", which is your *entire* file system.\nThese are not the files you are looking for" );
151             }
152             final AddDirectoryTask task = new AddDirectoryTask( fileSetDir, fileSetTransformers );
153 
154             final int dirMode = TypeConversionUtils.modeToInt( fileSet.getDirectoryMode(), LOGGER );
155             if ( dirMode != -1 )
156             {
157                 task.setDirectoryMode( dirMode );
158             }
159 
160             final int fileMode = TypeConversionUtils.modeToInt( fileSet.getFileMode(), LOGGER );
161             if ( fileMode != -1 )
162             {
163                 task.setFileMode( fileMode );
164             }
165 
166             task.setUseDefaultExcludes( fileSet.isUseDefaultExcludes() );
167             task.setExcludes( fileSet.getExcludes() );
168             task.setIncludes( fileSet.getIncludes() );
169             task.setOutputDirectory( destDirectory );
170 
171             task.execute( archiver );
172         }
173     }
174 
175     File getFileSetDirectory( final FileSet fileSet, final File basedir, final File archiveBaseDir )
176         throws ArchiveCreationException, AssemblyFormattingException
177     {
178         String sourceDirectory = fileSet.getDirectory();
179 
180         if ( sourceDirectory == null || sourceDirectory.trim().length() < 1 )
181         {
182             sourceDirectory = basedir.getAbsolutePath();
183         }
184 
185         File fileSetDir;
186 
187         if ( archiveBaseDir == null )
188         {
189             fileSetDir = new File( sourceDirectory );
190 
191             // If the file is not absolute then it's a subpath of the current project basedir
192             // For OS compatibility we also must treat any path starting with "/" as absolute
193             // as File#isAbsolute() returns false for /absolutePath under Windows :(
194             // Note that in Windows an absolute path with / will be on the 'current drive'.
195             // But I think we can live with this.
196             if ( ! AssemblyFileUtils.isAbsolutePath( fileSetDir ) )
197             {
198                 fileSetDir = new File( basedir, sourceDirectory );
199             }
200         }
201         else
202         {
203             fileSetDir = new File( archiveBaseDir, sourceDirectory );
204         }
205 
206         return fileSetDir;
207     }
208 
209     public void setProject( final MavenProject project )
210     {
211         this.project = project;
212     }
213 
214     public void setModuleProject( final MavenProject moduleProject )
215     {
216         this.moduleProject = moduleProject;
217     }
218 
219 }