There are several ways to organize the project with Maven modules in order to do what you need. As already in the comments, you can use Filters, profiles, move specific files by profile, etc. I will use a mixed Filters and profiles in a project without any behavior, just to demonstrate this organization.
However, there is something (so far I haven’t found any) that creates container-specific Scriptor, such as jboss-web.xml
or the glassfish-web.xml
. So, since there is nothing like this, we will make the changes by modifying properties and copying specific files according to the profile chosen, using only the plugin maven-resources-plugin
and the resources
of the build itself.
I will divide the answer/suggestion into two parts:
- creation of the modules, including an EAR that will have both
war
;
- creation of profiles and Filters. Profiles will be in the module Parent, not because it has to be so, but because it is personal taste.
Then we will have the following design structure:
Below is the summary of each module, with its respective pom.xml
containing strictly what is necessary at this time. I will assume the following premises:
jar-project
will be dependent on the two projects of package
war
;
ear-project
contains the two projects of package
war
;
Parent-project:
<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/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>com.brunocesar</groupId>
<version>0.0.1-SNAPSHOT</version>
<artifactId>parent-project</artifactId>
<packaging>pom</packaging>
<build>
<finalName>${project.artifactId}</finalName>
</build>
<modules>
<module>jar-project</module>
<module>web-project-1</module>
<module>web-project-2</module>
</modules>
</project>
jar-project:
<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/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>com.brunocesar</groupId>
<artifactId>parent-project</artifactId>
<version>0.0.1-SNAPSHOT</version>
</parent>
<artifactId>jar-project</artifactId>
</project>
web-project-1:
<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/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>com.brunocesar</groupId>
<artifactId>parent-project</artifactId>
<version>0.0.1-SNAPSHOT</version>
</parent>
<artifactId>web-project-1</artifactId>
<packaging>war</packaging>
<dependencies>
<dependency>
<groupId>${project.groupId}</groupId>
<artifactId>jar-project</artifactId>
<version>${project.version}</version>
</dependency>
</dependencies>
</project>
web-project-2:
<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/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>com.brunocesar</groupId>
<artifactId>parent-project</artifactId>
<version>0.0.1-SNAPSHOT</version>
</parent>
<artifactId>web-project-2</artifactId>
<packaging>war</packaging>
<dependencies>
<dependency>
<groupId>${project.groupId}</groupId>
<artifactId>jar-project</artifactId>
<version>${project.version}</version>
</dependency>
</dependencies>
</project>
Ear-project:
<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/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>com.brunocesar</groupId>
<artifactId>parent-project</artifactId>
<version>0.0.1-SNAPSHOT</version>
</parent>
<packaging>ear</packaging>
<artifactId>ear-project</artifactId>
<build>
<finalName>${project.artifactId}</finalName>
<plugins>
<plugin>
<artifactId>maven-ear-plugin</artifactId>
<version>2.10</version>
<configuration>
<version>7</version>
<defaultLibBundleDir>lib</defaultLibBundleDir>
<outputDirectory>${project.build.directory}/dist</outputDirectory>
<modules>
<webModule>
<groupId>${project.groupId}</groupId>
<artifactId>web-project-1</artifactId>
</webModule>
<webModule>
<groupId>${project.groupId}</groupId>
<artifactId>web-project-2</artifactId>
</webModule>
</modules>
<fileNameMapping>no-version</fileNameMapping>
</configuration>
</plugin>
</plugins>
</build>
<dependencies>
<dependency>
<groupId>${project.groupId}</groupId>
<artifactId>web-project-1</artifactId>
<version>${project.version}</version>
<type>war</type>
</dependency>
<dependency>
<groupId>${project.groupId}</groupId>
<artifactId>web-project-2</artifactId>
<version>${project.version}</version>
<type>war</type>
</dependency>
</dependencies>
</project>
Now let’s go to the construction of profiles and Filters, you can use only profiles with the properties, but I use both only as exercise. As we are considering three containers we will have 3 profiles and I assume the following:
jboss-web.xml
shall be included only in the build when the profiles for jboss
;
glassfish-web.xml
shall be included only in the build when the profiles for glassfish
;
context.xml
shall be included only in the build when the profiles for tomcat
;
tomcat
is the profile pattern;
As said before, the profiles are all on pom.xml
of the grouper project, below are just the stretches of them.
Profile jboss:
<profile>
<id>jboss</id>
<properties>
<container>jboss</container>
</properties>
<build>
<resources>
<resource>
<directory>src/main/resources</directory>
<filtering>true</filtering>
<excludes>
<exclude>**/context.xml</exclude>
<exclude>**/*-web.xml</exclude>
</excludes>
</resource>
</resources>
<plugins>
<plugin>
<artifactId>maven-resources-plugin</artifactId>
<executions>
<execution>
<id>copy-resources</id>
<phase>process-resources</phase>
<goals>
<goal>copy-resources</goal>
</goals>
<configuration>
<overwrite>true</overwrite>
<outputDirectory>${project.build.directory}/${project.build.finalName}/WEB-INF/</outputDirectory>
<resources>
<resource>
<filtering>true</filtering>
<directory>${project.basedir}/src/main/resources/WEB-INF</directory>
<excludes>
<exclude>**/glassfish*</exclude>
</excludes>
</resource>
</resources>
</configuration>
</execution>
</executions>
</plugin>
</plugins>
</build>
<modules>
<module>ear-project</module>
</modules>
</profile>
Profile glassfish:
<profile>
<id>glassfish</id>
<properties>
<container>glassfish</container>
</properties>
<build>
<!-- esta é a parte que iremos dizer para o maven em quais arquivos ele deve usar as propriedades que estão nos filters -->
<resources>
<resource>
<directory>src/main/resources</directory>
<filtering>true</filtering>
<excludes>
<exclude>**/context.xml</exclude>
<exclude>**/*-web.xml</exclude>
</excludes>
</resource>
</resources>
<plugins>
<!-- usaremos este plugin para incluir os arquivos *-web.xml no lugar correto -->
<plugin>
<artifactId>maven-resources-plugin</artifactId>
<executions>
<execution>
<id>copy-resources</id>
<phase>process-resources</phase>
<goals>
<goal>copy-resources</goal>
</goals>
<configuration>
<overwrite>true</overwrite>
<outputDirectory>${project.build.directory}/${project.build.finalName}/WEB-INF/</outputDirectory>
<resources>
<resource>
<filtering>true</filtering>
<directory>${project.basedir}/src/main/resources/WEB-INF</directory>
<excludes>
<exclude>**/jboss*</exclude>
</excludes>
</resource>
</resources>
</configuration>
</execution>
</executions>
</plugin>
</plugins>
</build>
<modules>
<module>ear-project</module>
</modules>
</profile>
Profile Tomcat:
<profile>
<id>tomcat</id>
<properties>
<container>tomcat</container>
</properties>
<activation>
<activeByDefault>true</activeByDefault>
</activation>
<build>
<!-- esta é a parte que iremos dizer para o maven em quais arquivos ele deve usar as propriedades que estão nos filters -->
<resources>
<resource>
<directory>src/main/resources</directory>
<filtering>true</filtering>
<excludes>
<exclude>**/*-web.xml</exclude>
</excludes>
<includes>
<include>**/context.xml</include>
</includes>
</resource>
</resources>
</build>
</profile>
I didn’t exemplify any project with package
of the kind ejb
, but you can do this (you probably won’t use, because you’re considering Tomcat as well), ie you can package, for example, the package
jar
in the ejb
and make the deploy of it along with the EAR
, as said at the beginning, there are N ways to organize the project.
The part of build of pom.xml
should also be changed to something like this:
<build>
<!-- a construção terá um nome específico por container (ex.: web-project-1-tomcat) -->
<finalName>${project.artifactId}-${container}</finalName>
<!-- execução padrão, por isto basta mvn para o tomcat -->
<defaultGoal>clean package</defaultGoal>
<!-- aqui é onde estão os filters com as propriedades que serão substituidas nos arquivos xml -->
<filters>
<filter>${filter.path}/src/filters/filter-${container}.properties</filter>
</filters>
<pluginManagement>
<plugins>
<plugin>
<artifactId>maven-war-plugin</artifactId>
<version>2.6</version>
<configuration>
<failOnMissingWebXml>false</failOnMissingWebXml>
</configuration>
</plugin>
<plugin>
<artifactId>maven-resources-plugin</artifactId>
<version>2.7</version>
</plugin>
</plugins>
</pluginManagement>
</build>
Another thing is a property to reference our filter, then include this in the pom.xml
of project-parant
:
<properties>
<filter.path>${project.basedir}</filter.path>
</properties>
And this in the rest pom.xml
:
<properties>
<filter.path>${project.basedir}/..</filter.path>
</properties>
This is an example of filter. They should be called filter-glassfish.properties
, filter-jboss.properties
and filter-tomcat.properties
:
webapp-1-context=app-1
webapp-2-context=app-2
For example everyone has the same content, you can customize as needed.
Another thing is that you can customize the configuration files the way you want, from using Filters, up to properties in profiles, by command line, is at your discretion.
To perform you must do something like the following:
- for
tomcat
: mvn
- for
jboss
: mvn clean install -P jboss
- for
glassfish
: mvn clean install -P glassfish
One last observation is: there is nothing to go *-web.xml
in other constructions, by the other containers would not understand it even and this service for all others Descriptors specific to each container.
Other ways to be made is by using the maven-antrun-plugin
(this is pretty cool, personally I like it more because it is less "verbose"), the maven-assembly-plugin
or even develop your own plugin, may decide to write one for you in order to create the specific files by container.
I don’t know if I could answer your question exactly, but I hope I helped =)
Exactly, where does the spring boot come in this story? As for packaging specific to each container, there are some forms with Maven, as using Filters, profiles, move specific files by profile, etc. Soon I include an answer for you.
– Bruno César
@Brunocésar, the Spring Boot, is an option, there may be smaller customers, who will run the application in only a single station, unfortunately there are customers who do not want the application running completely remote because they fear that their data will be used without authorization, I will soon be opening this application for further discussion on client development options, as soon as the core is working and approved (if approved) :D (will be Open Source, but not Free)
– Delfino
In this case is already another context, spring boot is a guy Coc to avoid Boiler Plate and put the application to run as soon as possible, so it is another project that can use common objects, nothing prevents. Say that "the production environment can use both Jboss and Glassfish or even Spring-Boot" is quite erroneous, since the boot is not container. It got a bit confused your question, even more after you quoted spring, run a container spring in a jee container full profile is not trivial.
– Bruno César
Then I remove the Spring Boot, we only have Jboss and Glasfish to simplify the answer.
– Delfino
Delfino, completed the response to a functional example with multiple types of profiles and generating specific packages by container. See if this helps you.
– Bruno César
@Brunocésar, I’m leaving, but I’ll be back today, then take a look. For now thank you.
– Delfino
I received a negative vote and I would like to know why to improve the question.
– Delfino
To record my research on the subject, since I have not yet reached the ideal model, and have not had a number of answers to determine the best, follow the link: https://developer.jboss.org/wiki/HowToConfigureJavaEApplicationToApplyDifferentSettingsinWebxmlEtcForVariousEnvironsByMaven
– Delfino
Basically the same approach as the answer, no?
– Bruno César