I am fighting with maven to include a managed dependency with 'provided' scope into tar file by using the maven-assembly-plugin.
I use super parent pom file as a base for all of my projects. most of the projects will be deployed under application server so two common dependencies are declared under the super parent pom. below it is the relevant management section from the super parent:
http://maven.apache.org/maven-v4_0_0.xsd"> <modelVersion>4.0.0</modelVersion> <groupId>com.xxx.integration</groupId> <artifactId>super-parent</artifactId> <packaging>pom</packaging> <version>1.1.3</version> <name>super parent</name> <url>http://maven.apache.org.check</url> . . . <dependencyManagement> <dependencies> <dependency> <groupId>junit</groupId> <artifactId>junit</artifactId> <version>${junit.version}</version> <scope>test</scope> </dependency> <dependency> <groupId>log4j</groupId> <artifactId>log4j</artifactId> <version>${log4j.version}</version> <scope>provided</scope> </dependency> </dependencies> </dependencyManagement>
log4j.version=2.0.8
in one of the inherited project (which is a standalone application), i am using maven-assembly-plugin with dependencySets in order to include the dependent libraries into a tar file. and of course I want also to include the log4j library.
below is the pom inherited from super parent:
<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/maven-v4_0_0.xsd"> <parent> <groupId>com.xxx.integration</groupId> <artifactId>super-parent</artifactId> <version>1.1.3</version> </parent> <modelVersion>4.0.0</modelVersion> <artifactId>plugin-cc-checker</artifactId> <name>plugin-cc-checker</name> <version>2.1</version> <build> <plugins> <plugin> <artifactId>maven-assembly-plugin</artifactId> <dependencies> <dependency> <groupId>com.orca.integration</groupId> <artifactId>integration-assembly-descriptor</artifactId> <version>1.1.1</version> </dependency> </dependencies> <executions> <execution> <id>make-assembly-according-to-distribution-xml</id> <phase>package</phase> <goals> <goal>single</goal> </goals> <configuration> <finalName>${artifactId}</finalName> <!-- This is where we use our shared assembly descriptor --> <descriptors> <descriptor>distribution-app.xml</descriptor> </descriptors> </configuration> </execution> </executions> </plugin> </plugins> </build> <dependencies> <dependency> <groupId>xerces</groupId> <artifactId>xerces</artifactId> <version>${xerces.version}</version> <scope>runtime</scope> </dependency> <dependency> <groupId>commons-logging</groupId> <artifactId>commons-logging-api</artifactId> <version>${commons-logging-api.version}</version> <scope>runtime</scope> </dependency> <dependency> <groupId>excalibur</groupId> <artifactId>excalibur-i18n</artifactId> <version>${excalibur-i18n.version}</version> <scope>runtime</scope> </dependency> <dependency> <groupId>org.snmp4j</groupId> <artifactId>snmp4j</artifactId> <version>${snmp4j.version}</version> <scope>runtime</scope> </dependency> <dependency> <groupId>log4j</groupId> <artifactId>log4j</artifactId> <scope>runtime</scope> </dependency> </dependencies> </project>
the distribution-app.xml file:
<?xml version="1.0" encoding="UTF-8"?> <assembly> <!-- Add module dependencies and the jar that is created in the packaging phase. Product name will be <project name>-app-<version no>.tar --> <id>app-${version}</id> <formats> <format>tar</format> </formats> <includeBaseDirectory>false</includeBaseDirectory> <fileSets> <fileSet> <directory>resources/app</directory> <outputDirectory>/</outputDirectory> </fileSet> </fileSets> <dependencySets> <dependencySet> <outputDirectory>/lib</outputDirectory> <excludes> <!-- Since there is a bug in xalan 2.7.1 all applications required to use xalan-orca jar file --> <exclude>xalan:xalan</exclude> </excludes> <!-- includes> <include>*</include> </includes--> </dependencySet> </dependencySets> <moduleSets> <moduleSet> <binaries> <outputDirectory>/guy</outputDirectory> <includes> <include>log4j:log4j</include> </includes> </binaries> </moduleSet> </moduleSets> </assembly>
Why maven-assembly-plugin refuse to include the log4j into the tar file? PS, trying to change scope to compile didn't work as well. I can'r change the declaration in the super parent pom.
Provided. We use this scope to mark dependencies that should be provided at runtime by JDK or a container. A good use case for this scope would be a web application deployed in some container, where the container already provides some libraries itself.
This descriptor specifies the type of assembly archive to create, the contents of the assembly, and the ways in which dependencies or its modules are bundled with an assembly. <assembly xmlns="http://maven.apache.org/ASSEMBLY/2.1.1" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
Defines the rules for matching and working with files in a given base directory. Element.
Dependency scope is used to limit the transitivity of a dependency and to determine when a dependency is included in a classpath. This is the default scope, used if none is specified. Compile dependencies are available in all classpaths of a project. Furthermore, those dependencies are propagated to dependent projects.
This can be done using the Assembly plugin.
First create an assembly.xml
with the following:
<assembly xmlns="http://maven.apache.org/plugins/maven-assembly-plugin/assembly/1.1.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/plugins/maven-assembly-plugin/assembly/1.1.0 http://maven.apache.org/xsd/assembly-1.1.0.xsd"> <id>bin</id> <formats> <format>jar</format> </formats> <includeBaseDirectory>false</includeBaseDirectory> <dependencySets> <dependencySet> <unpack>true</unpack> <scope>runtime</scope> </dependencySet> <dependencySet> <unpack>true</unpack> <scope>provided</scope> </dependencySet> </dependencySets> </assembly>
Then just enable it in your pom.xml
<plugin> <artifactId>maven-assembly-plugin</artifactId> <version>2.4</version> <configuration> <descriptor>src/main/assembly/assembly.xml</descriptor> </configuration> <executions> <execution> <id>make-assembly</id> <phase>package</phase> <goals> <goal>single</goal> </goals> </execution> </executions> </plugin>
This will create a yourproject-bin.jar that will include all the compile and provided resources exploded so they can be referenced in a classpath.
java -cp yourproject-bin.jar com.yourcompany.Main
it is not possible to override the 'provided' scope in maven.
To solve this issue, I declared a variable in the parent pom that will define the artifact scope. In order to override the scope the only thing that has to be done, is to set new value for the variable in the inherited pom.
See example below:
parent pom:
<properties> <log4j.version>1.2.8</log4j.version> <log4j.scope>provided</log4j.scope> </properties> . . . <dependencyManagement> <dependencies> <dependency> <groupId>log4j</groupId> <artifactId>log4j</artifactId> <version>${log4j.version}</version> <scope>${log4j.scope}</scope> </dependency> </dependencies> </dependencyManagement>
Now in the child pom, just declare the variable again:
<properties> <log4j.scope>runtime</log4j.scope> </properties>
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With