Eclipse (latest) artifact builder does not include ressources - java

i'm currently confused that eclipse ignores my configured pom building instructions.
Used : Eclipse 2023-03 / 2022-12 (both same failure)
parent pom :
...
<modules>
<module>my-module</module>
<module>my-webapp</module>
</modules>
<dependencyManagement>
<dependencies>
<dependency>
<groupId>com.example</groupId>
<artifactId>my-module</artifactId>
<version>1.0</version>
</dependency>
...
</dependencies>
</dependencyManagement>
<build>
<pluginManagement>
<plugins>
<plugin>
<groupId>com.github.eirslett</groupId>
<artifactId>frontend-maven-plugin</artifactId>
<version>1.12.1</version>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-jar-plugin</artifactId>
<version>3.3.0</version>
<configuration>
<excludes>
<exclude>**/module.dtd</exclude>
</excludes>
</configuration>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-war-plugin</artifactId>
<version>3.3.2</version>
</plugin>
<plugin>
<groupId>org.codehaus.mojo</groupId>
<artifactId>versions-maven-plugin</artifactId>
<version>2.14.2</version>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<version>3.10.1</version>
<configuration>
<source>17</source>
<target>17</target>
<showDeprecation>true</showDeprecation>
<showWarnings>true</showWarnings>
</configuration>
</plugin>
</plugins>
</pluginManagement>
<resources>
<resource>
<directory>src/main/resources</directory>
<includes>
<include>**/*</include>
</includes>
</resource>
<resource>
<filtering>true</filtering>
<directory>src/main/resources</directory>
</resource>
</resources>
</build>
my-module structure (pom refers to parent without any build instructions - packaging -> jar) :
src/main/java
---...
src/main/resources
src/main/resources/META-INF/test/file.xml
src/main/resources/example/bootstrap/file2.xml
my-webapp (refers to parent pom - packaging -> war) :
<build>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-war-plugin</artifactId>
<configuration>
<webResources>
<resource>
<directory>${config.path}</directory>
<targetPath>WEB-INF/config</targetPath>
<includes>
<include>**/*</include>
</includes>
</resource>
</webResources>
</configuration>
</plugin>
</plugins>
</build>
Build with mvn clean install results in a deployable war file which contains my-module.jar in lib folder as expected, size matches also the generated jar file in my-module targets folder.
so targets generated .war/.jar are correct.
Now i setup inside eclipse a default tomcat server above v.9.0.50+ (tried multiple versions, also latest 9.0.71). and added my-webapp(example-context) to the server (cleaned before and then publish).
at this point i inspected my unzipped war file inside tomcat webapproot (tried meta and tomcat location (both same failure)) , and was completly confused that my my-module-1.0.jar file only contains only META-INF/maven (pom.xml + pom.properties) and my java classes so that it doesen't match the size as expected (due to missing resource files).
Is there any trick or option to configure eclipse to build the artifact with resources as instructed by my poms or any other vaiable soloution ?
If i use intellij, it worked out of the box but i prefer eclipse for my project
Tried different versions of eclipse , tomcat , maven and plugin versions (latest) but nothing seems to work.
Sometimes if i change my resource or java files of my-mopdule, eclipse makes a redeploy and then the artifact contains the correct my-module-1.0.jar with resources included but after another mvn clean install its gone and i need to modify any files again up to 10 times if it happens again.

Related

Maven Exclude Files During Build

