Unpack Maven dependency into classes, keeping transitive dependencies - java

I am trying to unpack a maven dependency jar's contents into my classes folder, and at the same time include the transitive dependencies. I also don't want to unpack all of my project's dependencies. Only one would be good, even better if I could do this to a list of them. Found similar solutions but nothing addressing my exact issue.
Example Main Project Pom:
.
.
.
<dependencies>
<dependency>
<groupId>com.test.dep</groupId>
<artifact>first-dependency</artifact>
</dependency>
<dependency>
<groupId>com.test.dep</groupId>
<artifact>second-dependency</artifact>
</dependency>
</dependencies>
.
.
.
Example second-dependency Pom:
.
.
.
<dependencies>
<dependency>
<groupId>com.test.dep</groupId>
<artifact>third-dependency</artifact>
</dependency>
<dependency>
<groupId>com.test.dep</groupId>
<artifact>fourth-dependency</artifact>
</dependency>
</dependencies>
.
.
.
I want second-dependency to be unpacked into my classes folder nested under target and also want any of the artifacts (third-dependency, fourth-dependency) it depends on to still be included in my lib folder (not unpacked).
I tried the following (without including the the artifact in my dependencies):
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-dependency-plugin</artifactId>
<executions>
<execution>
<id>unpack</id>
<phase>generate-resources</phase>
<goals>
<goal>unpack</goal>
</goals>
<configuration>
<artifactItems>
<artifactItem>
<groupId>com.test.dep</groupId>
<artifactId>second-dependency</artifactId>
<type>jar</type>
<overWrite>true</overWrite>
<outputDirectory>${project.build.directory}/classes</outputDirectory>
<includes>**/*</includes>
</artifactItem>
</artifactItems>
</configuration>
</execution>
</executions>
</plugin>
And this did include the contents of second-dependency in my classes folder, but did not include third-dependency or fourth-dependency in my main projects lib directory.
Any ideas?

Try to use following plugin configuration, based on the described parameters of dependency:unpack-dependencies, instead:
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-dependency-plugin</artifactId>
<executions>
<execution>
<id>unpack</id>
<phase>generate-resources</phase>
<goals>
<goal>unpack</goal>
</goals>
<configuration>
<outputDirectory>${project.build.directory}/classes</outputDirectory>
<includeArtifactIds>second-dependency</includeArtifactIds>
</configuration>
</execution>
</executions>
</plugin>
Im not sure about your use case.
But if you want to build jar, that sounds like a use case for the maven-shade-plugin. This plugin is able to package the classes and resources of the project itself as well as of a specified set of artifacts (dependencies) into one jar.
Just define the artifact itself ("${project.groupId}:${project.artifactId}") and the "second dependency" to be included.
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-shade-plugin</artifactId>
<version>2.1</version>
<configuration>
<artifactSet>
<includes>
<include>${project.groupId}:${project.artifactId}</include>
<include>com.test.dep:second-dependency</include>
</includes>
</artifactSet>
</configuration>
<executions>
<execution>
<phase>package</phase>
<goals>
<goal>shade</goal>
</goals>
</execution>
</executions>
</plugin>

Related

How can I get class files from Maven dependency into the target\classes folder

Is there any sort of Maven plugin that allows me to copy the class files for a dependency into the target\classes folder for my project? Currently I have to manually open the jar file that has the dependencies extract the package that I need to copy over and then copy it into the target\class folder for my project.
I need a way to do those ideally within the pom.xml file but I haven't been able to find a solution that works. Any help would be appreciated, Thanks.
This sounds like a terrible idea. If you want to include unpacked dependencies into your project, use the maven assembly plugin or the maven shade plugin.
Use the maven-dependency-plugin. Here is an example of how you can extract the content of a dependency JAR:
<project>
[...]
<build>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-dependency-plugin</artifactId>
<version>3.1.2</version>
<executions>
<execution>
<id>unpack</id>
<phase>package</phase>
<goals>
<goal>unpack</goal>
</goals>
<configuration>
<artifactItems>
<artifactItem>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>3.8.1</version>
<type>jar</type>
<overWrite>false</overWrite>
<outputDirectory>${project.build.directory}/alternateLocation</outputDirectory>
<destFileName>optional-new-name.jar</destFileName>
<includes>**/*.class,**/*.xml</includes>
<excludes>**/*test.class</excludes>
</artifactItem>
</artifactItems>
<includes>**/*.java</includes>
<excludes>**/*.properties</excludes>
<outputDirectory>${project.build.directory}/wars</outputDirectory>
<overWriteReleases>false</overWriteReleases>
<overWriteSnapshots>true</overWriteSnapshots>
</configuration>
</execution>
</executions>
</plugin>
</plugins>
</build>
[...]
</project>
below is the example to use of assembly pulgin and it works for me
below is the child pom plugin
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-assembly-plugin</artifactId>
<version>3.4.2</version>
<configuration>
<archive>
<manifest>
<mainClass>my parent package statup class</mainClass>
</manifest>
</archive>
</configuration>
<executions>
<execution>
<id>make-assembly</id>
<phase>package</phase>
<goals>
<goal>single</goal>
</goals>
</execution>
</executions>
</plugin>
Parent pom plugin
<build>
<pluginManagement>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
</plugins>
</pluginManagement>
</build>

