com.webcohesion.enunciate.mojo.DeployArtifactBaseMojo.java Source code

Java tutorial

Introduction

Here is the source code for com.webcohesion.enunciate.mojo.DeployArtifactBaseMojo.java

Source

/**
 * Copyright  2006-2016 Web Cohesion (info@webcohesion.com)
 *
 * Licensed 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.
 */
package com.webcohesion.enunciate.mojo;

import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileReader;
import java.io.FileWriter;
import java.io.IOException;
import java.io.Reader;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

import com.webcohesion.enunciate.Enunciate;
import com.webcohesion.enunciate.artifacts.ArtifactType;
import com.webcohesion.enunciate.artifacts.ClientLibraryArtifact;
import com.webcohesion.enunciate.artifacts.FileArtifact;
import org.apache.maven.artifact.Artifact;
import org.apache.maven.artifact.deployer.ArtifactDeployer;
import org.apache.maven.artifact.deployer.ArtifactDeploymentException;
import org.apache.maven.artifact.factory.ArtifactFactory;
import org.apache.maven.artifact.metadata.ArtifactMetadata;
import org.apache.maven.artifact.repository.ArtifactRepository;
import org.apache.maven.artifact.repository.DefaultArtifactRepository;
import org.apache.maven.artifact.repository.layout.ArtifactRepositoryLayout;
import org.apache.maven.model.Model;
import org.apache.maven.model.Parent;
import org.apache.maven.model.io.xpp3.MavenXpp3Reader;
import org.apache.maven.model.io.xpp3.MavenXpp3Writer;
import org.apache.maven.plugin.AbstractMojo;
import org.apache.maven.plugin.MojoExecutionException;
import org.apache.maven.plugin.MojoFailureException;
import org.apache.maven.plugins.annotations.*;
import org.apache.maven.project.MavenProject;
import org.apache.maven.project.MavenProjectHelper;
import org.apache.maven.project.artifact.ProjectArtifactMetadata;
import org.codehaus.plexus.PlexusConstants;
import org.codehaus.plexus.PlexusContainer;
import org.codehaus.plexus.component.repository.exception.ComponentLookupException;
import org.codehaus.plexus.context.Context;
import org.codehaus.plexus.context.ContextException;
import org.codehaus.plexus.personality.plexus.lifecycle.phase.Contextualizable;
import org.codehaus.plexus.util.IOUtil;
import org.codehaus.plexus.util.xml.pull.XmlPullParserException;

/**
 * Deploy an Enunciate-generated artifact as if it were in its own project.
 *
 * @author Ryan Heaton
 */
@Mojo(name = "deploy-artifact", defaultPhase = LifecyclePhase.DEPLOY, requiresDependencyResolution = ResolutionScope.COMPILE_PLUS_RUNTIME)
public class DeployArtifactBaseMojo extends AbstractMojo implements Contextualizable {

    private static final Pattern ALT_REPO_SYNTAX_PATTERN = Pattern.compile("(.+)::(.+)::(.+)");

    @Component
    protected ArtifactDeployer deployer;

    @Parameter(defaultValue = "${localRepository}", readonly = true, required = true)
    protected ArtifactRepository localRepository;

    @Component
    protected MavenProjectHelper projectHelper;

    @Parameter(required = true)
    protected String enunciateArtifactId;

    @Parameter(defaultValue = "${project.distributionManagementArtifactRepository}", readonly = true)
    protected ArtifactRepository deploymentRepository;

    /**
     * Specifies an alternative repository to which the project artifacts should be deployed ( other
     * than those specified in <distributionManagement> ).
     * <br/>
     * Format: id::layout::url
     */
    @Parameter(defaultValue = "${altDeploymentRepository}")
    protected String altDeploymentRepository;

    /**
     * Contextualized.
     */
    protected PlexusContainer container;

    /**
     * Group id of the artifact to be deployed.  Retrieved from POM file if specified.
     */
    @Parameter(defaultValue = "${project.groupId}")
    protected String groupId;

    /**
     * ArtifactId of the artifact to be deployed.  Retrieved from POM file if specified.
     */
    @Parameter(defaultValue = "${project.artifactId}-client")
    protected String artifactId;

    /**
     * Version of the artifact to be deployed.  Retrieved from POM file if specified.
     */
    @Parameter(defaultValue = "${project.version}")
    protected String version;

    /**
     * Type of the artifact to be deployed.  Retrieved from POM file if specified.
     */
    @Parameter(defaultValue = "${project.packaging}")
    protected String packaging;

    /**
     * Description passed to a generated POM file (in case of generatePom=true)
     */
    @Parameter
    protected String description;

    /**
     * Component used to create an artifact
     */
    @Component
    protected ArtifactFactory artifactFactory;

