考虑Java库的以下项目POM:
<?xml version="1.0" encoding="UTF-8"?>
<?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>foo</groupId>
<artifactId>lib</artifactId>
<version>1</version>
<dependencyManagement>
<dependencies>
<dependency>
<groupId>commons-codec</groupId>
<artifactId>commons-codec</artifactId>
<version>1.10</version>
</dependency>
</dependencies>
</dependencyManagement>
<dependencies>
<dependency>
<groupId>org.apache.httpcomponents</groupId>
<artifactId>httpclient</artifactId>
<version>4.5.3</version>
</dependency>
</dependencies>
</project>
根据需要,此项目依赖于commons-codec 1.10版:
$ mvn dependency:list | grep commons-codec
[INFO] commons-codec:commons-codec:jar:1.10:compile
但是,如果此库用作下游项目中的依赖项,则传递的commons-codec版本将是1.9,因为org.apache.httpcomponents:httpclient:4.5.3
取决于1.9,而不是1.10。
这是一个应用程序POM,它说明了这个问题:
<?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>foo</groupId>
<artifactId>app</artifactId>
<version>1</version>
<dependencies>
<dependency>
<groupId>foo</groupId>
<artifactId>lib</artifactId>
<version>1</version>
</dependency>
</dependencies>
</project>
已解决的依赖项:
mvn dependency:list | grep commons-codec
[INFO] commons-codec:commons-codec:jar:1.9:compile
这是Maven中的错误吗?或预期的行为?
如果有意,是否有一种方法 - 在POM中没有硬编码传递依赖关系 - 继承版本,因为它们在构建库组件时被解析了?
一种解决方案是继承库的依赖关系管理,如下所示:
<?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>foo</groupId>
<artifactId>app</artifactId>
<version>1</version>
<dependencyManagement>
<dependencies>
<dependency>
<groupId>foo</groupId>
<artifactId>lib</artifactId>
<version>1</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
<dependencies>
<dependency>
<groupId>foo</groupId>
<artifactId>lib</artifactId>
<version>1</version>
</dependency>
</dependencies>
</project>
然后它起作用:
mvn dependency:list | grep commons-codec
[INFO] commons-codec:commons-codec:jar:1.10:compile
但这是最好的/唯一的解决方案吗?如果必须始终对每个依赖项执行此操作,以确保传递版本实际匹配,这似乎是不幸/无意的。
我还发布了此代码as a gist。