How to remove spring boot dependency using dependencyManagement? - maven

In my pom file i have the following:
<dependencyManagement>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-dependencies</artifactId>
<version>2.1.2.RELEASE</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
I use this because the project already have a parent pom.
I want to remove some of its dependencies such as:
<dependency>
<groupId>org.elasticsearch</groupId>
<artifactId>elasticsearch</artifactId>
<version>6.4.3</version>
</dependency>
How do I do this?

spring-boot-dependencies does not add any dependency. It mostly consists out of a giant <dependencyManagement> block containing managed versions for several libraries. This allows you to use versions of libraries that are known to work properly with the given version of Spring boot.
That means that you no longer have to add the <version> to each dependency you define.
It also means that if you have a dependency upon elasticsearch, it certainly doesn't come from spring-boot-dependencies.
If your goal is to override one of the versions, you can, by manually adding <version> to your dependency.
Otherwise, you can usually exclude a dependency by using <exclusions>:
<dependency>
<groupId>com.xyz</groupId>
<artifactId>artifact-abc</artifactId>
<exclusions>
<exclusion>
<groupId>org.elasticsearch</groupId>
<artifactId>elasticsearch</artifactId>
</exclusion>
</exclusions>
</dependency>

Related

How to change the version of a "son dependency" in pom?

there is another way to change the version of a maven dependency that is onto another dependency?
i did that like this and works fine but, i want to know if there's another way more cleaner to do that.
Example:
<!-- https://mvnrepository.com/artifact/org.springframework.boot/spring-boot-starter-web -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
<exclusions>
<!-- Dependency that i want to update -->
<exclusion>
<groupId>com.fasterxml.jackson.core</groupId>
<artifactId>jackson-annotations</artifactId>
</exclusion>
</exclusions>
</dependency>
<!-- https://mvnrepository.com/artifact/com.fasterxml.jackson.core/jackson-annotations -->
<dependency>
<groupId>com.fasterxml.jackson.core</groupId>
<artifactId>jackson-annotations</artifactId>
<version>2.9.4</version>
</dependency>
In my experience, the best practice is to do this with dependencyManagement, and only set the version for the dependency (not scope). This will enforce the version of the dependency with minimal effect on the dependency tree.
Adding a direct dependency like you do now, wrongfully signals that your code refers to jackson-annotations apis directly, and may also have side effects on the set of transitive dependencies.
<project>
...
<dependencyManagement>
<dependencies>
<dependency>
<groupId>com.fasterxml.jackson.core</groupId>
<artifactId>jackson-annotations</artifactId>
<version>2.9.4</version>
</dependency>
</dependencies>
</dependencyManagement>
...
Btw, I think that the exclusion in your example is unnecessary. You can verify that by running mvn dependency:tree.

How to override version of libraries included automatically under spring-boot-starter

I have spring-boot-starter in my POM and versions are automatically resolved by Camden dependency management system.
<dependencyManagement>
<dependencies>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-dependencies</artifactId>
<version>Camden.SR6</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
<dependencies>
<!-- Spring Boot -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter</artifactId>
</dependency>
</dependencies>
This gives me version 1.4.3.RELEASE of spring-boot-starter.
One of the jars spring boot starter includes automatically in the maven dependencies is logback-classic: 1.1.18
ch.qos.logback_logback-core version 1.1.8 has a vulnerability because of which I want to switch over to logback version 1.2
This vulnerability is explained in the link below
https://nvd.nist.gov/vuln/detail/CVE-2017-5929
Now, is there a way to override the logback version to 1.2 from what spring-boot-starter automatically resolves it to so that I am not exposed to this vulnerability ?
Based on your pom file, you can achieve this by excluding the dependency of 1.1.8 first then add the dependency of 1.2.0.
For example:
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter</artifactId>
<exclusions>
<exclusion>
<groupId>ch.qos.logback</groupId>
<artifactId>logback-classic</artifactId>
</exclusion>
</exclusions>
</dependency>
<dependency>
<groupId>ch.qos.logback</groupId>
<artifactId>logback-classic</artifactId>
<version>1.2.0</version>
</dependency>
add properties tag in pom like this
<properties>
<maven.compiler.source>1.8</maven.compiler.source>
<maven.compiler.target>1.8</maven.compiler.target>
<start-class>org.roshan.Application</start-class>
<hibernate.version>5.2.10.Final</hibernate.version>
<liquibase.version>3.5.3</liquibase.version>
<liquibase-hibernate5.version>3.6.0</liquibase-hibernate5.version>
<httpcore.version>4.4.5</httpcore.version>
<httpclient.version>4.5.3</httpclient.version>
<docker-maven-plugin.version>0.4.13</docker-maven-plugin.version>
</properties>

