Question

I would like to overlay another person's project, using customizations of specific files (ie one file would use a different controller, or display something in one way, or have different processes). We have been using an overlay that takes all of the files I have in my repository, and overlaying all of the files on top of their files so that my smaller set of customizations still act like the larger project should. We have accomplished it like this so far, but it plays havoc on the IDE. Is there a better way? I tried using maven-builder-helper-plugin but it gave me duplicate classes on the java files I had overriden.

<build>
   <sourceDirectory>target/overlay</sourceDirectory>
      <resources>
        <resource>
          <directory>target/overlay</directory>
          <filtering>false</filtering>
          <excludes>
            <exclude>**/*.java</exclude>
          </excludes>
        </resource>
      </resources>
      <plugins>
          <plugin>
            <artifactId>maven-antrun-plugin</artifactId>
            <executions>
              <execution>
                <phase>generate-sources</phase>
                <configuration>
                <tasks>
                    <copy todir="target/overlay" overwrite="true">
                        <fileset dir="src/main/java">
                        </fileset>
                        <fileset dir="src/main/resources">
                        </fileset>
                    </copy>
                </tasks>
                </configuration>
                    <goals>
                        <goal>run</goal>
                    </goals>
                </execution>
            </executions>
        </plugin>
        <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-dependency-plugin</artifactId>
            <executions>
                <execution>
                    <id>unpack</id>
                    <phase>initialize</phase>
                    <goals>
                        <goal>unpack</goal>
                    </goals>
                    <configuration>
                        <artifactItems>
                            <artifactItem>
                                <groupId>com.sample.service</groupId>
                                <artifactId>sampleService</artifactId>  
                                <classifier>sources</classifier>
                                <type>jar</type>
                                <overWrite>true</overWrite>
                                <outputDirectory>target/overlay</outputDirectory>
                            </artifactItem>
                        </artifactItems>
                    </configuration>
                </execution>
            </executions>
        </plugin>
    </plugins>
</build>

I should note that I'm absolutely fine with using a different direction than this one. I just couldn't figure out a better way to include all of the resource & source files that are needed from them to keep the project running properly. This is for a module that is a part of a web app. The module that is being built and the module it is overlaying are both jar's

Was it helpful?

Solution 2

So, I figured out a solution that allows me overlay the artifact without messing around with the source directory. Instead of slapping all of the files I want to overlay on top of the artifact files, I realized a simpler way would be to expand the artifact, remove the duplicate classes/resources, and use it as an additional source. I created my own plugin that takes as many 'source' directories as I want and it filters them in the order loaded.

<build>
    <plugins>
        <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-dependency-plugin</artifactId>
            <executions>
                <execution>
                    <id>unpack</id>
                    <phase>initialize</phase>
                    <goals>
                        <goal>unpack</goal>
                    </goals>
                    <configuration>
                        <artifactItems>
                            <artifactItem>
                                <groupId>com.sample.service</groupId>
                                <artifactId>sampleService</artifactId>  
                                <classifier>sources</classifier>
                                <type>jar</type>
                                <overWrite>true</overWrite>
                                <outputDirectory>${additional-source-folder}</outputDirectory>
                            </artifactItem>
                        </artifactItems>
                    </configuration>
                </execution>
            </executions>
        </plugin>
        <plugin>
            <groupId>mn-stateadvantage</groupId>
            <artifactId>duplicateSourceRemover-maven-plugin</artifactId>
            <version>1.0-SNAPSHOT</version>
            <executions>
                <execution>
                    <goals>
                        <goal>removeDuplicates</goal>
                    </goals>
                    <phase>generate-sources</phase>
                    <configuration>
                        <sourceDirectories>
                            <param>src/main</param>
                            <param>${additional-source-folder}</param>
                        </sourceDirectories>
                    </configuration>
                </execution>
            </executions>
        </plugin>
        <plugin>
            <groupId>org.codehaus.mojo</groupId>
            <artifactId>build-helper-maven-plugin</artifactId>
            <version>1.8</version>
            <executions>
                <execution>
                    <id>add-source</id>
                    <phase>generate-resources</phase>
                    <goals>
                        <goal>add-source</goal>
                    </goals>
                    <configuration>
                        <sources>
                            <source>${additional-source-folder}</source>
                        </sources>
                    </configuration>
                </execution>
                <execution>
                    <id>add-resource</id>
                    <phase>generate-resources</phase>
                    <goals>
                        <goal>add-resource</goal>
                    </goals>
                    <configuration>
                        <resources>
                            <resource>
                                <directory>${additional-source-folder}</directory>
                                <excludes>
                                    <exclude>**/*.java</exclude>
                                </excludes>
                            </resource>
                        </resources>
                    </configuration>
                </execution>
            </executions>
        </plugin>
    </plugins>
</build>

OTHER TIPS

We do this using the maven war overlay feature (read about it here). To do this we simply have a dependency from our web client module onto a war type <type>war</type>, and override what we need to in our module. Maven will take the contents of the dependent war and use its files to provide content for our web client, but if there is a clash on filename it'll take the file from our web client, not from the dependent jar. It's as if it takes the dependent jar and overlays our client on top of it to produce a new war. We do this very simply, without any need for ant run -- in years of using maven I have never had to resort to antrun (I consider it an antipattern).

You mention in the comments that you have a separate problem dealing with some xml files. This can be handled by the resource plugin, if you tell it which directory your files are in, and give it a wildcard to define the files you need copying.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top