当在使用gradle的子项目中使用时,为什么缺少杰克逊库依赖项?

问题描述

我有一个gradle项目P,它具有模块A和B。模块A具有以下jackson依赖性:

...
dependencies {
    ...
    compile 'com.fasterxml.jackson.core:jackson-core:2.12.0-rc1'
    compile 'com.fasterxml.jackson.core:jackson-annotations:2.12.0-rc1'
    compile 'com.fasterxml.jackson.core:jackson-databind:2.12.0-rc1'
    compile 'com.fasterxml.jackson.dataformat:jackson-dataformat-xml:2.12.0-rc1'
    ...
}
...

并且模块B使用模块A,并且不需要包含此依赖项,因为jackson用法封装在模块A中。但是,当从模块B执行的代码到达使用该模块从模块A调用代码的语句时,我遇到异常:

java.lang.NoClassDefFoundError: com/fasterxml/jackson/dataformat/xml/XmlMapper

如果我将相同的依赖项添加到模块的B gradle.build文件中,则该代码将起作用。 问题是,如果模块A不使用该库,为什么还要包括它们? 不应编译,打包模块A中的依赖项,以便在其他地方使用模块A时,其代码有效(使用本示例中的jackson库之类包含的依赖项)

解决方法

免责声明:我不知道Gradle,但这听起来像是Maven和Gradle常见的问题。

您可以构建模块但不能运行模块的事实意味着您没有将可传递依赖项带入Spring Boot胖子罐中。杰克逊对元数据文件,类加载器等没有任何奇怪的处理。

鉴于您尚未共享太多构建文件,找出是否已排除Jackson的XML模块的最简单方法是仅运行jar -xvf target/app.jar并检查输出是否在其中。

如果不是,请寻找与Maven依赖插件的依赖树目标等效的Gradle,该目标将向您显示整个传递依赖树。如果将其排除在外,您肯定会在依赖项转储中看到它。