没有工作解决方案的Java传递依赖问题
我正在使用Maven来管理我的项目依赖项。 我的依赖树在包B上有冲突,如:
A -> B (v1.4) C -> B (v1.5)
事实certificate,程序包A
依赖于在v1.5中修复的错误,而程序包C
需要1.5中不在1.4中的function。
具有大量依赖项的大型Java项目如何管理这些类型的问题? 即使包装A似乎在v1.5的表面层面上工作,我仍然觉得在所有边缘情况下假设它将像以前一样工作会有风险。
请注意,这是一种假设情况,因此无需知道这些代表哪些包。
只有Maven和经典的jar子,没有结果:这就是为什么我们称它为“依赖地狱”(“dll hell”是原始的,注意押韵:)
然而,有一种技术专门用于解决这个问题:OSGi。 通过大规模复杂和复杂的类加载器杂耍,OSGi设法满足每个包的特定依赖要求。 Bundle A可以使用Bundle B v1.4,而Bundle C可以使用B v1.5。
OSGi已经存在了十多年了,它似乎既不茁壮成长也不会消亡; 相反,它正在以冰川的速度获得采用,因此越来越多的JAR升级到OSGi捆绑。
最后,只有一个依赖项在运行时生效,您可以使用
和
来控制传递依赖项
-
和
每当依赖项发生冲突时,Maven就会根据最近获胜策略选择一个版本,这意味着将选择与模块相关的任何版本更接近您的模块,并忽略所有其他版本。 如果v1.4
在依赖树中更接近,即使它比v1.5
更旧,它也会被选中。
要控制要使用的依赖项,可以在模块中定义dependencyManagement
以设置Maven应使用的版本:
com.example packageB 1.5
或者,您可以在具有传递依赖性的依赖项中排除要忽略的版本:
com.example packageA com.example packageB
这不是maven问题 – 这是一个java问题。 Maven只是暴露它,并使识别和管理问题成为可能。 有许多解决方案:大多数(如果不是全部)解决方案都是作为独立的类加载器实现的,通常是在Java EE或OSGi容器中。
另外:作为一般规则,不要在项目中允许传递依赖 – 如果使用类,则将第一类依赖项添加到它所属的库中。 至少通过这种方式,您可以轻松查看依赖项的位置以及问题所在的位置。