/* * Copyright 2005 The Apache Software Foundation. * * 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 org.codehaus.mojo.jardiff; import java.io.File; import java.util.Locale; import org.apache.maven.artifact.Artifact; import org.apache.maven.artifact.factory.ArtifactFactory; import org.apache.maven.artifact.handler.ArtifactHandler; import org.apache.maven.artifact.repository.ArtifactRepository; import org.apache.maven.artifact.resolver.ArtifactNotFoundException; import org.apache.maven.artifact.resolver.ArtifactResolutionException; import org.apache.maven.artifact.resolver.ArtifactResolver; import org.apache.maven.doxia.sink.Sink; import org.apache.maven.doxia.siterenderer.Renderer; import org.apache.maven.project.MavenProject; import org.apache.maven.reporting.AbstractMavenReport; import org.apache.maven.reporting.MavenReportException; import org.osjava.jardiff.DiffException; import org.osjava.jardiff.JarDiff; import org.osjava.jardiff.SimpleDiffCriteria; /** * This plugin creates a jardiff report. * @goal jardiff * @description * */ public class JardiffReport extends AbstractMavenReport { /** * @parameter expression="${project}" * @required * @readonly */ private MavenProject project; /** * @component */ private Renderer siteRenderer; /** * @parameter expression="${project.reporting.outputDirectory}/jardiff" * @required * @readonly */ private File outputDirectory; /** * Artifact resolver, needed to download source jars. * * @component role="org.apache.maven.artifact.resolver.ArtifactResolver" * @required * @readonly */ private ArtifactResolver artifactResolver; /** * Artifact factory, needed to download source jars. * * @component role="org.apache.maven.artifact.factory.ArtifactFactory" * @required * @readonly */ private ArtifactFactory artifactFactory; /** * Location of the local repository. * @parameter expression="${localRepository}" * @readonly * @required */ private ArtifactRepository artifactRepository; /** * Location of the local repository. * @parameter */ private ArtifactConfiguration[] artifacts; /** * Comparison method * @parameter default-value="incremental" */ private String comparison; /** * List of Remote Repositories used by the resolver * @parameter expression="${project.remoteArtifactRepositories}" * @readonly * @required */ private java.util.List remoteArtifactRepositories; public void executeReport( Locale locale ) throws MavenReportException { if ( !outputDirectory.exists() && !outputDirectory.mkdirs()) { throw new MavenReportException( "Folder " + outputDirectory + " could not be created." ); } if (artifacts == null || artifacts.length == 0) { // provide default version throw new MavenReportException("nothing to do"); } final Artifact[][] comparisons; if ("incremental".equalsIgnoreCase(comparison)) { comparisons = getIncrementalComparisons(); } else if ("individual".equalsIgnoreCase(comparison)) { comparisons = getIndividualComparisons(); } else { throw new MavenReportException("unknown comparison method " + comparison); } final Sink sink = getSink(); sink.head(); sink.title(); sink.text(getName(locale)); sink.title_(); sink.head_(); sink.body(); for (int i = 0; i < comparisons.length; i++) { final Artifact oldArtifact = comparisons[i][0]; final Artifact newArtifact = comparisons[i][1]; getLog().info("diff " + oldArtifact + " vs " + newArtifact); resolveArtifact(oldArtifact); resolveArtifact(newArtifact); final JarDiff diff = new JarDiff(); diff.setOldVersion(oldArtifact.getVersion()); diff.setNewVersion(newArtifact.getVersion()); try { diff.loadOldClasses(oldArtifact.getFile()); diff.loadNewClasses(newArtifact.getFile()); diff.diff(new SinkDiffHandler(getSink()), new SimpleDiffCriteria()); } catch (DiffException e) { throw new MavenReportException("" ,e); } } sink.body_(); sink.flush(); sink.close(); } private String getOrDefault( String value, String def ) { if (value == null) { return def; } return value; } private Artifact getArtifact( ArtifactConfiguration config ) { final Artifact projectArtifact = project.getArtifact(); final Artifact artifact = artifactFactory.createArtifact( getOrDefault(config.groupId, projectArtifact.getGroupId()), getOrDefault(config.artifactId, projectArtifact.getArtifactId()), getOrDefault(config.version, projectArtifact.getVersion()), null, getOrDefault(config.type, projectArtifact.getType()) ); return artifact; } private void resolveArtifact( Artifact artifact ) throws MavenReportException { try { artifactResolver.resolve( artifact, remoteArtifactRepositories, artifactRepository ); } catch ( ArtifactResolutionException e ) { throw new MavenReportException( "Unable to resolve artifact.", e ); } catch ( ArtifactNotFoundException e ) { throw new MavenReportException( "Unable to find artifact.", e ); } if (artifact.getFile() == null || !artifact.getFile().exists()) { throw new MavenReportException( "Unable to find artifact file " + artifact); } } private Artifact[][] getIncrementalComparisons() { final Artifact[][] comparisons = new Artifact[artifacts.length][2]; comparisons[0][0] = getArtifact(artifacts[0]); comparisons[0][1] = project.getArtifact(); for (int i = 1; i < artifacts.length; i++) { comparisons[i][0] = getArtifact(artifacts[i]); comparisons[i][1] = comparisons[i-1][0]; } return comparisons; } private Artifact[][] getIndividualComparisons() { final Artifact[][] comparisons = new Artifact[artifacts.length][2]; for (int i = 0; i < artifacts.length; i++) { comparisons[i][0] = project.getArtifact(); comparisons[i][1] = getArtifact(artifacts[i]); } return comparisons; } public String getOutputName() { return "jardiff"; } protected String getOutputDirectory() { return this.outputDirectory.getAbsoluteFile().toString(); } protected Renderer getSiteRenderer() { return this.siteRenderer; } protected MavenProject getProject() { return this.project; } public String getName( Locale locale ) { return "Jardiff Report"; } public String getDescription( Locale locale ) { return ""; } public boolean canGenerateReport() { final ArtifactHandler artifactHandler = this.project.getArtifact().getArtifactHandler(); return "java".equals( artifactHandler.getLanguage() ); } }