Can you help me understand what really the advantage of using a BOM pom is ?
more precisely what is the difference between using a BOM pom and
writing the content of BOM pom in the dependencyManagement section of
a parent pom ?
<dependencyManagement>
<dependencies>
<dependency>
<groupId>xxx.yyy</groupId>
<artifactId>com.so</artifactId>
<version>${my.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
vs
<dependencyManagement>
<dependencies>
...
</dependencies>
</dependencyManagement>
Related
I need to import a dependency in my project; The problem is that that dependency is specified by a pom in this way:
<dependency>
<groupId>it.xxxx.yyyyy.be.esb</groupId>
<artifactId>CR_XXXXX_BE_PRODO_YYYYYY_V1</artifactId>
<version>1.0.0-SNAPSHOT</version>
<type>pom</type>
</dependency>
When I add this dependency in my project it compile well, and in my local repository (.m2) I find the folder at the path it.xxxx.yyyyy.be.esb;
But not find any jar inside the folder, so How I can use that dependency?
That dependency should be a client to make soap call to a server!
In other project the dependency was:
<dependency>
<groupId>it.xxxx.yyyyy.be.esb</groupId>
<artifactId>CR_XXXXX_BE_PRODO_YYYYYY_V1</artifactId>
<version>1.0.0-SNAPSHOT</version>
<type>jar</type>
</dependency>
And when I compile, the jar file is downloaded and i'm able to find it in my local repository (.m2), also I can decompile and see all class inside the package, and I can import in my class;
So my question is, is there a way to use the first dependency (the one with pom as type: pom)?
thanks
In dependencyManagement you can import a "bill of materials" (BOM) that is provided in pom format. Here all the supplied components, their requirements and their versions are included so that you know that you are using all the versions that the BOM provider used.
For example, Spring boot (I know you can do it as a parent pom):
<dependencyManagement>
<dependencies>
<!-- Import dependency management from Spring Boot -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-dependencies</artifactId>
<version>3.0.2</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
.
.
<dependencies>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring</artifactId>
</dependency>
</dependencies>
In their BOM, all the versions of the Spring Boot dependencies, including the versions of their plugins, are defined in one place.
Another good example is junit:
<!-- use dependency management to import pom -->
<dependencyManagement>
<dependencies>
<dependency>
<groupId>org.junit</groupId>
<artifactId>junit-bom</artifactId>
<version>5.9.2</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
.
.
<dependencies>
<!-- Version is defined in the parent pom -->
<dependency>
<groupId>org.junit.jupiter</groupId>
<artifactId>junit-jupiter</artifactId>
<scope>test</scope>
</dependency>
</dependencies>
These are the two pom files of parent and discovery service sitting inside parent .
<properties>
<maven.compiler.source>17</maven.compiler.source>
<maven.compiler.target>17</maven.compiler.target>
<spring-cloud-version>2021.0.2</spring-cloud-version>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
</properties>
<modules>
<module>product-service</module>
<module>order-service</module>
<module>inventory-service</module>
<module>discovery-service</module>
</modules>
<dependencyManagement>
<dependencies>
<dependency>
<groupId>org.testcontainers</groupId>
<artifactId>testcontainers-bom</artifactId>
<version>1.17.6</version>
<type>pom</type>
<scope>import</scope>
</dependency>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-dependencies</artifactId>
<version>${spring-cloud.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
and discovery service pom
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-autoconfigure</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix-eureka-server</artifactId>
</dependency>
</dependencies>
I am getting these errors .
**Non-resolvable import POM: org.springframework.cloud:spring-cloud-dependencies:pom:${spring-cloud.version} was not found in https://repo.maven.apache.org/maven2 during a previous attempt.
Another error is
org.springframework.cloud:spring-cloud-starter-netflix-eureka-server:jar:unknown was not found in **https://repo.maven.apache.org/maven2 during a previous attempt.
I tried different approaches such as changing this line to
<version>${spring-cloud.version}</version>
to 2021.0.2
but all this didn't help .
I need to use BOMs in my project, so simplify the task of managing dependencies. This is the requirement, I cannot pivot at this stage.
I removed parent spring-boot and added AWS, Spring Boot and Junit5 as BOMs. The issue is, even though I have them, dependencies aren't downloaded correctly. Am I missing some plugins or I am doing something else wrong?
I have tried:
Run code without BOMs
Research BOM usage
Run project with parent of Spring Boot
Research similar projects on GitHub
All of the above worked correctly. The issues I am getting after adding BOMs are:
package org.junit.jupiter.api does not exist
package org.mockito does not exist
cannot find symbol
[ERROR] symbol: class ExtendWith
My pom.xml file:
<?xml version="1.0" encoding="UTF-8"?>
<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">
<modelVersion>4.0.0</modelVersion>
<groupId>org.example</groupId>
<artifactId>bom-experiments</artifactId>
<version>1.0-SNAPSHOT</version>
<properties>
<maven.compiler.source>11</maven.compiler.source>
<maven.compiler.target>11</maven.compiler.target>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<junit-jupiter.version>5.7.2</junit-jupiter.version>
<aws-sdk.version>2.18.16</aws-sdk.version>
<mockito-inline.version>4.8.0</mockito-inline.version>
<org.springframework.boot.version>2.7.5</org.springframework.boot.version>
<org.springframework.version>5.3.24</org.springframework.version>
<lombok.version>1.18.24</lombok.version>
<maven-compiler-plugin.version>3.10.1</maven-compiler-plugin.version>
<maven-surefire-plugin.version>3.0.0-M7</maven-surefire-plugin.version>
<junit-jupiter-params.version>${junit-jupiter.version}</junit-jupiter-params.version>
<kubernetes-maven-plugin.version>1.9.0</kubernetes-maven-plugin.version>
<!-- Plugins -->
<mockito.version>4.9.0</mockito.version>
</properties>
<dependencyManagement>
<dependencies>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-framework-bom</artifactId>
<version>${org.springframework.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-dependencies</artifactId>
<version>${org.springframework.boot.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
<dependency>
<groupId>software.amazon.awssdk</groupId>
<artifactId>bom</artifactId>
<version>${aws-sdk.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
<dependency>
<groupId>org.junit</groupId>
<artifactId>junit-bom</artifactId>
<version>${junit-jupiter.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
<dependency>
<groupId>org.mockito</groupId>
<artifactId>mockito-bom</artifactId>
<version>${mockito.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-actuator</artifactId>
</dependency>
<!-- Secret managers -->
<dependency>
<groupId>software.amazon.awssdk</groupId>
<artifactId>secretsmanager</artifactId>
</dependency>
<dependency>
<groupId>software.amazon.awssdk</groupId>
<artifactId>ssm</artifactId>
</dependency>
<dependency>
<groupId>software.amazon.awssdk</groupId>
<artifactId>sts</artifactId>
</dependency>
<!-- Lombok -->
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<version>${lombok.version}</version>
<scope>provided</scope>
</dependency>
<!-- Testing -->
<dependency>
<groupId>org.junit.jupiter</groupId>
<artifactId>junit-jupiter-engine</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.mockito</groupId>
<artifactId>mockito-inline</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.mockito</groupId>
<artifactId>mockito-junit-jupiter</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.junit.jupiter</groupId>
<artifactId>junit-jupiter-params</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.junit.jupiter</groupId>
<artifactId>junit-jupiter-api</artifactId>
<scope>test</scope>
</dependency>
</dependencies>
<build>
<finalName>bom-experiments</finalName>
<sourceDirectory>${project.basedir}</sourceDirectory>
<testSourceDirectory>${project.basedir}/src/test</testSourceDirectory>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-surefire-plugin</artifactId>
<version>${maven-surefire-plugin.version}</version>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<version>${maven-compiler-plugin.version}</version>
</plugin>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
<version>${org.springframework.boot.version}</version>
</plugin>
</plugins>
</build>
</project>
Am I understanding BOM concept wrong? Why are there no dependencies, even though they are declared in pom.xml? How can I run this code without parent but with BOM?
Importing the BOM via dependencyManagement and scope import copies their dependencyManagement configuration into your current dependencyManagement, as you would have written these dependencyManagement configuration.
The section dependencyManagement should only be used within POM of packaging pom. The resulting pom artefact could be used as parent of other POM.
Therefore you should not use BOM without parent.
Have a closer look at https://maven.apache.org/guides/introduction/introduction-to-dependency-mechanism.html
The issue I had, was related to a misconfiguration in pom.xml
Instead of
<sourceDirectory>${project.basedir}</sourceDirectory>
I have to use
<sourceDirectory>${project.basedir}/src/main</sourceDirectory>
This said, it is possible to package differently from pom packaging, so I can use jar or other alternatives.
I have a parent platform BOM like this:
<project>
<modelVersion>4.0.0</modelVersion>
<groupId>com.company</groupId>
<artifactId>platform-bom</artifactId>
<version>7.0.LTS.9</version>
<packaging>pom</packaging>
<dependencyManagement>
<dependencies>
<!-- Third Party Dependencies Managed Via third-party BOM -->
<dependency>
<groupId>com.company</groupId>
<artifactId>third-party</artifactId>
<version>7.0.LTS.9</version>
<scope>import</scope>
<type>pom</type>
</dependency>
<dependency>
<groupId>com.company</groupId>
<artifactId>api</artifactId>
<version>7.0.LTS.9</version>
</dependency>
</dependencies>
</dependencyManagement>
</project>
I am importing it like this in my project:
<dependencyManagement>
<dependencies>
<dependency>
<groupId>com.company</groupId>
<artifactId>platform-bom</artifactId>
<version>7.0.LTS.9</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
When I am importing api dependency like below, it automatically pulls the version from the imported BOM.
<dependency>
<groupId>com.company</groupId>
<artifactId>api</artifactId>
</dependency>
However when I try to do the same for the third party bom, it is not able to pull the version from the imported BOM.
<dependency>
<groupId>com.company</groupId>
<artifactId>third-party</artifactId>
<type>pom</pom>
</dependency>
Error I get is: Unresolved dependency: 'com.company:third-party:pom:unknown'. Is there a way to pull the version from the BOM which is imported? If not, I think it defeats the purpose of having a BOM in the first place.
I am in the process of upgrading form Apache CXF 2.7.5 to 3.0.2 but I am having the problem below.
When I am including the dependency
<dependency>
<groupId>org.apache.cxf</groupId>
<artifactId>cxf</artifactId>
<version>3.0.2</version>
<type>pom</type>
<scope>import</scope>
</dependency>
to my pom.xml I don't see any .jar files downloaded to my project. There are no errors on the project.
I am using Maven 3.2.3 with Eclipse Juno Release2 and m2e 1.3.1
Why the <type>pom</type> is not getting resolved to the respective jar files of the framework?
Isn't the <type>pom</type> dependencies suppose to give the respective libs automatically? And if not what is the benefit of using them?
UPDATE
This is how my pom.xml look like
<?xml version="1.0" encoding="UTF-8"?>
<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">
<modelVersion>4.0.0</modelVersion>
<groupId>com.test.sysman</groupId>
<artifactId>serviceWrapper</artifactId>
<packaging>war</packaging>
<version>0.0.1-SNAPSHOT</version>
<name>serviceWrapper Maven Webapp</name>
<url>http://maven.apache.org</url>
<dependencyManagement>
<dependencies>
<dependency>
<groupId>org.apache.cxf</groupId>
<artifactId>cxf</artifactId>
<version>3.0.2</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
<dependencies>
<dependency>
<groupId>org.apache.cxf</groupId>
<artifactId>cxf</artifactId>
</dependency>
</dependencies>
<build>
<finalName>serviceWrapper</finalName>
<pluginManagement>
<plugins></plugins>
</pluginManagement>
<plugins></plugins>
</build>
</project>
Thanks
Your dependency scope is import. This means it must be part of a dependency management declaration.
With dependency management you are not directly download dependencies. It is a way to ensure that specific versions of dependencies are required. So further down your pom in the dependencies part if you declare
<groupId>org.apache.cxf</groupId>
<artifactId>cxf</artifactId>
without specifying the version, maven knows which artifacts to download. Also controls versions in transitive dependencies.
Your pom probably refers to a bill of materials (BOM)
For more details see http://maven.apache.org/guides/introduction/introduction-to-dependency-mechanism.html#Dependency_Management
Where do you include this statement?
<scope>import</scope> is only effective inside the <dependencyManagement> section, i.e.
<dependencyManagement>
<dependency>
<groupId>org.apache.cxf</groupId>
<artifactId>cxf</artifactId>
<version>3.0.2</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencyManagement>
Also, it does not download dependency per se, but instead expands referenced pom in place.
If you just need the pom, exclude <scope>import</scope>.