How to properly use org.wildly wildfly-server dependency in pom.xml?

I'm trying to setup an easy to maintain Maven config for my current project. The EAR with two EJB und one WAR module will be deployed to JBoss Wildfly v8.2.0.Final and I want to ease the build process by using the following dependency in my pom.xml:
<dependencyManagement>
<dependencies>
<dependency>
<groupId>org.wildfly</groupId>
<artifactId>wildfly-server</artifactId>
<version>8.2.0.Final</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
I've thought this would allow me to use all the provided modules like EJB, CDI and the others without explicitly naming them in my modules pom.xml. But that doesn't seem to be the case. I had to add the following dependencies manually... is this really needed?
<dependencies>
<dependency>
<groupId>org.jboss.spec.javax.interceptor</groupId>
<artifactId>jboss-interceptors-api_1.2_spec</artifactId>
</dependency>
<dependency>
<groupId>org.jboss.spec.javax.faces</groupId>
<artifactId>jboss-jsf-api_2.2_spec</artifactId>
</dependency>
<dependency>
<groupId>org.jboss.spec.javax.servlet</groupId>
<artifactId>jboss-servlet-api_3.1_spec</artifactId>
</dependency>
<dependency>
<groupId>org.jboss.spec.javax.ejb</groupId>
<artifactId>jboss-ejb-api_3.2_spec</artifactId>
</dependency>
<dependency>
<groupId>org.jboss.spec.javax.el</groupId>
<artifactId>jboss-el-api_3.0_spec</artifactId>
</dependency>
<dependency>
<groupId>org.jboss.spec.javax.transaction</groupId>
<artifactId>jboss-transaction-api_1.2_spec</artifactId>
</dependency>
</dependencies>
Or is this the way it should be? How to use jars from Wildfly correctly in Maven? is not clear at this point.
What are you looking for is not usage of wildfly-server, which is artifact that is entry point for booting the server and not needed by application developers in general.
You are looking for boms that go with WildFly.
you can find all different kind of boms here https://github.com/wildfly/boms
to include all dependencies you could use
<dependencyManagement>
<dependencies>
<dependency>
<groupId>org.wildfly.bom</groupId>
<artifactId>jboss-javaee-7.0-with-all</artifactId>
<version>8.2.1.Final</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
If you only need the Java EE API then just use the Java EE API dependency. However, you may hit issues during unit and low-level integration testing.
So the approach I use is the glassfish-embedded-all dependency which is at least the reference implementation and bundles everything up nicely for me. However, I only recommend it only for testing and needs to be before the javaee dependency.
My core dependencies in my parent pom usually looks like this
<dependencies>
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>4.12</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.glassfish.main.extras</groupId>
<artifactId>glassfish-embedded-all</artifactId>
<version>4.1</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>javax</groupId>
<artifactId>javaee-api</artifactId>
<version>7.0</version>
<scope>provided</scope>
</dependency>
</dependencies>
By using this approach I get the best of both worlds. I can run low level integration tests against a reference implementation while I ensure that when it compiles it only compiles against the standard API.
It is important you keep the glassfish-embedded-all before the API dependency otherwise the classloader will pick the API dependency first which isn't want you want during testing.

How to exclude transitive dependencies of spring-boot-dependencies from maven import scope

