I have two maven projects.
-- my-common-lib
-- my-web-application
my-common-lib - contains just a pom which all dependencies.
my-web-application - is a web application.
Is there a maven plugin which I can define in "my-application" pom that makes that all dependencies defined in "my-common-lib" should not be added to "WEB-INF/lib" when building my-web-application project .
Thanks
Sundar
You can use the following to import dependencies from the other artifact.
<dependencyManagement>
<dependencies>
<dependency>
<groupId>com.sample<groupId>
<artifactId>myartifact</artifactId>
<version>0.0.1</version>
<scope>import</scope>
<type>pom</type>
</dependency>
</dependencies>
</dependencyManagement>
Related
My company has 3 Maven projects organized as follows:
Project A depends on Project B.
Project B depends on Project C. (Project B has set Project C as an Optional dependency in their POM)
I am the owner of Project A. I would like to add Project C as a direct dependency in my POM. However, I do not want to be responsible for keeping the version of Project C up to date. Is there a way I can inherit the version of Project C specified in Project B's POM at all times?
If you don't control project B, it's not possible, except possibly with some plugin hackery.
If you do control project B then you can declare a dependency management section in that project which you can additionally import into project A.
Project B POM
<dependencyManagement>
<groupId>com.foo</groupId>
<artifactId>project-c</artifactId>
<version>1.2.3</version>
</dependencyManagement>
<dependencies>
<dependency>
<groupId>com.foo</groupId>
<artifactId>project-c</artifactId>
<!-- no need for version here, comes from dependencyManagement -->
<optional>true</optional>
</dependency>
</dependencies>
Project A POM
<properties>
<!-- using a property isn't necessary, but ensures the
POM import and dependency stay in sync -->
<project.b.version>2.3.4</project.b.version>
</properties>
<dependencyManagement>
<dependencies>
<dependency>
<groupId>com.foo</groupId>
<artifactId>project-b</artifactId>
<version>${project.b.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
<dependencies>
<dependency>
<groupId>com.foo</groupId>
<artifactId>project-b</artifactId>
<version>${project.b.version}</version>
</dependency>
<dependency>
<groupId>com.foo</groupId>
<artifactId>project-c</artifactId>
<!-- version is not necessary, imported from project-b's dependency management -->
</dependency>
</dependencies>
This will mean Project A will default to Project B for all dependencies in B's dependency management section. I don't think there's a way to restrict it to just a specific one. I doubt you'll care but just something to be aware of.
Any versions that Project A defines, either in its own dependency management or directly in <dependencies>, will override any version brought in from Project B's dependency management.
I've been trying to override a transitive dependency version in one of my projects. I found the following sample project on github to experiment on ( https://github.com/Richou/swagger-codegen-maven-plugin). The parent pom of this project contains a dependency for swagger-codegen. Swagger-codegen in turn has a dependency called slf4j-ext whose version is 1.6.3. I want to upgrade/override the version of slf4j-ext to 1.7.30 from the parent pom. I tried adding the required slf4j-version inside the property tag in the parent pom but it didn't work when I checked the maven dependency tree. What is the correct method to do it?
<dependency>
<groupId>io.swagger</groupId>
<artifactId>swagger-codegen</artifactId>
<version>2.1.2</version>
</dependency>
</dependencies>
<properties>
<slf4j-version>1.7.30</slf4j-version>
<java.version>1.7</java.version>
</properties>
You can add the slf4j-ext with the version you want in the dependencyManagement section of your parent pom.
<dependencyManagement>
<dependencies>
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-ext</artifactId>
<version>${slf4j-version}</version>
</dependency>
</dependencies>
</dependencyManagement>
In my AWS lambda java project, I included the following snippet in my pom.xml.
<!-- https://mvnrepository.com/artifact/software.amazon.awssdk/bom -->
<dependency>
<groupId>software.amazon.awssdk</groupId>
<artifactId>bom</artifactId>
<version>2.13.39</version>
<type>pom</type>
</dependency>
After I execute maven update on the project and try to import software.amazon.awssdk.* it shows an error message saying it can't find any such package.
Is it because the packages are not installed properly by maven?
The bom should go in a dependancy management
->
<dependencyManagement>
<dependencies>
<dependency>
<groupId>software.amazon.awssdk</groupId>
<artifactId>bom</artifactId>
<version>2.13.39</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
A BOM is a list of versions for dependencies. It goes into <dependencyManagement>.
This means that a BOM does not add any dependencies to the project. DependencyManagement only fixes versions for dependencies that appear otherwise.
So you need to declare all relevant dependencies in your <dependencies> section.
I'm writing a library that I'd like to compile into implementable jar which then will be used in other projects / tests.
In my library I depend on various jars: okHttp, guava, etc., What I want to do is to tell maven not to put those dependencies into the final JAR but make that projects / modules that depend on this library provide those dependencies
How can this be done in maven?
library pom.xml
<groupId>com.example</groupId>
<artifactId>testing-library</artifactId>
<packaging>jar</packaging>
<version>1.0.0-SNAPSHOT</version>
<dependencies>
<dependency>
<groupId>com.google.guava</groupId>
<artifactId>guava</artifactId>
<version>28.2-jre</version>
<scope>compile</scope>
</dependency>
<dependency>
<groupId>com.squareup.okhttp3</groupId>
<artifactId>okhttp</artifactId>
<version>4.3.1</version>
<scope>compile</scope>
</dependency>
</dependencies>
implementation module pom.xml
<groupId>com.example</groupId>
<artifactId>implementation-</artifactId>
<version>1.0.0-SNAPSHOT</version>
<dependencies>
<dependency>
<groupId>com.example</groupId>
<artifactId>testing-library</artifactId>
<version>1.0.0-SNAPSHOT</version>
<scope>test</scope>
</dependency>
</dependencies>
But I'm getting java.lang.NoClassDefFoundError: com/google/common/base/Preconditions error
If you put code into src/test/java, this code will not be part of the final jar. The code is meant for tests during the build of the jar.
If your library is a helper library for tests, put the code into src/main/java and reference it in other projects with <scope>test</scope>.
BTW, don't use Maven shade plugin or Maven assembly plugin for a library. These are mainly meant for standalone jars that run on their own.
Ok, I solved the issue. It seems that the generated POM.xml for the testing-library did not contain any dependencies.
I was using mvn install:install-file ... -DgeneratePom=true for installing jar into local repository for quick debugging and the pom generated this way seemed to be lacking library dependencies'
Here is my situation:
I created a new artifact in a library called 'web-ng-framework', and moved code into it from an old artifact in the library, 'web'
I deleted the 'web' artifact
And here is the problem:
ProjectA uses an older version of the library, and so it has a compile dependency on 'web'
ProjectB depends on ProjectA
ProjectB uses the latest version of the library, so when ProjectB is built, it contains both the 'web' and 'web-ng-framework' libraries, causing a possible conflict
Does anyone know how I can solve this? Thanks!
EDIT:
Would doing 'relocation' of 'web' to 'web-ng-framework' maybe work better? In ProjectA, I could include a dependency on 'web' so that Maven would see that what it really needs is 'web-ng-framework'. Would that work?
When including ProjectA in ProjectB exclude web. Like this
<dependency>
<groupId>your.group</groupId>
<artifactId>projectA</artifactId>
<exclusions>
<exclusion>
<groupId>your.group</groupId>
<artifactId>web</artifactId>
</exclusion>
</exclusions>
</dependency>
A classic solution to this problem is the 'Version 99' hack.
To do this, use the following in your root pom:
<dependencyManagement>
<dependency>
<groupId>your.group</groupId>
<artifactId>web</artifactId>
<version>99.0-does-not-exist</version>
</dependency>
</dependencyManagement>
Then put an empty web-99.0-does-not-exist.pom and web-99.0-does-not-exist.jar in your repository.
This ensures that every project that inherits from this root pom will not get the old version of the web.jar anymore.
I suggest that you use optional dependencies
This can be acheived by making web depencency optional in projectA.
<project>
<groupId>some.group</groupId>
<artifactId>projectA</artifactId>
...
<dependencies>
<!-- declare the dependency to be set as optional -->
<dependency>
<groupId>some.group</groupId>
<artifactId>web</artifactId>
<version>1.0</version>
<scope>compile</scope>
<optional>true</optional>
</dependency>
</dependencies>
</project>
When declaring some other project that depends on projectA the web dependency will not be included.
<project>
<groupId>some.group</groupId>
<artifactId>projectB</artifactId>
...
<dependencies>
<dependency>
<groupId>some.group</groupId>
<artifactId>projectA</artifactId>
<version>1.0</version>
</dependency>
<dependency>
<groupId>some.group</groupId>
<artifactId>web-ng-framework</artifactId>
<version>1.0</version>
</dependency>
</dependencies>
</project>
Now projectB will only have a dependency on projectA and web-ng-framework, not web.