Commits

Samuel Le Berrigaud committed b50cd1c

First cut.
There is a goal to create a report, validate a report.

Comments (0)

Files changed (5)

+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+         xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
+    <modelVersion>4.0.0</modelVersion>
+
+    <groupId>com.atlassian.maven.plugins</groupId>
+    <artifactId>atlassian-maven-plugin</artifactId>
+    <version>1.0-SNAPSHOT</version>
+    <packaging>maven-plugin</packaging>
+    <name>Atlassian Maven Plugin</name>
+
+    <dependencies>
+        <dependency>
+            <groupId>org.codehaus.groovy.maven</groupId>
+            <artifactId>gmaven-mojo</artifactId>
+            <version>${gmaven.version}</version>
+        </dependency>
+        <dependency>
+            <groupId>commons-lang</groupId>
+            <artifactId>commons-lang</artifactId>
+            <version>2.4</version>
+        </dependency>
+        <dependency>
+            <groupId>commons-collections</groupId>
+            <artifactId>commons-collections</artifactId>
+            <version>3.2.1</version>
+        </dependency>
+    </dependencies>
+
+    <build>
+        <plugins>
+            <plugin>
+                <groupId>org.codehaus.groovy.maven</groupId>
+                <artifactId>gmaven-plugin</artifactId>
+                <version>${gmaven.version}</version>
+                <executions>
+                    <execution>
+                        <goals>
+                            <goal>generateStubs</goal>
+                            <goal>compile</goal>
+                            <goal>generateTestStubs</goal>
+                            <goal>testCompile</goal>
+                        </goals>
+                    </execution>
+                </executions>
+            </plugin>
+        </plugins>
+    </build>
+    <properties>
+        <gmaven.version>1.0-rc-4</gmaven.version>
+    </properties>
+</project>

src/main/groovy/com/atlassian/maven/plugins/AbstractMapMojo.groovy

+package com.atlassian.maven.plugins
+
+import com.atlassian.maven.plugins.DependencyReportLine
+import org.apache.maven.project.MavenProject
+import org.codehaus.groovy.maven.mojo.GroovyMojo
+
+abstract class AbstractMapMojo extends GroovyMojo
+{
+    static final String UKNOWN_MD5 = '?'
+
+    /**
+     * The Maven Project
+     *
+     * @parameter expression="${project}"
+     * @required
+     * @readonly
+     */
+    MavenProject project
+
+    String reportFileName = 'dependencies.txt'
+
+    SortedSet<DependencyReportLine> reportLines()
+    {
+        final SortedSet report = new TreeSet()
+        project.dependencyArtifacts.each { report.add(DependencyReportLine.from(it, md5(it))) }
+        return report
+    }
+
+    String md5(artifact)
+    {
+        if (!artifact.file?.exists())
+        {
+            println "File for $artifact doesn't exists"
+            return UKNOWN_MD5
+        }
+        else
+        {
+            def checksumName = "${artifact.file.name}.md5"
+            ant.checksum(file: artifact.file, property: checksumName)
+            return ant.project.properties[checksumName]
+        }
+    }
+
+    void writeReportToFile(String fileName, Set report)
+    {
+        new File(fileName).withWriter {writer -> report.each { writer << "$it\n" } }
+    }
+}

src/main/groovy/com/atlassian/maven/plugins/DependencyReportLine.groovy

