当 gradle 中排除库依赖项时,幕后发生了什么?

What's happening under the hood when a library dependency is excluded in gradle?

今天我开始为我的公司构建一个库,这样我们就可以避免在我们的一些应用程序中出现一些重复代码。该库使用了一些在应用程序中重复的依赖项。在这种情况下,Retrofit 和 Eventbus。无论如何,当我包含我的图书馆时,它看起来像这样:

implementation (project(":mylib")

知道我将使用 Eventbus 以及其他一些依赖项,我想测试排除它们以避免重复的依赖项。因此,我将 Eventbus 添加到应用程序的 gradle 文件中,并从我的库中排除了 Eventbus。

implementation 'org.greenrobot:eventbus:3.0.0'
implementation (project(":mylib")){
    exclude module: 'eventbus'
}

现在我完全意识到我不能通过仅导入 mylib 将 Eventbus 包含在应用程序中,当然我已经排除了过去的依赖项以避免构建冲突所以我熟悉用法,但我只是想试验一下,因为我突然想到,我真的不知道这种排除在幕后发生了什么。术语排除意味着(对我而言)这种依赖性在排除点不是编译期,但是,情况并非如此,因为第 3 方库(在这种情况下为 Eventbus)似乎仍然可以很好地执行 mylib,如果它没有编译,那么由于奇怪的库依赖性问题,世界范围内的代码都会崩溃。那么这里到底发生了什么?它是否仍然为库编译,并且仍然为应用程序编译,但不知何故这些依赖关系只是分开了?如果是这样,这似乎并不是那么有效,因为您仍然会复制项目中的所有方法。

显然我对此了解有限,所以如果有人能澄清这一点,我将不胜感激。

AAR/JAR 库不包含存档中的依赖项 类, 它只包含您的代码。通常它们存储在类似 maven 的存储库中,带有包含其依赖项列表的 .pom 文件。 当您将它添加到 build.gradle 文件中的项目时,它只会下载 AAR/JAR、解析 .pom 文件并下载列出的所有依赖项(对每个库递归重复该过程,直到它获得所有依赖项)。 这意味着如果模块也依赖于您的应用使用的相同库,则您不必排除模块。

是否将库添加为本地模块 implementation (project(":mylib") 它做完全相同的事情,但是对于子项目的 build.gradle

中列出的每个依赖项

如果排除传递依赖性,它只会在解析 .pom 文件时忽略具有指定名称的工件