In the pom file I have the dependencyManagement tag (could be also inherited from parent) and i would like to know how this tag can influence the version of dependencies. so let show an exemple:
<dependencyManagement>
<dependencies>
<dependency>
<groupId>org.hamcrest</groupId>
<artifactId>hamcrest-core</artifactId>
<version>2.2</version>
<scope>test</scope>
</dependency>
</dependencies>
</dependencyManagement>
<dependencies>
<dependency>
<groupId>org.hamcrest</groupId>
<artifactId>hamcrest-core</artifactId>
<version>1.0</version>
<scope>test</scope>
</dependency>
</dependencies>
In the exemple below what version of the hamcrest-core dependency will be used? the version 2.2 or 1.0?
dependencies defined in the pom should get priority over dependencyManagement.
Using dependencyManagement is useful when you have child projects under a parent project,
Dependencies specified in the parent pom dependencies section will always be included as a dependency of the child modules.
Dependencies specified in the dependencyManagement section, will only be included in the child module if they were also specified in the dependencies section of the child module.
You can specify the version and scope in the parent, but you can leave them out when specifying the dependencies in the child POM (to ensure all projects are using same version).
Related
I have a spring batch dependency in my pom.xml declared as below:
<dependency>
<groupId>org.springframework.batch</groupId>
<artifactId>spring-batch-core</artifactId>
<version>3.0.9.RELEASE</version>
</dependency>
There is one artifact xstream that is included by above with version 1.4.7 and it needs to be updated to 1.4.11.
It can be added as follow:
<groupId>com.thoughtworks.xstream</groupId>
<artifactId>xstream</artifactId>
<version>1.4.11</version>
</dependency>
What is the correct way for this?I am thinking of following approach:
Both above pieces of code will be there but do I need to use < exclusions > to specifically exclude xstream artifact old version from spring-batch-core or does maven takes care of this automatically?
Better way will be using <dependencyManagement/> tag. Dependency management will make sure the version will be maintained even if some other transitive dependency brings higher version of the dependency.
Usage:
<dependencyManagement>
<dependencies>
<dependency>
<groupId>com.thoughtworks.xstream</groupId>
<artifactId>xstream</artifactId>
<version>1.4.11</version>
</dependency>
</dependencies>
</dependencyManagement>
Note: dependencyManagement tag is used for defining the version and scope (if not in the default scope which is compile) of a dependency it does not add the dependencies in it to you project, you must define separate <dependencies/> section in your pom.xml for adding dependencies to your project.
In your case it will be like.
<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">
...
<dependencyManagement>
<dependencies>
<dependency>
<groupId>com.thoughtworks.xstream</groupId>
<artifactId>xstream</artifactId>
<version>1.4.11</version>
</dependency>
</dependencies>
...
</dependencyManagement>
<dependencies>
<dependency>
<groupId>org.springframework.batch</groupId>
<artifactId>spring-batch-core</artifactId>
<version>3.0.9.RELEASE</version>
</dependency>
...
</dependencies>
...
</project>
In this case spring-batch-core is added as a direct dependency and if it has xstream as dependecny you project will use 1.4.11 version even spring-batch-core has a different version of xstream as dependency.
Ref: Dependency Management
According to the maven docs Dependency management
is a mechanism for centralizing dependency information.
and from this question here SO Question, many people suggested to use Dependency managmement instead of dependencies when we have a common jar file for all children.
as in dependency management , dependencies are propogated only when children request for it but incase of dependencies the dependecies are propogated even when not required.
but wouldn't it be a better approch when the jar file is common to all children ,i.e when all the children inherit the same jar file
for example (rewritten example taken from maven docs)
child a
<dependencies>
<dependency>
<groupId>group-a</groupId>
<artifactId>artifact-a</artifactId>
</dependency>
<dependency>
<groupId>group-c</groupId>
<artifactId>artifact-b</artifactId>
</dependency>
</dependencies>
child b
<dependencies>
<dependency>
<groupId>group-c</groupId>
<artifactId>artifact-b</artifactId>
</dependency>
<dependency>
<groupId>group-a</groupId>
<artifactId>artifact-b</artifactId>
</dependency>
</dependencies>
parent of both a and b
<dependencyManagement>
<dependencies>
<dependency>
<groupId>group-a</groupId>
<artifactId>artifact-a</artifactId>
<version>1.0</version>
</dependency>
</dependencies>
</dependencyManagement>
but wouldn't this yeild the same result ??
parent of both a and b
<dependencies>
<dependency>
<groupId>group-a</groupId>
<artifactId>artifact-a</artifactId>
<version>1.0</version>
</dependency>
</dependencies>
child a
<dependencies>
<dependency>
<groupId>group-c</groupId>
<artifactId>artifact-b</artifactId>
</dependency>
</dependencies>
child b
<dependencies>
<dependency>
<groupId>group-c</groupId>
<artifactId>artifact-b</artifactId>
</dependency>
</dependencies>
or did i misunderstand them??
and which one should i use and in what conditions ??
Dependency management section in the parent pom is managing versions and only versions of these libraries, when you are using them in the child projects.
Dependency section on the contrary ENFORCES all child modules to have these dependencies, regardless child modules need them or not.
If you are sure ALL your child modules will use group-a:module-a:version, then feel free to declare it in parent dependencies section.
If you have at least one child module in the project, where such enforced dependency is unnecessary, then dependencyManagement better suites your need.
I am using spring-boot 2.0.3.RELEASE. When I am clicking on "show Effective POM" option by using IntelliJ IDEA, it loads Effective POM. And there I can see a few dependencies that my client don't want to have at there side.
Is there any way to tell Maven not to include these dependencies? How can we exclude dependencies from effective poms?
Maven provides a way to exclude dependencies with the exclude tag
Here is an example taken from the documentation website https://maven.apache.org/guides/introduction/introduction-to-optional-and-excludes-dependencies.html
<dependencies>
<dependency>
<groupId>sample.ProjectA</groupId>
<artifactId>Project-A</artifactId>
<version>1.0</version>
<scope>compile</scope>
<exclusions>
<exclusion> <!-- declare the exclusion here -->
<groupId>sample.ProjectB</groupId>
<artifactId>Project-B</artifactId>
</exclusion>
</exclusions>
</dependency>
</dependencies>
The idea is to locate parent dependencie from where you are getting deps you don't want and add an exclusion tag.
If they are needed in runtime you can specify the scope to provided
<dependency>
<groupId>sample.ProjectA</groupId>
<artifactId>Project-A</artifactId>
<version>1.0</version>
<scope>provided</scope>
</dependency>
That will tell maven to use the deps to compile but not no include them in the target package, and they will be provided in the production environment by the JVM executing the code.
Hope this helps
I have a library that has several sub modules. I have set the version for the library in the parent POM.
<groupId>com.softtech</groupId>
<artifactId>BatchLibrary</artifactId>
<version>2.1</version>
<packaging>pom</packaging>
Also, I have created a Maven Bill Of Materials(BOM) project where this library is defined.
In first case, I set the version for entire library in BOM as below
<dependencyManagement>
<dependencies>
<dependency>
<groupId>com.softtech</groupId>
<artifactId>BatchLibrary</artifactId>
<version>2.1</version>
</dependency>
</dependencies>
</dependencyManagement>
In second case, I set the version for library's each sub module individually like below
<dependencyManagement>
<dependencies>
<dependency>
<groupId>com.softtech</groupId>
<artifactId>BatchLibrary-core</artifactId>
<version>2.1</version>
</dependency>
<dependency>
<groupId>com.softtech</groupId>
<artifactId>BatchLibrary-web</artifactId>
<version>2.1</version>
</dependency>
</dependencies>
</dependencyManagement>
I have added this BOM to my projects. When declaring library's sub module without version in my project. In first case mentioned above, I get an error
dependency.version is missing
In Second case, it works fine.
Is that is how BOM works? Do I have to define all the sub modules with version individually in my BOM or I can just define the parent POM of my library with version and it should work. If it should? Why It is not working in my case?
The BOM should list the version of all the artifacts. I snipped the following from the Importing Dependencies section of the Maven website's "Introduction to the Dependency Mechanism":
The root of the project is the BOM pom. It defines the versions of all the artifacts that will be created in the library. Other projects that wish to use the library should import this pom into the dependencyManagement section of their pom.
Is there a way, without modifying parent POM to use version of some dependency from child POM?
For example in parent POM i have:
<dependency>
<groupId>org.dbunit</groupId>
<artifactId>dbunit</artifactId>
<version>2.4.8</version>
</dependency>
In child POM:
<dependency>
<groupId>org.dbunit</groupId>
<artifactId>dbunit</artifactId>
<version>2.5.0</version>
</dependency>
If you put that dependency in the dependencyManagement section of your child pom, then modules from your child pom downwards (it will not affect siblings of your child pom) will use the version you specify. It will, effectively, override the version in the parent pom.