mojohaus / rpm-maven-plugin

http://www.mojohaus.org/rpm-maven-plugin/
Other
56 stars 48 forks source link

mappings not additive bewteen execution based config and plugin based config #28

Open sc1478 opened 8 years ago

sc1478 commented 8 years ago

Mavin plugin configurations can be defined at both the execution and plugin level. These are supposed to be and usually are additive between configurations defined in an execution and configurations defined in a plugin. That is the configuration of a plugin as it executes an execution is to add the configuration defined in the execution to that defined in the plugin. I believe that an execution-defined configuration would overwrite a plugin-defined configuration of the same name.

This presents a problem with mappings elements. The rpm-maven-plugin's mapping configurations follow this rule exactly, with unfortunate consequences. Suppose you want to run two executions of the plugin, each producing different rpms. Further suppose that some of the files are common between the two executions and others are not. You might want to define some mappings in the plugin configuration (the common files) and others in the execution configurations (the execution-specific mappings). This doesn't work. Instead the execution-specific mappings override the plugin-specified mappings which are simply not included in the rpm. Thus, in such a pom, the common mappings must be redundantly repeated in each execution.

It would be nicer if there was a mechanism whereby the two levels of mappings could be combined.

khmarbaise commented 8 years ago

you know the things like this:

<configuration>
  <items combine.children="append">
    <!-- combine.children="merge" is the default -->
    <item>child-1</item>
  </items>
  <properties combine.self="override">
    <!-- combine.self="merge" is the default -->
    <childKey>child</childKey>
  </properties>
</configuration>
sc1478 commented 8 years ago

Thanks, Karl. I see that but I'm not sure how to apply it in the case of the rpm-maven-plugin's <mappings> elements. This whole document seems to pertain to parent/child pom's rather than plugin/execution configurations and I'm having difficulty translating.

khmarbaise commented 8 years ago

The combine etc. will also work from plugin configuration to execution level...Can you show what you have so far and explain what the problem is?

sc1478 commented 8 years ago

In the beginning we had

<plugin>
    <groupId>org.codehaus.mojo</groupId>
    <artifactId>rpm-maven-plugin</artifactId>
    <version>2.1.4</version>
    <executions>
        <execution>
            <id>attach-rpm</id>
            <goals>
                <goal>attached-rpm</goal>
            </goals>
        </execution>
    </executions>
    <configuration>
         ...
          <mappings>
             <mapping>
                 <directory>${tomcat.deploy.dir}</directory>
                 <sources>
                     <source>
                         <location>${project.build.directory}/${project.artifactId}.war</location>
                     </source>
                 </sources>
                 <directoryIncluded>false</directoryIncluded>
             </mapping>
             <mapping>
                 <directory>${conf.dir}</directory>
                 <sources>
                     <source>
                         <location>${project.basedir}/conf/log4j2.xml</location>
                     </source>
                 </sources>
                 <directoryIncluded>false</directoryIncluded>
             </mapping>
     </configuration>
 </plugin>

One rpm, all configs at the plugin level, not at the execution level. Everything works fine.

But then we needed to build two rpms. The first (war) mapping had a different destination directory than the second (log4j config) mapping. So the thought was to put the mapping that varied at the execution level and the other at the plugin level:

