Coverage Report - org.apache.maven.plugins.repository.BundlePackMojo
 
Classes in this File Line Coverage Branch Coverage Complexity
BundlePackMojo
47%
56/120
55%
35/64
0
 
 1  
 package org.apache.maven.plugins.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 org.apache.maven.artifact.Artifact;
 23  
 import org.apache.maven.artifact.factory.ArtifactFactory;
 24  
 import org.apache.maven.artifact.repository.ArtifactRepository;
 25  
 import org.apache.maven.artifact.resolver.ArtifactNotFoundException;
 26  
 import org.apache.maven.artifact.resolver.ArtifactResolutionException;
 27  
 import org.apache.maven.artifact.resolver.ArtifactResolver;
 28  
 import org.apache.maven.model.License;
 29  
 import org.apache.maven.model.Model;
 30  
 import org.apache.maven.model.Scm;
 31  
 import org.apache.maven.model.io.xpp3.MavenXpp3Reader;
 32  
 import org.apache.maven.model.io.xpp3.MavenXpp3Writer;
 33  
 import org.apache.maven.plugin.AbstractMojo;
 34  
 import org.apache.maven.plugin.MojoExecutionException;
 35  
 import org.apache.maven.settings.Settings;
 36  
 import org.codehaus.plexus.archiver.ArchiverException;
 37  
 import org.codehaus.plexus.archiver.jar.JarArchiver;
 38  
 import org.codehaus.plexus.components.interactivity.InputHandler;
 39  
 import org.codehaus.plexus.util.ReaderFactory;
 40  
 import org.codehaus.plexus.util.WriterFactory;
 41  
 import org.codehaus.plexus.util.xml.pull.XmlPullParserException;
 42  
 
 43  
 import java.io.File;
 44  
 import java.io.FileNotFoundException;
 45  
 import java.io.IOException;
 46  
 import java.util.Collections;
 47  
 import java.util.List;
 48  
 
 49  
 /**
 50  
  * Packs artifacts already available in a local repository in a bundle for an
 51  
  * upload requests. It requires that the artifact has a POM in the local
 52  
  * repository. It will check for mandatory elements, asking interactively for
 53  
  * missing values. Can be used to generate bundles for third parties artifacts
 54  
  * that have been manually added to the local repository.
 55  
  *
 56  
  * @goal bundle-pack
 57  
  * @requiresProject false
 58  
  * @since 2.1
 59  
  */
 60  6
 public class BundlePackMojo
 61  
     extends AbstractMojo
 62  
 {
 63  
     public static final String POM = "pom.xml";
 64  
 
 65  
     /**
 66  
      * Jar archiver.
 67  
      * 
 68  
      * @component role="org.codehaus.plexus.archiver.Archiver" roleHint="jar"
 69  
      */
 70  
     protected JarArchiver jarArchiver;
 71  
 
 72  
     /**
 73  
      * Artifact resolver.
 74  
      * 
 75  
      * @component
 76  
      */
 77  
     protected ArtifactResolver artifactResolver;
 78  
 
 79  
     /**
 80  
      * Artifact factory.
 81  
      * 
 82  
      * @component
 83  
      */
 84  
     protected ArtifactFactory artifactFactory;
 85  
 
 86  
     /**
 87  
      * Local maven repository.
 88  
      * 
 89  
      * @parameter default-value="${localRepository}"
 90  
      * @required
 91  
      * @readonly
 92  
      */
 93  
     protected ArtifactRepository localRepository;
 94  
 
 95  
     /**
 96  
      * @component
 97  
      */
 98  
     protected InputHandler inputHandler;
 99  
 
 100  
     /**
 101  
      * Directory where the upload-bundle will be created.
 102  
      *
 103  
      * @parameter default-value="${basedir}"
 104  
      * @readonly
 105  
      */
 106  
     protected String basedir;
 107  
 
 108  
     /**
 109  
      * GroupId for the artifact to create an upload bundle for.
 110  
      *
 111  
      * @parameter expression="${groupId}"
 112  
      */
 113  
     protected String groupId;
 114  
 
 115  
     /**
 116  
      * ArtifactId for the artifact to create an upload bundle for.
 117  
      *
 118  
      * @parameter expression="${artifactId}"
 119  
      */
 120  
     protected String artifactId;
 121  
 
 122  
     /**
 123  
      * Version for the artifact to create an upload bundle for.
 124  
      * 
 125  
      * @parameter expression="${version}"
 126  
      */
 127  
     protected String version;
 128  
     
 129  
     /**
 130  
      * Viewable URL for SCM connections, in cases where this isn't provided by the POM.
 131  
      * @parameter expression="${scmUrl}"
 132  
      */
 133  
     protected String scmUrl;
 134  
     
 135  
     /**
 136  
      * Read-only URL for SCM tool connections, in cases where this isn't provided by the POM.
 137  
      * <br/>
 138  
      * <b>NOTE:</b> This should be a standard maven-scm URL. See the 
 139  
      * <a href="http://maven.apache.org/scm/scm-url-format.html">format guidelines</a> for more 
 140  
      * information.
 141  
      * 
 142  
      * @parameter expression="${scmConnection}"
 143  
      */
 144  
     protected String scmConnection;
 145  
     
 146  
     /**
 147  
      * @parameter default-value="${settings}"
 148  
      * @readonly
 149  
      */
 150  
     protected Settings settings;
 151  
 
 152  
     /**
 153  
      * Disable validations to make sure bundle supports project materialization.
 154  
      * <br/>
 155  
      * <b>WARNING: This means your project will be MUCH harder to use.</b>
 156  
      * @parameter expression="${bundle.disableMaterialization}" default-value="false"
 157  
      */
 158  
     private boolean disableMaterialization;
 159  
 
 160  
     @SuppressWarnings( "unchecked" )
 161  
     public void execute()
 162  
         throws MojoExecutionException
 163  
     {
 164  6
         readArtifactDataFromUser();
 165  
 
 166  6
         Artifact artifact = artifactFactory.createProjectArtifact( groupId, artifactId, version );
 167  
 
 168  
         try
 169  
         {
 170  6
             artifactResolver.resolve( artifact, Collections.EMPTY_LIST, localRepository );
 171  
         }
 172  0
         catch ( ArtifactResolutionException e )
 173  
         {
 174  0
             throw new MojoExecutionException( "Unable to resolve artifact " + artifact.getId(), e );
 175  
         }
 176  0
         catch ( ArtifactNotFoundException e )
 177  
         {
 178  0
             throw new MojoExecutionException( "Artifact " + artifact.getId() + " not found in local repository", e );
 179  6
         }
 180  
 
 181  6
         File pom = artifact.getFile();
 182  
 
 183  6
         File dir = pom.getParentFile();
 184  
 
 185  6
         Model model = readPom( pom );
 186  
 
 187  6
         boolean rewrite = false;
 188  
         try
 189  
         {
 190  
 
 191  6
             if ( model.getPackaging() == null )
 192  
             {
 193  0
                 model.setPackaging( "jar" );
 194  0
                 rewrite = true;
 195  
             }
 196  6
             if ( model.getName() == null )
 197  
             {
 198  0
                 getLog().info( "Project name is missing, please type the project name [" + artifactId + "]:" );
 199  0
                 model.setName( inputHandler.readLine() );
 200  0
                 if ( model.getName() == null )
 201  
                 {
 202  0
                     model.setName( artifactId );
 203  
                 }
 204  0
                 rewrite = true;
 205  
             }
 206  6
             if ( model.getDescription() == null )
 207  
             {
 208  0
                 getLog().info( "Project description is missing, please type the project description:" );
 209  0
                 model.setDescription( inputHandler.readLine() );
 210  0
                 rewrite = true;
 211  
             }
 212  6
             if ( model.getUrl() == null )
 213  
             {
 214  0
                 getLog().info( "Project URL is missing, please type the project URL:" );
 215  0
                 model.setUrl( inputHandler.readLine() );
 216  0
                 rewrite = true;
 217  
             }
 218  
 
 219  6
             List<License> licenses = model.getLicenses();
 220  6
             if ( licenses.isEmpty() )
 221  
             {
 222  0
                 License license = new License();
 223  
 
 224  0
                 getLog().info( "License name is missing, please type the license name:" );
 225  0
                 license.setName( inputHandler.readLine() );
 226  0
                 getLog().info( "License URL is missing, please type the license URL:" );
 227  0
                 license.setUrl( inputHandler.readLine() );
 228  0
                 licenses.add( license );
 229  0
                 rewrite = true;
 230  
             }
 231  
             
 232  6
             if ( disableMaterialization )
 233  
             {
 234  0
                 getLog().warn( "Validations to confirm support for project materialization have been DISABLED." +
 235  
                         "\n\nYour project may not provide the POM elements necessary to allow users to retrieve sources on-demand," +
 236  
                         "\nor to easily checkout your project in an IDE. THIS CAN SERIOUSLY INCONVENIENCE YOUR USERS." +
 237  
                         "\n\nContinue? [y/N]" );
 238  
                 
 239  
                 try
 240  
                 {
 241  0
                     if ( 'y' != inputHandler.readLine().toLowerCase().charAt( 0 ) )
 242  
                     {
 243  0
                         disableMaterialization = false;
 244  
                     }
 245  
                 }
 246  0
                 catch ( IOException e )
 247  
                 {
 248  0
                     getLog().debug( "Error reading confirmation: " + e.getMessage(), e );
 249  0
                 }
 250  
                 
 251  
             }
 252  
             
 253  6
             if ( !disableMaterialization )
 254  
             {
 255  6
                 Scm scm = model.getScm();
 256  6
                 if ( scm == null )
 257  
                 {
 258  0
                     scm = new Scm();
 259  0
                     model.setScm( scm );
 260  
                 }
 261  
                 
 262  6
                 if ( scm.getUrl() == null )
 263  
                 {
 264  0
                     if ( scmUrl != null )
 265  
                     {
 266  0
                         scm.setUrl( scmUrl );
 267  
                     }
 268  
                     else
 269  
                     {
 270  0
                         getLog().info( "SCM view URL is missing, please type the URL for the viewable SCM interface:" );
 271  0
                         scm.setUrl( inputHandler.readLine() );
 272  0
                         rewrite = true;
 273  
                     }
 274  
                 }
 275  
                 
 276  6
                 if ( scm.getConnection() == null )
 277  
                 {
 278  0
                     if ( scmConnection != null )
 279  
                     {
 280  0
                         scm.setConnection( scmConnection );
 281  
                     }
 282  
                     else
 283  
                     {
 284  0
                         getLog().info( "SCM read-only connection URL is missing, please type the read-only SCM URL:" );
 285  0
                         scm.setConnection( inputHandler.readLine() );
 286  0
                         rewrite = true;
 287  
                     }
 288  
                 }
 289  
             }
 290  
         }
 291  0
         catch ( IOException e )
 292  
         {
 293  0
             throw new MojoExecutionException( e.getMessage(), e );
 294  6
         }
 295  
 
 296  
         try
 297  
         {
 298  6
             if ( rewrite )
 299  
             {
 300  0
                 new MavenXpp3Writer().write( WriterFactory.newXmlWriter( pom ), model );
 301  
             }
 302  
 
 303  6
             String finalName = null;
 304  
 
 305  6
             if ( model.getBuild() != null )
 306  
             {
 307  0
                 finalName = model.getBuild().getFinalName();
 308  
             }
 309  6
             if ( finalName == null )
 310  
             {
 311  6
                 finalName = model.getArtifactId() + "-" + model.getVersion();
 312  
             }
 313  
             
 314  6
             boolean batchMode = settings == null ? false : !settings.isInteractiveMode();
 315  6
             List<File> files = BundleUtils.selectProjectFiles( dir, inputHandler, finalName, pom, getLog(), batchMode );
 316  
 
 317  6
             File bundle = new File( basedir, finalName + "-bundle.jar" );
 318  
 
 319  6
             jarArchiver.addFile( pom, POM );
 320  
 
 321  6
             boolean artifactChecks = !"pom".equals( model.getPackaging() );
 322  6
             boolean sourcesFound = false;
 323  6
             boolean javadocsFound = false;
 324  
             
 325  6
             for ( File f : files )
 326  
             {
 327  8
                 if ( artifactChecks && f.getName().endsWith( finalName + "-sources.jar" ) )
 328  
                 {
 329  1
                     sourcesFound = true;
 330  
                 }
 331  7
                 else if ( artifactChecks && f.getName().equals( finalName + "-javadoc.jar" ) )
 332  
                 {
 333  2
                     javadocsFound = true;
 334  
                 }
 335  
                 
 336  8
                 jarArchiver.addFile( f, f.getName() );
 337  
             }
 338  
             
 339  6
             if ( artifactChecks && !sourcesFound )
 340  
             {
 341  4
                 getLog().warn( "Sources not included in upload bundle." );
 342  
             }
 343  
 
 344  6
             if ( artifactChecks && !javadocsFound )
 345  
             {
 346  3
                 getLog().warn( "Javadoc not included in upload bundle." );
 347  
             }
 348  
 
 349  6
             jarArchiver.setDestFile( bundle );
 350  
 
 351  6
             jarArchiver.createArchive();
 352  
 
 353  
         }
 354  0
         catch ( IOException e )
 355  
         {
 356  0
             throw new MojoExecutionException( e.getMessage(), e );
 357  
         }
 358  0
         catch ( ArchiverException e )
 359  
         {
 360  0
             throw new MojoExecutionException( e.getMessage(), e );
 361  6
         }
 362  
 
 363  6
     }
 364  
 
 365  
     /**
 366  
      * Read groupId, artifactId and version from the user on the command line,
 367  
      * if they were not provided as parameters.
 368  
      *
 369  
      * @throws MojoExecutionException If the values can't be read
 370  
      */
 371  
     private void readArtifactDataFromUser()
 372  
         throws MojoExecutionException
 373  
     {
 374  
         try
 375  
         {
 376  6
             if ( groupId == null )
 377  
             {
 378  0
                 getLog().info( "groupId? " );
 379  
 
 380  0
                 groupId = inputHandler.readLine();
 381  
 
 382  
             }
 383  
 
 384  6
             if ( artifactId == null )
 385  
             {
 386  0
                 getLog().info( "artifactId? " );
 387  0
                 artifactId = inputHandler.readLine();
 388  
             }
 389  
 
 390  6
             if ( version == null )
 391  
             {
 392  0
                 getLog().info( "version? " );
 393  0
                 version = inputHandler.readLine();
 394  
             }
 395  
         }
 396  0
         catch ( IOException e )
 397  
         {
 398  0
             throw new MojoExecutionException( e.getMessage(), e );
 399  6
         }
 400  6
     }
 401  
 
 402  
     /**
 403  
      * Read the POM file.
 404  
      *
 405  
      * @param pom The file to read
 406  
      * @return A Maven Model
 407  
      * @throws MojoExecutionException if something goes wrong when reading the file
 408  
      */
 409  
     private Model readPom( File pom )
 410  
         throws MojoExecutionException
 411  
     {
 412  
         Model model;
 413  
         try
 414  
         {
 415  6
             model = new MavenXpp3Reader().read( ReaderFactory.newXmlReader( pom ) );
 416  
         }
 417  0
         catch ( XmlPullParserException e )
 418  
         {
 419  0
             throw new MojoExecutionException( "Unable to parse POM at " + pom.getAbsolutePath() + ": " + e.getMessage(),
 420  
                                               e );
 421  
         }
 422  0
         catch ( FileNotFoundException e )
 423  
         {
 424  0
             throw new MojoExecutionException( "Unable to read POM at " + pom.getAbsolutePath() + ": " + e.getMessage(),
 425  
                                               e );
 426  
         }
 427  0
         catch ( IOException e )
 428  
         {
 429  0
             throw new MojoExecutionException( "Unable to read POM at " + pom.getAbsolutePath() + ": " + e.getMessage(),
 430  
                                               e );
 431  6
         }
 432  6
         return model;
 433  
     }
 434  
 
 435  
 }