I am having problems getting Maven to build my webapp without including extraneous development file, such as unminified script and css files.
First i tried using exclude in combination with webResources
<build>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-war-plugin</artifactId>
<version>2.6</version>
<configuration>
<warName>ReportRocket-1</warName>
<webResources>
<resource>
<directory>src/main/webapp/resources/</directory>
<excludes>
<exclude>annotated-js/*.js</exclude>
<exclude>compiled-js/*.js</exclude>
<exclude>css/*.css</exclude>
<exclude>less/*.less/exclude>
</excludes>
<directory>src/main/webapp/WEB-INF</directory>
<excludes>
<exclude>connection.json</exclude>
<exclude>reportRocket.jsp</exclude>
</excludes>
</resource>
</webResources>
</configuration>
</plugin>
</plugins>
</build>
The result was the contents of WEB-INF being duplicated in the project root and no excluded directories or files.
So, I looked around here and found this: maven2: excluding directory from WAR but running mvn clean package using either warSourceExcludes or packagingExcludes results in the directories i'm trying to exclude not being, well, excluded...
The build section of my pom.xml
<build>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-war-plugin</artifactId>
<version>2.6</version>
<configuration>
<warName>ReportRocket-1</warName>
<packagingExcludes>
src/main/webapp/resources/annotated-js/,
src/main/webapp/resources/compiled-js/,
src/main/webapp/resources/css/,
src/main/webapp/resources/less/,
src/main/webapp/WEB-INF/connection.json
</packagingExcludes>
</configuration>
</plugin>
</plugins>
</build>
Building the project with these settings results in the following project structure:
META-INF
resources
//desired folders
annotated-js
compiled-js
css
less
WEB-INF
// desired files
connection.json
This is my first time using a build tool, so i'm probably overlooking something simple but in the meantime, this is driving me crazy. Any suggestions or obvious problems with my xml?
First you should read the documentation of the maven-war-plugin cause the packagingExclude is intended for a different purpose, but in your case you need to do the configuration in that way:
<configuration>
<webResources>
<resource>
<!-- this is relative to the pom.xml directory -->
<directory>src/main/webapp/resources/</directory>
<!-- there's no default value for this -->
<excludes>
<exclude>annotated-js/**</exclude>
</excludes>
</resource>
</webResources>
</configuration>

How to put maven zip dependency on classpath for Java tests

I have a Java project entirely consisting of junit/integration tests which is managed by maven. One of the dependencies is a zip archive, the contents of which I would like to be available on the classpath when the tests are run. Since maven does not put the content of a zip dependency on the classpath I have had to come up with what I consider to be a hacky workaround. I unpack the zip archive to a temp directory then copy one of the resulting directories into the /test-classes folder. I also had to make the clean step delete the temp directory. Here are the relevant parts of the pom:
<groupId>com.my.package</groupId>
<artifactId>test-project</artifactId>
<version>0.0.1-SNAPSHOT</version>
<name>My Test Project</name>
<properties>
<config.artifactId>environment-dev</config.artifactId>
<config.version>2.0.8-SNAPSHOT</config.version>
<tempDir>${project.basedir}/temp</tempDir>
</properties>
<build>
<plugins>
...
<!-- clean out our custom temp directory as well as the default dir during clean phase-->
<plugin>
<artifactId>maven-clean-plugin</artifactId>
<version>2.3</version>
<configuration>
<filesets>
<fileset>
<directory>${tempDir}</directory>
</fileset>
</filesets>
</configuration>
</plugin>
<!-- since the config dependency is a zip it does not get added to the classpath. So we extract
it to a temp dir, then copy the content we need into a directory on the classpath -->
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-dependency-plugin</artifactId>
<version>2.8</version>
<executions>
<execution>
<id>unpack-config</id>
<phase>compile</phase>
<goals><goal>unpack-dependencies</goal></goals>
<configuration>
<includeGroupIds>com.my.package.config</includeGroupIds>
<includeArtifactIds>${config.artifactId}</includeArtifactIds>
<includeClassifiers>config</includeClassifiers>
<outputDirectory>${tempDir}</outputDirectory>
</configuration>
</execution>
</executions>
</plugin>
<!-- copy the content of the zip file that we extracted into a directory on the classpath -->
<plugin>
<artifactId>maven-resources-plugin</artifactId>
<version>2.6</version>
<executions>
<execution>
<phase>compile</phase>
<goals><goal>copy-resources</goal></goals>
<configuration>
<outputDirectory>${project.build.directory}/test-classes/TargetDir</outputDirectory>
<resources>
<resource>
<directory>${tempDir}/${config.artifactId}-${config.version}/TargetDir</directory>
<filtering>true</filtering>
</resource>
</resources>
</configuration>
</execution>
</executions>
</plugin>
</plugins>
</build>
<dependencies>
...
<dependency>
<groupId>com.my.package.config</groupId>
<artifactId>${config.artifactId}</artifactId>
<version>${config.version}</version>
<classifier>config</classifier>
<type>zip</type>
</dependency>
</dependencies>
There must be a better way of doing this.
Can I force maven to treat the zip file as if it were a jar? The link I provided has a tantalising hint that this might once have been possible, but I can't find anything relevant in the documentation. This seems like such a simple thing to be able to do, I really hope I've just missed a config parameter somewhere. Can anyone suggest a better way of getting the content of a zip dependency onto the classpath?
I would unzip the dependency into a subdirectory of the target directory and add that directory to the additionalClasspathElements configuration of the surefire plugin.
<properties>
<config.artifactId>environment-dev</config.artifactId>
<config.version>2.0.8-SNAPSHOT</config.version>
<unzipDir>${project.build.directory}/addTestClasspath</unzipDir>
</properties>
<build>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-dependency-plugin</artifactId>
<version>2.8</version>
<executions>
<execution>
<id>unpack-config</id>
<phase>compile</phase>
<goals><goal>unpack-dependencies</goal></goals>
<configuration>
<includeGroupIds>com.my.package.config</includeGroupIds>
<includeArtifactIds>${config.artifactId}</includeArtifactIds>
<includeClassifiers>config</includeClassifiers>
<outputDirectory>${unzipDir}</outputDirectory>
</configuration>
</execution>
</executions>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-surefire-plugin</artifactId>
<version>2.17</version>
<configuration>
<additionalClasspathElements>
<additionalClasspathElement>${unzipDir}</additionalClasspathElement>
</additionalClasspathElements>
</configuration>
</plugin>
</plugins>
</build>
In this case you can omit the clean plugin config because everything is under the target folder which will be deleted by the clean plugin by default.
Sadly this configuration does only work on the command line and not within eclipse, because the m2e plugin does not honor the additionalClasspathElement. See the jira issue MNGECLIPSE-1213

redefine webapp location - maven standard folder for web resources

I have big Java project build with Ant, that I am converting to maven.
How to redefine webapp - maven standard folder for web resources?
I can't move web content, and it is always under active development.
See here:
http://maven.apache.org/plugins/maven-war-plugin/war-mojo.html
The property you want to change is "warSourceDirectory"
Solved by
<!-- http://maven.apache.org/plugins/maven-war-plugin/examples/adding-filtering-webresources.html -->
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-war-plugin</artifactId>
<version>2.3</version>
<configuration>
<webResources>
<resource>
<!-- this is relative to the pom.xml directory -->
<directory>${webapp-folder}</directory>
<excludes>
<exclude>**/*.jar</exclude>
</excludes>
</resource>
</webResources>
</configuration>
</plugin>