    /**
     * Location of an existing POM file to be deployed alongside the artifact(s).
     */
    @Parameter
    protected File pomFile;

    /**
     * Upload a POM for the artifact(s) to be deployed.  Will generate a default POM if none is supplied with the pomFile argument.
     */
    @Parameter(defaultValue = "true")
    protected boolean generatePom;

    /**
     * Add classifier to the artifact
     */
    @Parameter
    protected String classifier;

    public void execute() throws MojoExecutionException, MojoFailureException {
        if (this.enunciateArtifactId == null) {
            throw new MojoExecutionException("An enunciate artifact id must be supplied.");
        }

        Enunciate enunciate = (Enunciate) getPluginContext().get(ConfigMojo.ENUNCIATE_PROPERTY);
        if (enunciate == null) {
            throw new MojoExecutionException("No enunciate mechanism found in the project!");
        }

        com.webcohesion.enunciate.artifacts.Artifact enunciateArtifact = enunciate
                .findArtifact(this.enunciateArtifactId);
        if (enunciateArtifact == null) {
            throw new MojoExecutionException("Unknown Enunciate artifact: " + this.enunciateArtifactId + ".");
        }

        File mainArtifact = null;
        File sources = null;
        File javadocs = null;
        if (enunciateArtifact instanceof ClientLibraryArtifact) {
            for (com.webcohesion.enunciate.artifacts.Artifact childArtifact : ((ClientLibraryArtifact) enunciateArtifact)
                    .getArtifacts()) {
                if (childArtifact instanceof FileArtifact) {
                    ArtifactType artifactType = ((FileArtifact) childArtifact).getArtifactType();
                    if (artifactType != null) {
                        switch (artifactType) {
                        case binaries:
                            mainArtifact = ((FileArtifact) childArtifact).getFile();
                            break;
                        case sources:
                            sources = ((FileArtifact) childArtifact).getFile();
                            break;
                        case javadocs:
                            javadocs = ((FileArtifact) childArtifact).getFile();
                            break;
                        }
                    }
                }
            }
        } else if (enunciateArtifact instanceof FileArtifact) {
            mainArtifact = ((FileArtifact) enunciateArtifact).getFile();
        } else {
            try {
                mainArtifact = enunciate.createTempFile(this.enunciateArtifactId, "artifact");
                enunciateArtifact.exportTo(mainArtifact, enunciate);
            } catch (IOException e) {
                throw new MojoExecutionException("Unable to create a temp file.", e);
            }
        }

        if (mainArtifact == null) {
            if (sources != null) {
                mainArtifact = sources;
                sources = null;
            }
        }

        if (mainArtifact == null) {
            throw new MojoExecutionException(
                    "Unable to determine the file to deploy from enunciate artifact " + enunciateArtifactId + ".");
        }

        // Process the supplied POM (if there is one)
        Model model = null;
        if (pomFile != null) {
            generatePom = false;
            model = readModel(pomFile);
            processModel(model);
        }

        if (this.packaging == null) {
            String artifactName = mainArtifact.getName();
            int dotIndex = artifactName.indexOf('.');
            if (dotIndex > 0 && (dotIndex + 1 < artifactName.length())) {
                this.packaging = artifactName.substring(dotIndex + 1);
            }
        }

        if (this.packaging == null) {
            throw new MojoExecutionException("Unable to determine the packaging of enunciate artifact "
                    + enunciateArtifactId + ". Please specify it in the configuration.");
        }

        if (this.version == null) {
            throw new MojoExecutionException("Null version.");
        }

        if (model == null) {
            model = new Model();
            model.setModelVersion("4.0.0");
            model.setGroupId(this.groupId);
            model.setArtifactId(this.artifactId);
            model.setVersion(this.version);
            model.setPackaging(this.packaging);
            model.setDescription(this.description);
        }

        ArtifactRepository repo = getDeploymentRepository();

        String protocol = repo.getProtocol();

        if (protocol.equals("scp")) {
            File sshFile = new File(System.getProperty("user.home"), ".ssh");

            if (!sshFile.exists()) {
                sshFile.mkdirs();
            }
        }

        Artifact artifact = this.artifactFactory.createArtifactWithClassifier(groupId, artifactId, version,
                packaging, classifier);

        // Upload the POM if requested, generating one if need be
        if (generatePom) {
            ArtifactMetadata metadata = new ProjectArtifactMetadata(artifact, generatePomFile(model));
            artifact.addMetadata(metadata);
        } else {
            ArtifactMetadata metadata = new ProjectArtifactMetadata(artifact, pomFile);
            artifact.addMetadata(metadata);
        }

        try {
            getDeployer().deploy(mainArtifact, artifact, repo, this.localRepository);

            if (sources != null || javadocs != null) {
                MavenProject project = new MavenProject(model);
                project.setArtifact(artifact);
                if (sources != null) {
                    //we have to do it this way because of classloading issues.
                    this.projectHelper.attachArtifact(project, artifact.getType(), "sources", sources);
                    getDeployer().deploy(sources, (Artifact) project.getAttachedArtifacts().get(0), repo,
                            this.localRepository);
                }

                if (javadocs != null) {
                    //we have to do it this way because of classloading issues.
                    this.projectHelper.attachArtifact(project, artifact.getType(), "javadoc", javadocs);
                    getDeployer().deploy(javadocs, (Artifact) project.getAttachedArtifacts().get(0), repo,
                            this.localRepository);
                }
            }
        } catch (ArtifactDeploymentException e) {
            throw new MojoExecutionException(e.getMessage(), e);
        }
    }

