Chris Beach
Chris Beach

Reputation: 4392

In Maven how can I generate a classpath file that includes the artifact I'm building?

I'm using maven-dependency-plugin:build-classpath to build a classpath file. To support a legacy deployment, I need this file to include the artifact I'm building, in addition to the usual set of dependency JARs.

Current classpath file:

dep1.jar:dep2.jar

Classpath file I want:

project-I'm-building.jar:dep1.jar:dep2.jar

I'm contemplating using maven-antrun-plugin to generate a file containing a classpath to the artifact JAR, then using the option of build-classpath to add the dependency JARs. This seems inelegant though. Is there a better way?

Upvotes: 1

Views: 2372

Answers (1)

Chris Beach
Chris Beach

Reputation: 4392

This works for me:

<plugin>
    <groupId>org.codehaus.gmaven</groupId>
    <artifactId>gmaven-plugin</artifactId>
    <executions>
        <execution>
            <id>build-classpath-files-for-artifact-and-direct-aspect-dependencies</id>
            <phase>generate-sources</phase>
            <goals>
                <goal>execute</goal>
            </goals>
            <configuration>
                <properties>
                    <outputPath>${path.classpath}</outputPath>
                    <prefix>${prefix.classpath}</prefix>
                </properties>
                <source><![CDATA[
// Function for keying artifacts (groupId:artifactId)
def artId(art) {"${art.groupId}:${art.artifactId}".toString()}                                

if (project.packaging != "tgz") {
    log.info "Skipping generation of classpath file(s) as this isn't a tgz project"
} else {
    new File(project.properties.outputPath).mkdirs()

    // Map artifact keys to versions (as resolved by this -dist project)
    def artVers = project.runtimeArtifacts.collectEntries{[(artId(it)): it.version]}

    // Get global Maven ProjectBuilder, used for resolving artifacts to projects
    def builder = session.lookup('org.apache.maven.project.ProjectBuilder');

    // Build the classpath files, including both the dependencies plus the project artifact itself
    (project.dependencyArtifacts.findAll{dep -> dep.type == 'jar' && dep.groupId == project.groupId} + project.artifact).each{art -> 
        def req = session.projectBuildingRequest.setResolveDependencies(true)
        def depProj = builder.build(art, req).getProject();

        // Only include artifacts of type jar, and for which a resolved version exists (this excludes -dist artifacts) 
        def classpath = ([art] + depProj.runtimeArtifacts).findAll{a -> a.type == 'jar' && artVers[artId(a)] != null}.collect{
            "${project.properties.prefix}/${it.artifactId}-${artVers[artId(it)]}.jar" 
        }                                   
        def file = new File(project.properties.outputPath, art.artifactId + ".classpath")
        log.info "Writing classpath with ${classpath.size} artifact(s) to " + file
        file.write(classpath.join(":"))
    }
}                                                                
                    ]]></source>
            </configuration>
        </execution>
    </executions>
</plugin>

Upvotes: 1

Related Questions