Maven copy only specific dependencies

I'm developping an OSGI email client with Maven following component-based software engineering. I must make sure that the dependencies between all my components are resolved inside of the OSGI container, so I cannot copy the dependencies inside the generated JARs, otherwise there would be no point using OSGI. But there is one dependency I really have to copy inside of the JAR, it's javax.mail, because I cannot find any OSGI-compatible bundle that does emailing.
To do that, I have seen this page: https://maven.apache.org/plugins/maven-dependency-plugin/examples/copying-artifacts.html
So I edited my pom.xml:
<project>
...
<build>
<plugins>
<plugin> <!-- to edit the MANIFEST.MF, required for OSGI -->
<groupId>org.apache.felix</groupId>
<artifactId>maven-bundle-plugin</artifactId>
<version>4.2.1</version>
<extensions>true</extensions>
<configuration>
<instructions>
<Class-Path>lib/</Class-Path>
... OSGI instructions ...
</instructions>
</configuration>
</plugin>
<plugin> <!-- to copy the dependencies -->
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-dependency-plugin</artifactId>
<version>3.1.1</version>
<executions>
<execution>
<phase>install</phase>
<goals>
<goal>copy-dependencies</goal>
</goals>
<configuration>
<artifactItems>
<artifactItem>
<groupId>com.sun.mail</groupId>
<artifactId>javax.mail</artifactId>
<version>1.6.2</version>
<outputDirectory>${project.build.directory}/lib</outputDirectory>
</artifactItem>
</artifactItems>
</configuration>
</execution>
</executions>
</plugin>
</plugins>
</build>
...
</project>
But the <artifactItems> tag doesn't seem to work. When I mvn install, it copies ALL the dependencies into a dependency/ folder and not a lib/ folder. How can I do to copy only the javax.mail JAR into a folder named lib/?
Thank you for your help.
The maven-bundle-plugin allows to embed dependencies:
https://felix.apache.org/documentation/subprojects/apache-felix-maven-bundle-plugin-bnd.html
<Embed-Dependency>javax.mail|javax.mail-api</Embed-Dependency>
You mixed up the goals copy-dependencies and copy. Replace copy-dependencies by copy.
http://maven.apache.org/plugins/maven-dependency-plugin/copy-mojo.html

Maven wsdl import. How to use the generated files?

i have a problem and I'm not able to solve or understand the hole workflow behind this process.
I use eclipse with maven.
This is my simple test pom.xml
...
<dependencies>
<dependency>
<groupId>com.sun.xml.ws</groupId>
<artifactId>jaxws-rt</artifactId>
<version>2.2.8</version>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.jvnet.jax-ws-commons</groupId>
<artifactId>jaxws-maven-plugin</artifactId>
<version>2.2</version>
<executions>
<execution>
<phase>generate-sources</phase>
<goals>
<goal>wsimport</goal>
</goals>
<configuration>
<xdebug>true</xdebug>
<verbose>true</verbose>
<keep>true</keep>
<packageName>abc.model</packageName>
<sourceDestDir>${project.build.directory}/generated-sources/wsimport/</sourceDestDir>
</configuration>
</execution>
</executions>
</plugin>
<plugin> <groupId>org.codehaus.mojo</groupId>
<artifactId>build-helper-maven-plugin</artifactId>
<version>1.9.1</version>
<executions>
<execution>
<id>add-source</id>
<phase>generate-sources</phase>
<goals>
<goal>add-source</goal>
</goals>
<configuration>
<sources>
<source>${project.build.directory}/generated-sources/wsimport/</source>
</sources>
</configuration>
</execution>
</executions>
</plugin>
</plugins>
</build>
...
The jaxws-maven-plugin generate the files in the sourceDestDir. The build-helper-maven-plugin add the files during the maven install process the to the correct folder and also into the resulting jar file. So far so good.
But I'm not able to use the generated files/classes in eclipse. So in eclipse maven does not recognize the files as source or does not but this in the source path. Did I make an mistake or did I miss something?
Thanks for your help.
Update:
I observer a strange behavior. Same test project same pom file. If I import this existing Maven Project in eclipse it works like expected. I can directly use the generated files as source.
But if I delete this source folder, I'm still not able to restore this with maven.