    public ArtifactDeployer getDeployer() {
        return deployer;
    }

    //
    private ArtifactRepository getDeploymentRepository() throws MojoExecutionException, MojoFailureException {
        if (deploymentRepository == null && altDeploymentRepository == null) {
            String msg = "Deployment failed: repository element was not specified in the pom inside"
                    + " distributionManagement element or in -DaltDeploymentRepository=id::layout::url parameter";

            throw new MojoExecutionException(msg);
        }

        ArtifactRepository repo = null;

        if (altDeploymentRepository != null) {
            getLog().info("Using alternate deployment repository " + altDeploymentRepository);

            Matcher matcher = ALT_REPO_SYNTAX_PATTERN.matcher(altDeploymentRepository);

            if (!matcher.matches()) {
                throw new MojoFailureException(altDeploymentRepository, "Invalid syntax for repository.",
                        "Invalid syntax for alternative repository. Use \"id::layout::url\".");
            } else {
                String id = matcher.group(1).trim();
                String layout = matcher.group(2).trim();
                String url = matcher.group(3).trim();

                ArtifactRepositoryLayout repoLayout;
                try {
                    repoLayout = (ArtifactRepositoryLayout) container.lookup(ArtifactRepositoryLayout.ROLE, layout);
                } catch (ComponentLookupException e) {
                    throw new MojoExecutionException("Cannot find repository layout: " + layout, e);
                }

                repo = new DefaultArtifactRepository(id, url, repoLayout);
            }
        }

        if (repo == null) {
            repo = deploymentRepository;
        }

        return repo;
    }

    public void contextualize(Context context) throws ContextException {
        this.container = (PlexusContainer) context.get(PlexusConstants.PLEXUS_KEY);
    }

    /**
     * Process the supplied pomFile to get groupId, artifactId, version, and packaging
     *
     * @throws NullPointerException if model is <code>null</code>
     */
    private void processModel(Model model) {
        Parent parent = model.getParent();

        if (this.groupId == null) {
            if (parent != null && parent.getGroupId() != null) {
                this.groupId = parent.getGroupId();
            }
            if (model.getGroupId() != null) {
                this.groupId = model.getGroupId();
            }
        }
        if (this.artifactId == null && model.getArtifactId() != null) {
            this.artifactId = model.getArtifactId();
        }
        if (this.version == null && model.getVersion() != null) {
            this.version = model.getVersion();
        }
        if (this.packaging == null && model.getPackaging() != null) {
            this.packaging = model.getPackaging();
        }
    }

    protected Model readModel(File pomFile) throws MojoExecutionException {

        if (!pomFile.exists()) {
            throw new MojoExecutionException("Specified pomFile does not exist");
        }

        Reader reader = null;
        try {
            reader = new FileReader(pomFile);
            MavenXpp3Reader modelReader = new MavenXpp3Reader();
            return modelReader.read(reader);
        } catch (FileNotFoundException e) {
            throw new MojoExecutionException("Error reading specified POM file: " + e.getMessage(), e);
        } catch (IOException e) {
            throw new MojoExecutionException("Error reading specified POM file: " + e.getMessage(), e);
        } catch (XmlPullParserException e) {
            throw new MojoExecutionException("Error reading specified POM file: " + e.getMessage(), e);
        } finally {
            IOUtil.close(reader);
        }
    }

    private File generatePomFile(Model model) throws MojoExecutionException {
        FileWriter fw = null;
        try {
            File tempFile = File.createTempFile("mvninstall", ".pom");
            tempFile.deleteOnExit();

            fw = new FileWriter(tempFile);
            new MavenXpp3Writer().write(fw, model);

            return tempFile;
        } catch (IOException e) {
            throw new MojoExecutionException("Error writing temporary pom file: " + e.getMessage(), e);
        } finally {
            IOUtil.close(fw);
        }
    }

}