Maven multi-module project with license plugin

11,497

Solution 1

Try to use an absolute path by using

<header>${basedir}/NOTICE</header>

If this doesn't work, try to set a property to and in the parent module's basedir and use it:

<header>${main.basedir}/NOTICE</header>

A third option is setting a property at runtime:

mvn clean install -Dmain.basedir=path/to/main/basedir

Edit:

Ok, a whole other option is to execute the maven-dependency-plugin before your license plugin. But you have to make sure the parent attaches the NOTICE (with maven-assembly-plugin plugin)

<plugin>
         <groupId>org.apache.maven.plugins</groupId>
         <artifactId>maven-dependency-plugin</artifactId>
         <version>2.6</version>
         <executions>
           <execution>
             <id>unpack-parent</id>
             <phase>verify</phase>
             <goals>
               <goal>unpack</goal>
             </goals>
             <configuration>
               <artifactItems>
                 <artifactItem>
                   <groupId>parent</groupId>
                   <artifactId>parent</artifactId>
                   <version>parent</version>
                   <type>pom</type>
                   <overWrite>false</overWrite>
                   <outputDirectory>${project.build.directory}/license</outputDirectory>
                   <includes>NOTICE</includes>
                 </artifactItem>
               </artifactItems>
             </configuration>
           </execution>
         </executions>
       </plugin>

The header changes then in:

<header>${project.build.directory}/license/NOTICE</header>

Edit2:

I came across the find-maven-plugin. I think this could work:

<plugin>
    <groupId>com.github.goldin</groupId>
    <artifactId>find-maven-plugin</artifactId>
    <version>0.2.5</version>
    <executions>
        <execution>
            <id>find-notice-file</id>
            <goals>
                <goal>find</goal>
            </goals>
            <phase>validate</phase>
            <configuration>
                <propertyName>notice.file</propertyName>
                <file>NOTICE</file>
            </configuration>
        </execution>
    </executions>
</plugin>

Solution 2

There's actually a much easier way to do this. Just set the aggregate tag to true in the configuration. Here's the full maven-license-plugin definition:

<plugin>
    <groupId>com.mycila.maven-license-plugin</groupId>
    <artifactId>maven-license-plugin</artifactId>
    <version>1.10.b1</version>
    <configuration>
        <header>etc/header.txt</header>
        <aggregate>true</aggregate>
        <includes>
            <include>**/*.java</include>
        </includes>
    </configuration>
</plugin>

You then just need to have a file called header.txt in etc/header.txt in the parent root directory.

Share:
11,497
John Ericksen
Author by

John Ericksen

Java developer and Android fanatic. Author of the following: Transfuse - A compile time dependency injection and integration library for Google Android. Parceler - A code generation library that generates the Android Parcelable boilerplate source code. Asciidoclet - A Javadoc Doclet based on Asciidoctor that lets you write Javadoc in the AsciiDoc syntax.

Updated on October 17, 2022

Comments

  • John Ericksen
    John Ericksen over 1 year

    I have a multi-module project in which I'm trying to set up the license plugin to manage all the licenses. Here's the project setup:

    ─── transfuse-project
        ├── examples
        │   ├── helloAndroid
        │   │   ├── pom.xml
        │   │   ├── ...
        │   ├── integrationTest
        │   │   ├── pom.xml
        │   │   ├── ...
        │   ├── pom.xml
        │   └── ...
        ├── transfuse
        │   ├── pom.xml
        │   ├── ...
        ├── transfuse-api
        │   ├── pom.xml
        │   ├── ...
        ├── NOTICE
        └── pom.xml
    

    Each pom.xml inherits from the transfuse-project pom.xml. In the project pom.xml I have set up the license plugin to apply the NOTICE to the relevant files:

            <plugin>
                <groupId>com.mycila.maven-license-plugin</groupId>
                <artifactId>maven-license-plugin</artifactId>
                <version>1.9.0</version>
                <configuration>
                    <header>NOTICE</header>
                    <includes>
                        <include>**/*.java</include>
                        <include>**/*.xml</include>
                    </includes>
                    <excludes>
                        <exclude>**/.*/**</exclude>
                        <exclude>target/**</exclude>
                        <exclude>**/AndroidManifest.xml</exclude>
                    </excludes>
                    <properties>
                        <year>2013</year>
                        <name>John Ericksen</name>
                    </properties>
                    <useDefaultExcludes>true</useDefaultExcludes>
                    <strictCheck>true</strictCheck>
                </configuration>
                <executions>
                    <execution>
                        <id>check-headers</id>
                        <phase>verify</phase>
                        <goals>
                            <goal>check</goal>
                        </goals>
                    </execution>
                </executions>
            </plugin>
    

    This configuration works if I build directly off of the root (transfuse-project). The problem arises when I build the integrationTest example or api directly. Maven cannot find the NOTICE file I provided in the project root:

    [ERROR] Failed to execute goal com.mycila.maven-license-plugin:maven-license-plugin:1.9.0:check (check-headers) on project transfuse-api: Some files do not have the expected license header -> [Help 1]
    

    And what's worse, it finds another dependency's NOTICE file. If I run mvn license:format in a sub-module it replaces all of the module's headers with the dependency's NOTICE file.

    I believe I can add a NOTICE file within each sub-module to fix this problem and configure each sub-module pom with its own license plugin, but I would like to avoid that duplication if possible. Is there some configuration or setup that will work with my project setup?

  • John Ericksen
    John Ericksen over 11 years
    ah, I tried that as well. Building from the root works, but building any of the sub-modules fails.
  • John Ericksen
    John Ericksen over 11 years
    Spoke too soon. This: ${project.parent.parent.basedir} does not seem to reference the grand-parent when built from the root. Ideas?
  • John Ericksen
    John Ericksen over 11 years
    would I add the dependency plugin to the root or each sub-module?
  • asgoth
    asgoth over 11 years
    In the root, but the execution should be in the child poms
  • John Ericksen
    John Ericksen over 11 years
    Ugh, ran into a bug in Maven with this solution: "[ERROR] Failed to execute goal org.apache.maven.plugins:maven-dependency-plugin:2.6:unpack (unpack-parent) on project transfuse-project: Unknown archiver type: No such archiver: 'xml'."
  • John Ericksen
    John Ericksen over 11 years
    I wonder, could I host the header online and reference it via url? Seems like a huge workaround, bit may solve my relative path issues.
  • asgoth
    asgoth over 11 years
    I found a plugin which searches a file in a parent path: evgeny-goldin.com/wiki/Find-maven-plugin. I've added it to the answer
  • John Ericksen
    John Ericksen over 11 years
    Edit2 works. I like the fact that it is only defined in the parent pom. Thanks again for your diligence, check mark well earned.
  • abhiyenta
    abhiyenta over 10 years
    This works when building the parent, but not when you build an individual module by itself.