How to override configLocation in maven checkstyle plugin?

I want to override the configLocation option in maven checkstyle plugin. Sample part of POM.xml is :
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-checkstyle-plugin</artifactId>
<executions>
<execution>
<goals>
<goal>check</goal>
</goals>
</execution>
</executions>
<configuration>
<configLocation>blahblah/checkstyle/checkstyle.xml</configLocation>
<consoleOutput>true</consoleOutput>
</configuration>
<dependencies>
<dependency>
<groupId>com.example.blahblah</groupId>
<artifactId>checkstyle-config</artifactId>
<version>2.0.0-SNAPSHOT</version>
</dependency>
</dependencies>
<configuration>
<configLocation>checkstyle.config.xml</configLocation>
<suppressionsLocation>checkstyle.suppressions.xml</suppressionsLocation>
... other configuration ...
</configuration>
</plugin>
As it can be seen above, checkstyle-config is a separate maven project which contains the rules for style check and the config file use for rules is blahblah/checkstyle/checkstyle.xml. If I have to override blahblah/checkstyle/checkstyle.xml and use some other .xml which is stored in current project and not checkstyle-config project, then how can I do that?
You can override the plugin configuration in your module by copying the above plugin configuration part and just overriding the config location. In this you can move the configuration tag to within the execution, so that that configuration is applicable to that execution only.
See below example
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-checkstyle-plugin</artifactId>
<executions>
<execution>
<goals>
<goal>check</goal>
</goals>
<configuration>
<configLocation>blahblah/checkstyle/checkstyle.xml</configLocation>
</configuration>
</execution>
</executions>

How to move (or copy) a war's jar to another war's folder?

I have maven prj with 2 modules: a JAR and a WAR that depends on the JAR.
after the MAVEN INSTALL I have into a WAR the classic WEB-INF/lib folder that contains all the jar dependencies(including the first module's JAR).
I need the first module's JAR is moved to another folder, for example WEB-INF/resources.
as I can?
I was able to move the jar but only within the TARGET, the WAR remains the same.
I used the following plugin:
...
<build>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-dependency-plugin</artifactId>
<version>2.9</version>
<executions>
<execution>
<id>copy-installed</id>
<phase>install</phase>
<goals>
<goal>copy</goal>
</goals>
<configuration>
<artifactItems>
<artifactItem>
<groupId>groupId</groupId>
<artifactId>artifactId</artifactId>
<version>1.0</version>
<type>jar</type>
<overWrite>false</overWrite>
<outputDirectory>${project.build.directory}/.../WEB-INF/services</outputDirectory>
</artifactItem>
</artifactItems>
<outputDirectory>${project.build.directory}/.../WEB-INF/services</outputDirectory>
</configuration>
</execution>
</executions>
</plugin>
</plugins>
</build>
For now, I surrendered.
I could not move this JAR from WEB-INF/lib to WEB-INF/services of the EAR.
The workaround I used is to say MODULE1 to copy its JAR in the WEB-INF/services of MODULE2. Consequently, the JAR will be present in the WEB-INF/services of the sources folders, in the WEB-INF/services of the TARGET folders and in the end in the WEB-INF/services of the EAR.
i used:
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-jar-plugin</artifactId>
<version>2.5</version>
<configuration>
<outputDirectory>..MOSULE1/src/main/webbapp/WEB-INF/services</outputDirectory>
</configuration>
</plugin>
</plugins>
into MODULE1 pom.
I had to give up to make module1 independent module2 ;(
i hope i will found a clean solution..
Maybe this will help:
<project.warSourceDirectory>${basedir}/src/main/webapp</project.warSourceDirectory>
...
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-dependency-plugin</artifactId>
<version>2.9</version>
<executions>
<execution>
<id>copy-installed</id>
<phase>install</phase>
<goals>
<goal>copy</goal>
</goals>
<configuration>
<artifactItems>
<artifactItem>
<groupId>groupId</groupId>
<artifactId>artifactId</artifactId>
<version>1.0</version>
<type>jar</type>
<overWrite>false</overWrite>
<outputDirectory>${project.warSourceDirectory}/WEB-INF/services</outputDirectory>
</artifactItem>
</artifactItems>
</configuration>
</execution>
</executions>
</plugin>

Categories