001package org.apache.maven.plugin.plugin;
002
003/*
004 * Licensed to the Apache Software Foundation (ASF) under one
005 * or more contributor license agreements.  See the NOTICE file
006 * distributed with this work for additional information
007 * regarding copyright ownership.  The ASF licenses this file
008 * to you under the Apache License, Version 2.0 (the
009 * "License"); you may not use this file except in compliance
010 * with the License.  You may obtain a copy of the License at
011 *
012 *   http://www.apache.org/licenses/LICENSE-2.0
013 *
014 * Unless required by applicable law or agreed to in writing,
015 * software distributed under the License is distributed on an
016 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
017 * KIND, either express or implied.  See the License for the
018 * specific language governing permissions and limitations
019 * under the License.
020 */
021
022import org.apache.maven.artifact.ArtifactUtils;
023import org.apache.maven.plugin.AbstractMojo;
024import org.apache.maven.plugin.MojoExecutionException;
025import org.apache.maven.plugin.MojoFailureException;
026import org.apache.maven.plugin.registry.MavenPluginRegistryBuilder;
027import org.apache.maven.plugin.registry.Plugin;
028import org.apache.maven.plugin.registry.PluginRegistry;
029import org.apache.maven.plugin.registry.PluginRegistryUtils;
030import org.apache.maven.plugin.registry.TrackableBase;
031import org.apache.maven.plugin.registry.io.xpp3.PluginRegistryXpp3Writer;
032import org.apache.maven.plugins.annotations.Component;
033import org.apache.maven.plugins.annotations.LifecyclePhase;
034import org.apache.maven.plugins.annotations.Mojo;
035import org.apache.maven.plugins.annotations.Parameter;
036import org.codehaus.plexus.util.IOUtil;
037import org.codehaus.plexus.util.WriterFactory;
038import org.codehaus.plexus.util.xml.pull.XmlPullParserException;
039
040import java.io.File;
041import java.io.IOException;
042import java.io.Writer;
043import java.text.SimpleDateFormat;
044import java.util.Date;
045
046/**
047 * Update the user plugin registry (if it's in use) to reflect the version we're installing.
048 *
049 * @since 2.0
050 * @deprecated plugin registry has been removed from Maven 3, this goal will be removed in next release
051 */
052@Mojo( name = "updateRegistry", defaultPhase = LifecyclePhase.INSTALL, threadSafe = true )
053public class UpdatePluginRegistryMojo
054    extends AbstractMojo
055{
056    /**
057     * Indicates whether the <code>plugin-registry.xml</code> file is used by Maven or not
058     * to manage plugin versions.
059     */
060    @Parameter( defaultValue = "${settings.usePluginRegistry}", required = true, readonly = true )
061    private boolean usePluginRegistry;
062
063    /**
064     * The group id of the project currently being built.
065     */
066    @Parameter( defaultValue = "${project.groupId}", required = true, readonly = true )
067    private String groupId;
068
069    /**
070     * The artifact id of the project currently being built.
071     */
072    @Parameter( defaultValue = "${project.artifactId}", required = true, readonly = true )
073    private String artifactId;
074
075    /**
076     * The version of the project currently being built.
077     */
078    @Parameter( defaultValue = "${project.artifact.version}", required = true, readonly = true )
079    private String version;
080
081    /**
082     * Plexus component for retrieving the plugin registry info.
083     */
084    @Component
085    private MavenPluginRegistryBuilder pluginRegistryBuilder;
086
087    /**
088     * Set this to "true" to skip invoking any goals or reports of the plugin.
089     *
090     * @since 2.8
091     */
092    @Parameter( defaultValue = "false", property = "maven.plugin.skip" )
093    private boolean skip;
094
095    /**
096     * Set this to "true" to skip updating the plugin registry.
097     *
098     * @since 2.8
099     */
100    @Parameter( defaultValue = "false", property = "maven.plugin.update.registry.skip" )
101    private boolean skipUpdatePluginRegistry;
102
103    /** {@inheritDoc} */
104    public void execute()
105        throws MojoExecutionException, MojoFailureException
106    {
107        if ( usePluginRegistry )
108        {
109            if ( skip || skipUpdatePluginRegistry )
110            {
111                getLog().warn( "Execution skipped" );
112                return;
113            }
114            updatePluginVersionInRegistry( groupId, artifactId, version );
115        }
116    }
117
118    /**
119     * @param aGroupId not null
120     * @param anArtifactId not null
121     * @param aVersion not null
122     * @throws MojoExecutionException if any
123     */
124    private void updatePluginVersionInRegistry( String aGroupId, String anArtifactId, String aVersion )
125        throws MojoExecutionException
126    {
127        PluginRegistry pluginRegistry;
128        try
129        {
130            pluginRegistry = getPluginRegistry( aGroupId, anArtifactId );
131        }
132        catch ( IOException e )
133        {
134            throw new MojoExecutionException( "Failed to read plugin registry.", e );
135        }
136        catch ( XmlPullParserException e )
137        {
138            throw new MojoExecutionException( "Failed to parse plugin registry.", e );
139        }
140
141        String pluginKey = ArtifactUtils.versionlessKey( aGroupId, anArtifactId );
142        Plugin plugin = (Plugin) pluginRegistry.getPluginsByKey().get( pluginKey );
143
144        // if we can find the plugin, but we've gotten here, the useVersion must be missing; fill it in.
145        if ( plugin != null )
146        {
147            if ( TrackableBase.GLOBAL_LEVEL.equals( plugin.getSourceLevel() ) )
148            {
149                // do nothing. We don't rewrite the globals, under any circumstances.
150                getLog().warn( "Cannot update registered version for plugin {" + aGroupId + ":" + anArtifactId
151                    + "}; it is specified in the global registry." );
152            }
153            else
154            {
155                plugin.setUseVersion( aVersion );
156
157                SimpleDateFormat format =
158                    new SimpleDateFormat( org.apache.maven.plugin.registry.Plugin.LAST_CHECKED_DATE_FORMAT );
159
160                plugin.setLastChecked( format.format( new Date() ) );
161            }
162        }
163        else
164        {
165            plugin = new org.apache.maven.plugin.registry.Plugin();
166
167            plugin.setGroupId( aGroupId );
168            plugin.setArtifactId( anArtifactId );
169            plugin.setUseVersion( aVersion );
170
171            pluginRegistry.addPlugin( plugin );
172
173            pluginRegistry.flushPluginsByKey();
174        }
175
176        writeUserRegistry( aGroupId, anArtifactId, pluginRegistry );
177    }
178
179    /**
180     * @param aGroupId not null
181     * @param anArtifactId not null
182     * @param pluginRegistry not null
183     */
184    private void writeUserRegistry( String aGroupId, String anArtifactId, PluginRegistry pluginRegistry )
185    {
186        File pluginRegistryFile = pluginRegistry.getRuntimeInfo().getFile();
187
188        PluginRegistry extractedUserRegistry = PluginRegistryUtils.extractUserPluginRegistry( pluginRegistry );
189
190        // only rewrite the user-level registry if one existed before, or if we've created user-level data here.
191        if ( extractedUserRegistry != null )
192        {
193            Writer fWriter = null;
194
195            try
196            {
197                pluginRegistryFile.getParentFile().mkdirs();
198                fWriter = WriterFactory.newXmlWriter( pluginRegistryFile );
199
200                PluginRegistryXpp3Writer writer = new PluginRegistryXpp3Writer();
201
202                writer.write( fWriter, extractedUserRegistry );
203            }
204            catch ( IOException e )
205            {
206                getLog().warn( "Cannot rewrite user-level plugin-registry.xml with new plugin version of plugin: \'"
207                    + aGroupId + ":" + anArtifactId + "\'.", e );
208            }
209            finally
210            {
211                IOUtil.close( fWriter );
212            }
213        }
214    }
215
216    /**
217     * @param aGroupId not null
218     * @param anArtifactId not null
219     * @return the plugin registry instance
220     * @throws IOException if any
221     * @throws XmlPullParserException if any
222     */
223    private PluginRegistry getPluginRegistry( String aGroupId, String anArtifactId )
224        throws IOException, XmlPullParserException
225    {
226        PluginRegistry pluginRegistry = null;
227
228        pluginRegistry = pluginRegistryBuilder.buildPluginRegistry();
229
230        if ( pluginRegistry == null )
231        {
232            pluginRegistry = pluginRegistryBuilder.createUserPluginRegistry();
233        }
234
235        return pluginRegistry;
236    }
237}