Using war excludes in the pom.xml

The maven documentation for this has to be wrong.
Here are the various permutations I have tried with all failing to exclude the file:
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-war-plugin</artifactId>
<configuration>
<warSourceExcludes>**/*server.properties</warSourceExcludes>
</configuration>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-war-plugin</artifactId>
<configuration>
<webResources>
<resource>
<!-- this is relative to the pom.xml directory -->
<directory>src/main/resources/com/mycom/myapplication/</directory>
<!-- there's no default value for this -->
<excludes>
<exclude>**/*server.properties</exclude>
</excludes>
</resource>
</webResources>
</configuration>
</plugin>
A mail list entry suggests using this older version and a string list:
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-war-plugin</artifactId>
<version>2.0.1</version>
<configuration>
<webResources>
<resource>
<!-- this is relative to the pom.xml directory -->
<directory>src/main/resources/com/pictage/provendirect/</directory>
<!-- there's no default value for this -->
<excludes>**/*server.properties</excludes>
</resource>
</webResources>
</configuration>
</plugin>
Which results in:
(found static expression: '/*server.properties' which may act as a default value).
Cause: Cannot assign configuration entry 'excludes' to 'interface java.util.List' from '/*server.properties', which is of type class java.lang.String
Also tried:
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-war-plugin</artifactId>
<version>2.0.1</version>
<configuration>
<packagingExcludes>
**/server.properties
</packagingExcludes>
</configuration>
</plugin>
Any ideas? I am going crazy with this.
A more careful reading of the maven docs suggests:
<configuration>
<webResources>
<resource>
should only be used when excluding resources outside /src/main/resources. To do it inside this folder, you need to use warSourceExcludes and possibly warSourceDirectory parameters if the property isn't in the root of the directory.
I cry a little inside when it takes me hours to to do something via configuration in maven when it could have been handled in two seconds with a scripting language but I guess it's the 'right' way to implement it.

How to exclude classes from a packaged webapp with maven

How can I filter certain classes in /target/classes from going into /target/[webapp]/WEB-INF/classes? I want them compiled into /target/classes/ but not in the final war.
What are these classes for? If they are for testing, you can specify them in src/test/java, they will then be compiled into target/test-classes in the test-compile phase, but won't be included in the final war.
If they aren't for testing and aren't to be included in the war, perhaps they should be refactored into another project so you can specify it as a dependency (perhaps with "provided" scope so they won't be deployed.
For reference you can configure the war to include and exclude resources when packaging.
The following example will include all jpgs but exclude resources from the image2 sub folder:
<configuration>
<webResources>
<resource>
<!-- this is relative to the pom.xml directory -->
<directory>resource2</directory>
<!-- the list has a default value of ** -->
<includes>
<include>**/*.jpg</include>
<includes>
<excludes>
<exclude>**/image2</exclude>
</excludes>
</resource>
</webResources>
</configuration>
See the war plugin documentation for more details.
You can use the TrueZIP Maven Plugin ( http://mojo.codehaus.org/truezip-maven-plugin/ ).
See examples in:
http://svn.codehaus.org/mojo/trunk/mojo/truezip-maven-plugin/src/it/
You might have luck with this, assuming you them in a package that you can define with an ant pattern
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-war-plugin</artifactId>
<version>2.0.2</version>
<configuration>
<excludes>**/dontneed/*.class</excludes>
</configuration>
</plugin>
With current version of maven-war-plugin (3.0.0) this works for me -
<profile>
<id>abc</id>
...
<build>
<plugin>
<artifactId>maven-war-plugin</artifactId>
<version>3.0.0</version>
<configuration>
<packagingExcludes>WEB-INF/classes/com/abc/pqr/ClassName.class</packagingExcludes>
</configuration>
</plugin>
</build>
</profile>

Categories