<plugin>
    <groupId>org.codehaus.mojo</groupId>
    <artifactId>rpm-maven-plugin</artifactId>
    <version>2.1.4</version>
    <executions>
        <execution>
            <id>attach-is-rpm</id>
            <goals>
                <goal>attached-rpm</goal>
            </goals>
            <configuration>
                ...
                 <mappings>
                    <mapping>
                        <directory>${tomcat.deploy.dir.is}</directory>
                        <sources>
                            <source>
                                <location>${project.build.directory}/${project.artifactId}.war</location>
                            </source>
                        </sources>
                        <directoryIncluded>false</directoryIncluded>
                    </mapping>
                </mappings>
            </configuration>
        </execution>
        <execution>
            <id>attach-rs-rpm</id>
            <goals>
                <goal>attached-rpm</goal>
            </goals>
            <configuration>
                ...
                <mappings>
                    <mapping>
                        <directory>${tomcat.deploy.dir.rs}</directory>
                        <sources>
                            <source>
                                <location>${project.build.directory}/${project.artifactId}.war</location>
                            </source>
                        </sources>
                        <directoryIncluded>false</directoryIncluded>
                    </mapping>
                 </mappings>
            </configuration>
        </execution>
    </executions>
    <configuration>
        ...
        <mappings>
            <mapping>
                <directory>${conf.dir}</directory>
                <sources>
                     <source>
                        <location>${project.basedir}/conf/log4j2.xml</location>
                    </source>
                </sources>
                <directoryIncluded>false</directoryIncluded>
            </mapping>
         </mappings>
    </configuration>
</plugin>

This seemed to work, but closer inspection revealed that the log4j2.xml file was not being placed in the spec file and not being installed. The execution level mappings were simply overriding the plugin level mappings, not adding to them.

This left us no choice but to adopt the suboptimal solution of reuse-by-copying in order to deploy everything:

<plugin>
    <groupId>org.codehaus.mojo</groupId>
    <artifactId>rpm-maven-plugin</artifactId>
    <version>2.1.4</version>
    <executions>
        <execution>
            <id>attach-is-rpm</id>
            <goals>
                <goal>attached-rpm</goal>
            </goals>
            <configuration>
                ...
                 <mappings>
                    <mapping>
                        <directory>${tomcat.deploy.dir.is}</directory>
                        <sources>
                            <source>
                                <location>${project.build.directory}/${project.artifactId}.war</location>
                            </source>
                        </sources>
                        <directoryIncluded>false</directoryIncluded>
                    </mapping>
                    <mapping>
                        <directory>${conf.dir}</directory>
                        <sources>
                            <source>
                                <location>${project.basedir}/conf/log4j2.xml</location>
                            </source>
                        </sources>
                        <directoryIncluded>false</directoryIncluded>
                    </mapping>
                </mappings>
            </configuration>
        </execution>
        <execution>
            <id>attach-rs-rpm</id>
            <goals>
                <goal>attached-rpm</goal>
            </goals>
            <configuration>
                ...
                <mappings>
                    <mapping>
                        <directory>${tomcat.deploy.dir.rs}</directory>
                        <sources>
                            <source>
                                <location>${project.build.directory}/${project.artifactId}.war</location>
                            </source>
                        </sources>
                        <directoryIncluded>false</directoryIncluded>
                    </mapping>
                    <mapping>
                        <directory>${conf.dir}</directory>
                        <sources>
                             <source>
                                <location>${project.basedir}/conf/log4j2.xml</location>
                            </source>
                        </sources>
                        <directoryIncluded>false</directoryIncluded>
                    </mapping>
                 </mappings>
            </configuration>
        </execution>
    </executions>
    <configuration>
        ...
    </configuration>
</plugin>

The optimal solution would be the second example. So, my question is, how do we apply the "combine" syntax to these mappings to achieve that?

Thanks.

JayBur commented 7 years ago

Hi @sc1478, did you find a more optimal solution in the end? Any chance the combine syntax worked for you? I'm currently running into the same issue: Any mapping specified inside an execution will override the plugin configuration's mapping. Preferably I would have it extend the plugin configuration's mapping instead.

sc1478 commented 7 years ago

Yes. My solution was to stop using Maven for building RPMs and start using Gradle. The Gradle syntax is much cleaner and more intuitive and easily builds RPMs without the fuss. Really, Gradle can do almost everything Maven can do, and our shop is all Gradle now, using Maven only rarely.

JayBur commented 7 years ago

Thanks, cheers for responding!

I've tried Gradle with some smaller projects and really love it. I'll probably just use the duplicate workaround here for now, but chances are quite high I'll convert the Maven things we have over to Gradle eventually too.