I have the following in my Spring Boot application pom as per the documentation:
<dependencyManagement>
<dependencies>
<!-- Spring -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-dependencies</artifactId>
<version>${spring-boot.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
I need to use use dependencyManagement and <scope>import</scope> because I need to use a standard corporate base pom.
However, it doesn't seem possible to exclude transitive dependencies of spring-boot-dependencies. In my particular case, Spring Boot 1.2.1.RELEASE is bringing in a version of Jetty that is too new with respect to some of my other <dependencies>. I tried using an <exclusion> of the form:
<dependencyManagement>
<dependencies>
<!-- Spring -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>${spring-boot.version}</version>
<type>pom</type>
<scope>import</scope>
<!-- Doesn't work -->
<exclusions>
<exclusion>
<groupId>org.eclipse.jetty</groupId>
<artifactId>*</artifactId>
</exclusion>
</exclusions>
</dependency>
</dependencies>
</dependencyManagement>
using Maven 3.2.1's wildcard support, but it doesn't seem to take effect.
Is there a solution to this problem other than explicitly overriding all the Jetty dependencies? There are many Jetty libraries and that approach would be quite brittle. Furthermore, it appears I would need to do the same with Jetty's transitive dependencies as well.
According to the Spring Boot Maven Plugin 2.3.1.RELEASE documentation, to override individual dependencies, you need to add entries in the dependencyManagement section of your project before the spring-boot-dependencies entry.
<dependencyManagement>
<dependencies>
<!-- Your jetty version dependency -->
<dependency>
<groupId>org.eclipse.jetty</groupId>
<artifactId>*</artifactId>
<version>${jetty.version}</version>
</dependency>
<!-- Spring -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>${spring-boot.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
Looks like this isn't possible with Maven import scope:
The import scope can be used to include dependency management
information from a remote POM into the current project. One of the
limitations of this is that it does not allow additional excludes to
be defined for a multi module project.
Likewise, there is a confirmation from the Spring Boot documentation:
If you have added spring-boot-dependencies in your own
dependencyManagement section with <scope>import</scope> you have to
redefine the artifact yourself [...].

Why does my project always try to download the latest spring-beans 3.2.*.RELEASE artefact

I have a spring MVC web application that has the following spring dependencies:
spring-aop-3.2.1.RELEASE
spring-beans-3.2.1.RELEASE
spring-context-support-3.2.1.RELEASE
spring-context-3.2.1.RELEASE
spring-core-3.2.1.RELEASE
spring-expression-3.2.1.RELEASE
spring-jdbc-3.2.1.RELEASE
spring-jms-3.2.1.RELEASE
spring-orm-3.2.1.RELEASE
spring-test-3.2.1.RELEASE
spring-tx-3.2.1.RELEASE
spring-web-3.2.1.RELEASE
spring-webmvc-3.2.1.RELEASE
spring-aspects-3.2.1.RELEASE
spring-spring-security-core-3.2.0.RELEASE
spring-security-web-3.2.0.RELEASE
spring-security-config-3.2.0.RELEASE
spring-security-taglibs-3.2.0.RELEASE
My question is that when i build using mvn clean install does it try and download spring-beans-3.2.10.RELEASE. I am assuming one of my dependencies is dragging it in but not sure which.
Any help would be greatly appreciated.
Thanks in advance.
You can define your dependencies in the <dependencyManagement> section of POM. The versions that you define in <dependencyManagement> will apply not only to the dependencies that you mention in the top-level <dependencies> section, but also to their transitive dependencies.
For example:
<dependencyManagement>
<dependencies>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-beans</artifactId>
<version>3.2.1.RELEASE</version>
</dependency>
...
</dependencies>
</dependencyManagement>
<dependencies>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-beans</artifactId>
</dependency>
...
</dependencies>
These fragments will make sure that Maven uses only version 3.2.1.RELEASE. (Note that there are no <version> in the second section.)
If you still want to find out where that dependency comes from, and if you use Eclipse, open your pom.xml and have a look at the Dependency Hierarchy tab. If necessary, you can double-click on dependencies there: it will open the dependency's own pom.xml where you can research transitive dependencies further.
You can solve your proble in the following way:
<dependencyManagement>
<dependencies>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-framework-bom</artifactId>
<version>4.1.0.BUILD-SNAPSHOT</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
<dependencies>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-context</artifactId>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-web</artifactId>
</dependency>
<dependencies>
and then you can manage your dependency without worry of single version number. In this way all spring dependencies will have the same 4.1.0.BUILD-SNAPSHOT version

Resources