Declaring multiple artifactId under one groupId in a pom.xml - java

I'm declaring quite a few dependencies within one package in a Maven pom.xml, and the document is getting very long and difficult to maintain as is, even without a separate dependency block for each referenced artifact. Instead of doing this:
<dependencies>
<dependency>
<groupId>com.test.foo</groupId>
<artifactId>bar1</artifactId>
<version>1.0.0-SNAPSHOT</version>
<type>war</type>
</dependency>
<dependency>
<groupId>com.test.foo</groupId>
<artifactId>bar2</artifactId>
<version>1.0.0-SNAPSHOT</version>
<type>war</type>
</dependency>
<dependency>
<groupId>com.test.foo</groupId>
<artifactId>bar3</artifactId>
<version>1.0.0-SNAPSHOT</version>
<type>war</type>
</dependency>
</dependencies>
Is it possible (and I'd be willing to work with a plugin, if necessary) to do something like this:
<dependencies>
<dependency>
<groupId>com.test.foo</groupId>
<artifactId>bar1</artifactId>
<artifactId>bar2</artifactId>
<artifactId>bar3</artifactId>
<version>1.0.0-SNAPSHOT</version>
<type>war</type>
</dependency>
</dependencies>

No. But if you own those dependencies (I assume from your code that you do) you can have a module aggregating all those dependencies, then you can depend on that module. Or if working in a multi module project you can create a parent pom to define the dependencies from your project so you don't repeat it everywhere.

Related

How can I get a dependencyNode's premanagedVersion in Maven 3.0+ API?

I have a pom-packaging project called "testMultiManage". The following content is in its pom.xml:
...
<modules>
<module>sub1</module>
<module>sub1/subsub1</module>
</modules>
<dependencyManagement>
<dependencies>
<dependency>
<groupId>groupC</groupId>
<artifactId>C</artifactId>
<version>2.0</version>
</dependency>
</dependencies>
</dependencyManagement>
...
In its sub project "sub1", the content in the pom.xml is
<dependencies>
<dependency>
<groupId>groupB</groupId>
<artifactId>B</artifactId>
<version>1.0</version>
</dependency>
</dependencies>
And what in B-1.0.pom is
<dependencies>
<dependency>
<groupId>groupC</groupId>
<artifactId>C</artifactId>
<version>1.0</version>
</dependency>
...
<dependencies>
So, according to maven's management control rules, "sub1" will depend on B-1.0, and then transitively depend on C-2.0.
When I use the following code to get the DependencyGraph with Maven 3.0+ API
DefaultProjectBuildingRequest defaultProjectBuildingRequest = new DefaultProjectBuildingRequest();
defaultProjectBuildingRequest.setRepositorySession(getVerboseRepositorySession(project));
defaultProjectBuildingRequest.setProject(project);
defaultProjectBuildingRequest.setRemoteRepositories(remoteRepositories);
defaultProjectBuildingRequest.setResolveDependencies(true);
org.apache.maven.shared.dependency.graph.DependencyNode dependencyNode = dependencyGraphBuilder.buildDependencyGraph(defaultProjectBuildingRequest, null);
, I get the dependency relationships correctly for project "sub1". However, the premanagedVersion of "C-2.0" is null.
So how can I use Maven 3.0+ API to get a dependency node's premanagedVersion? Thanks a lot!

Java/Gradle: Any tips on centralizing dependency version control for a multiple repository project?

I am tired of having to manually change the dependency version for every repository and run the build and tests.
Are there any good solutions/tools out there to centralize this, so that you only have to change the version in one file?
A requirement is that you still can override the desired version from the local repository.
In my Maven projects i use a parent pom for dependency management. I use the "dependencyManagement" tag in parent pom for declare al available dependencies and his versions for child modoules.
DIRECTORY HERARCHY
- project-name
- module-A
- pom.xml
- pom.xml
In parent pom.xml I specify the depencyManagement tag:
<dependencyManagement>
<dependencies>
<dependency>
<groupId>com.test</groupId>
<artifactId>artifact</artifactId>
<version>1.0</version>
</dependency>
</dependencies>
</dependencyManagement>
In module-A pom.xml there is something like:
<parent>
<artifactId>module-A</artifactId>
<groupId>com.test</groupId>
<version>1.0</version>
</parent>
<dependencies>
<!-- The version is inherited from parent pom -->
<dependency>
<groupId>com.test</groupId>
<artifactId>artifact</artifactId>
</dependency>
</dependencies>
This way permits change the version of dependencies only in parent pom.xml. Al child modules will use it.
You can find more details in Maven's official documentation: https://maven.apache.org/guides/introduction/introduction-to-dependency-mechanism.html

How to bundle/package latest version of custom library in maven web project without updating pom.xml?

I have a custom library - Dao.jar which contains the database persistence logic.
I push this jar to artifactory with new version each time there is a change in code as shown below :
mvn install:install-file -Dfile=C:\*****\target\Dao.jar -DgroupId=non-public.com.karthik -DartifactId=dao -Dversion=2.0 -Dpackaging=jar
I have another maven web project which has a dependency on this jar. This jar is also packaged/bundled in the maven webapp project/war.
<dependency>
<groupId>non-public.com.karthik</groupId>
<artifactId>dao</artifactId>
<version>2.0</version>
</dependency>
Currently, I am changing the version of dao dependency in the pom.xml & re-building the maven webapp project each time a new version of Dao.jar is available in the artifactory.
Is there any option to build the maven project with the latest version of Dao.jar without manually changing the dependency version in the pom.xml?
When Maven searches for a dependency, it first checks the local repository (~/.m2/repository). If it's not found, it tries other resources, such as remote repositories defined in the POM file or in the settings file (~/.m2/settings.xml).
By that logic, if you try to use a version of a local project that's not yet installed to the local repository, Maven will never be able to find it to use in another project.
To avoid changing version numbers all the time and manually building both projects. You could create a parent POM for both projects. The parent would then be able to recognize that one of the child projects depends on the other and build them in the correct order.
Based on Luciano's inputs, I have created a multi-module maven project/parent POM with 2 modules(dao & web)
Parent
<groupId>com.karthik</groupId>
<artifactId>test</artifactId>
<packaging>pom</packaging>
<version>1.0-SNAPSHOT</version>
<dependencyManagement>
<dependencies>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-core</artifactId>
<version>3.0.5.RELEASE</version>
</dependency>
<dependency>
<groupId>oracle</groupId>
<artifactId>ojdbc6</artifactId>
<version>11.2.0.3</version>
</dependency>
..........
</dependencies>
</dependencyManagement>
<modules>
<module>web</module>
<module>dao</module>
</modules>
Child module # 1 - dao
<parent>
<groupId>com.karthik</groupId>
<artifactId>test</artifactId>
<version>1.0-SNAPSHOT</version>
</parent>
<artifactId>dao</artifactId>
<packaging>jar</packaging>
<dependencies>
<dependency>
<groupId>oracle</groupId>
<artifactId>ojdbc6</artifactId>
</dependency>
.........
</dependencies>
Child module # 2 - web(declared dao dependency in POM)
<parent>
<groupId>com.karthik</groupId>
<artifactId>test</artifactId>
<version>1.0-SNAPSHOT</version>
</parent>
<artifactId>web</artifactId>
<packaging>war</packaging>
<dependencies>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-core</artifactId>
</dependency>
<dependency>
<groupId>com.karthik</groupId>
<artifactId>dao</artifactId>
<version>1.0-SNAPSHOT</version>
</dependency>
.........
</dependencies>
When I run mvn package command at root path of parent pom, both modules - web.war and dao.jar are built. This method ensures always the latest version of dao.jar is packaged in web.war.

Missing artifact net.sf.jung:jung2:jar:2.0

jung2 is in maven repository, here and here.
But my Eclipse does not finding it out:
Code is here:
<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>tests.jung</groupId>
<artifactId>TryJung</artifactId>
<version>0.0.1-SNAPSHOT</version>
<dependencies>
<dependency>
<groupId>net.sf.jung</groupId>
<artifactId>jung2</artifactId>
<version>2.0</version>
</dependency>
</dependencies>
</project>
UPDATE
Sorry can't accept answers about dependency type, because it is not complete. The code for jung dependency was taken from Maven repository directly:
So, I need an explanation, why doesn't code, taken from repository site, work actually.
What is happening here, who is "guilty"?
As already said, you are addressing a pom file. Which is, in a sense, correct, but if you want to compile you will need to add the actual jars in the dependencies section, such as:
<dependencies>
<dependency>
<groupId>net.sf.jung</groupId>
<artifactId>jung2</artifactId>
<version>${jung.version}</version>
<type>pom</type>
</dependency>
<dependency>
<groupId>net.sf.jung</groupId>
<artifactId>jung-api</artifactId>
<version>${jung.version}</version>
<scope>compile</scope>
</dependency>
<dependency>
<groupId>net.sf.jung</groupId>
<artifactId>jung-visualization</artifactId>
<version>${jung.version}</version>
<scope>compile</scope>
</dependency>
<dependency>
<groupId>net.sf.jung</groupId>
<artifactId>jung-graph-impl</artifactId>
<version>${jung.version}</version>
<scope>compile</scope>
</dependency>
<dependency>
<groupId>net.sf.jung</groupId>
<artifactId>jung-algorithms</artifactId>
<version>${jung.version}</version>
<scope>compile</scope>
</dependency>
<dependency>
<groupId>net.sf.jung</groupId>
<artifactId>jung-io</artifactId>
<version>${jung.version}</version>
<scope>compile</scope>
</dependency>
</dependencies>
Do not forget to define the version property also in the properties section:
<properties>
<jung.version>2.0.1</jung.version>
</properties>
Hope this helps.
The problem is simply the artifact you are adressing is a pom file and not a jar file. That's the reason for the message.
just stumbled into the same problem pit. apparently these are pom files purely for building/documenting (all) sub-projects (or submodules in maven speak) of a project (in this case jung2)
they can't be used as a dependency in a useful way
actually you can depend on them with <type>pom</type> but will just include the dependencies of that pom but not it's modules.
see here for a more complete explanation:
How to use POMs as a dependency in Maven?

How to use POMs as a dependency in Maven?

Is there a way to add a pom type dependency to my POM and get all its modules?
JavaMail is a good example. Maven Central Repo has a parent POM called: com.sun.mail:all:1.5.0 with modules: mail, mailapi, mailapijar, smtp, imap, gimap, pop3, and dsn.
However, the "all" artefact only has a single file: pom.xml Is there a way to add this "all" artefact as a dependency to my POM and get all its modules? I am 90% sure this is not the right way to use dependencies in Maven, but I want to hear it from an expert on The Stack.
Ideas:
<dependencies><dependency>...<type>pom</type></dependency></dependencies>
<dependencyManagement><dependencies><dependency>...<type>pom</type><scope>import</scope></dependency></dependencies></dependencyManagement>
Related: Netbeans: maven dependencies of type pom
You have to go with
<dependencies>
<dependency>
<groupId>com.my</groupId>
<artifactId>commons-deps</artifactId>
<type>pom</type>
</dependency>
</dependencies>
This will transitively add all dependencies declared in com.my:commons-deps to your current POM.
Using
<dependencyManagement>
<dependencies>
<dependency>
<groupId>...</groupId>
<artifactId>...</artifactId>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
works as a simple 'include' of artifacts versions in your dependency management. Thus, it won't add any dependency in your project.
I believe you can create your own POM which aggregates the dependencies you want, and then in your original project add a dependency on that aggregate pom. You will still have to add dependencies on each individual module in your dependency POM, but it will be abstracted from the actual project POMs and allows those dependencies to be managed in one place, which could become useful if you end up having multiple projects that depend on that set of dependencies.
In your example you could create a new pom like this:
<?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.mycompany</groupId>
<artifactId>mail-deps</artifactId>
<version>1.0.0</version>
<packaging>pom</packaging>
<dependencies>
<dependency>
<groupId>com.sun.mail</groupId>
<artifactId>mail</artifactId>
<version>1.5.0</version>
</dependency>
<dependency>
<groupId>com.sun.mail</groupId>
<artifactId>mailapi</artifactId>
<version>1.5.0</version>
</dependency>
<dependency>
<groupId>com.sun.mail</groupId>
<artifactId>mailapijar</artifactId>
<version>1.5.0</version>
</dependency>
<dependency>
<groupId>com.sun.mail</groupId>
<artifactId>imap</artifactId>
<version>1.5.0</version>
</dependency>
<dependency>
<groupId>com.sun.mail</groupId>
<artifactId>gimap</artifactId>
<version>1.5.0</version>
</dependency>
<dependency>
<groupId>com.sun.mail</groupId>
<artifactId>pop3</artifactId>
<version>1.5.0</version>
</dependency>
<dependency>
<groupId>com.sun.mail</groupId>
<artifactId>dsn</artifactId>
<version>1.5.0</version>
</dependency>
</dependencies>
</project>
Then in your original project just add:
<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">
...
<modules>
<module>src/main/java/com/mycompany</module>
</modules>
...
<dependencies>
<dependency>
<groupId>com.mycompany</groupId>
<artifactId>mail-deps</artifactId>
<version>1.0.0</version>
<type>pom</type>
</dependency>
</dependencies>
</project>
The short answer: You cannot do this in Maven.
The other answers make only the "all" POM a dependency. Does not solve the issue. Another answer tries to import the dependencies of the "all" POM. I don't need the dependencies; I need the (child) modules of the "all" POM. Again, does not solve the issue.
Side note: I was using the JavaMail library incorrectly. I only needed to add one dependency: com.sun.mail:javax.mail:1.5.0
If the pom you're trying to import, contains dependencies defined in a <dependencies/> section, and you would like to import them all, you can try the code below.
(Disclaimer: I haven't done this in a while): in your <dependencyManagement/> section, add the pom dependency like this:
<dependencyManagement>
<dependencies>
<dependency>
<groupId>kung.fu<groupId>
<artifactId>ninja</artifactId>
<version>1.2.3</version>
<scope>import</scope>
<type>pom</type> <!-- Not too sure if you needed this
when it's scoped as import,
but just in case -->
</dependency>
</dependencies>
</dependencyManagement>
It may as well be the case that you define the dependency directly in the <dependencies/> section not needing the <dependencyManagement/> bit, but as far as I recall, it should be scoped import as shown above.
As someone already wrote above : You can't do it . But this is what i did and it worked .
Lets assume you have some pom file (JavaMail in your example) with following :
<type>pom</type>
<dependencyManagement><dependencies><dependency></dependencyManagement>
And You want copy all jars mentioned in this pom to some place .
This is what i did and it is fast working solution
Open original pom and just copy-paste all dependencies section from original pom file to your new pom as is .
Of course use maven dependency plugin to copy all .

Categories

Resources