+package com.atlassian.maven.plugins
+
+import org.apache.commons.lang.builder.EqualsBuilder
+import org.apache.maven.artifact.Artifact
+import org.apache.maven.plugin.MojoFailureException
+import org.apache.commons.lang.builder.HashCodeBuilder
+
+public class DependencyReportLine implements Comparable
+{
+    String groupId
+    String artifactId
+    String version
+    String md5
+
+    String toString()
+    {
+        "$groupId:$artifactId:$version|$md5"
+    }
+
+    public int compareTo(Object line)
+    {
+        if (!line || !(line instanceof DependencyReportLine)) return -1
+        int g = groupId.compareTo(line.groupId)
+        if (g) return g
+        int a = artifactId.compareTo(line.artifactId)
+        if (a) return a
+        int v = version.compareTo(line.version)
+        if (v) return v
+        int m = md5.compareTo(line.md5)
+        return m
+    }
+
+    public boolean equals(Object obj)
+    {
+        if (!obj) return false
+        if (obj == this) return true
+        if (obj.class != this.class) return false
+
+        new EqualsBuilder()
+                .append(groupId, obj.groupId)
+                .append(artifactId, obj.artifactId)
+                .append(version, obj.version)
+                .append(md5, obj.md5)
+                .isEquals()
+    }
+
+    public int hashCode()
+    {
+        new HashCodeBuilder()
+            .append(groupId)
+            .append(artifactId)
+            .append(version)
+            .append(md5)
+            .toHashCode()
+    }
+
+
+
+
+    static DependencyReportLine from(Artifact artifact, String md5)
+    {
+        new DependencyReportLine(
+                groupId: artifact.groupId,
+                artifactId: artifact.artifactId,
+                version: artifact.version,
+                md5: md5)
+    }
+
+    static DependencyReportLine from(String line)
+    {
+        def lineMatcher = line =~ /[^\|]+/
+        if (!lineMatcher)
+        {
+            throw new MojoFailureException("Could not parse line '$line'")
+        }
+        def artifactMatcher = lineMatcher[0] =~ /[^\:]+/
+        if (!artifactMatcher)
+        {
+            throw new MojoFailureException("Could not parse artifact '${lineMatcher[0]}'")
+        }
+
+        new DependencyReportLine(
+                groupId: artifactMatcher[0],
+                artifactId: artifactMatcher[1],
+                version: artifactMatcher[2],
+                md5: lineMatcher[1])
+    }
+}

src/main/groovy/com/atlassian/maven/plugins/GenerateDependenciesReportMojo.groovy

+package com.atlassian.maven.plugins
+
+import com.atlassian.maven.plugins.AbstractMapMojo
+
+/**
+ *
+ * @requiresDependencyResolution test
+ * @goal dependencies-report
+ */
+class GenerateDependenciesReportMojo extends AbstractMapMojo
+{
+    void execute()
+    {
+        writeReportToFile(reportFileName, reportLines())
+    }
+}

src/main/groovy/com/atlassian/maven/plugins/ValidateDepdendenciesMojo.groovy

+package com.atlassian.maven.plugins
+
+import com.atlassian.maven.plugins.AbstractMapMojo
+import com.atlassian.maven.plugins.DependencyReportLine
+import org.apache.commons.collections.CollectionUtils
+import org.apache.maven.plugin.MojoFailureException
+
+/**
+ * @requiresDependencyResolution test
+ * @goal validate-dependencies
+ * @phase validate
+ */
+class ValidateDepdendenciesMojo extends AbstractMapMojo
+{
+    void execute()
+    {
+        final File report = new File(reportFileName)
+        if (!report?.exists())
+        {
+            log.warn("$report.absolutePath doesn't exists, won't validate dependencies")
+            return
+        }
+
+        def fileReport = report.readLines().collect { DependencyReportLine.from(it) }
+        def runtimeReport = reportLines()
+
+        def newDependencies = CollectionUtils.subtract(runtimeReport, fileReport)
+        def removedDependencies = CollectionUtils.subtract(fileReport, runtimeReport)
+
+        if (!newDependencies && !removedDependencies)
+        {
+            log.debug "Calculated dependencies are the same as in the report"
+            return
+        }
+
+        log.error "The following dependencies are not present in the report:"
+        newDependencies.each { log.error "\t$it" }
+        log.error "The following dependencies are present in the report but no longer calculated:"
+        removedDependencies.each { log.error "\t$it" }
+
+        String fileName = "${reportFileName}.tmp"
+        writeReportToFile(fileName, runtimeReport);
+
+        throw new MojoFailureException("The dependency report and your resolved dependencies are not in sync. An updated report has been written to <${new File(fileName).absolutePath}>")
+    }
+}