我正在一个有3个模块的项目中工作,如下所示:
Project
|
|-- Common
|
|-- SDK
|
|-- App
Common
是一个其他所有模块都依赖的Android库模块,但是我不必在任何地方发布它,因为它仅包含其他模块的通用代码。另一方面,SDK
是另一个Android库项目,必须在我们的内部工件上发布。
App
是SDK的示例项目。我可以毫无问题地发布SDK
工件,但是当我将其导入客户端应用程序时,编译失败,因为找不到Common
模块中的任何类。
对于SDK模块所依赖的第三方依赖项,我使用implementation
(例如implementation 'com.squareup.okhttp3:okhttp:3.11.0'
,并且所有那些依赖项都已成功添加到SDK
POM文件中),并且依赖于我使用Common
的{{1}}模块。
在导入implementation project(path: ':Common')
库的客户端应用程序中,编译器显示以下错误
SDK
(Foo是“通用”模块中的类)
为什么当我导入Error: cannot access Foo
class file for com.acme.Foo not found
模块时,找不到SDK
模块中的所有类?我期望的是编译器将两个模块合并为一个模块。有谁知道我该如何解决这个问题?
(我知道一种解决方案是在工件上发布Common
,但我不想这样做,因为这只是内部通用代码)。
答案 0 :(得分:3)
用implementation project(path: ':Common')
补充api project(path: ':Common')
关于api和实现之间的区别,您可以检查this article。
答案 1 :(得分:1)
这是gradle模块的预期行为;如您所料,唯一支持的用法是将它们作为单独的工件发布(并在pom文件中列出依赖项)。
https://github.com/adwiv/android-fat-aar中有一个插件可以满足您的需要,但是不再维护,因此您的行程可能会有所不同。 另外,您可以通过更新SDK的SourceSet使其直接指向通用模块源,并完全删除gradle依赖项来获得类似的结果。为此找不到很好的链接,但是应该可以的。这确实删除了模块的所有内置处理,但可能会更好地匹配您使用模块的方式。
答案 2 :(得分:1)
我自己也遇到过类似的问题。
视觉帮助是使用Android Studio
自己的项目结构视图:
文件->项目结构
然后为您的:app
检查您拥有的modules dependencies
:
如果需要,可以删除当前模块依赖项,然后再次添加它们,以进行仔细检查。之后,当您单击“确定”时,gradle将尝试同步其文件。
通过这种方式,您可以让Android Studio完成集成所有模块的工作,并希望它将解决您的问题。
PS::我认为您导入的项目是错误的方式。您应该使用api
而不是implementation
。从文档中:
api::当模块包含api依赖项时,它将让Gradle 知道该模块希望将该依赖关系可传递到 其他模块,以便在运行时和 编译时间。此配置的行为就像编译( 现在已弃用),通常只应在库中使用此功能 模块。这是因为,如果api依赖项更改了其外部 API,Gradle重新编译所有可以访问该依赖项的模块 在编译时。因此,拥有大量的api依赖项可以 大大增加了构建时间。除非您想公开 依赖项的API到单独的测试模块,应用模块应改为 使用实现依赖。
检查官方文档:https://developer.android.com/studio/build/gradle-plugin-3-0-0-migration.html#new_configurations
答案 3 :(得分:0)
我也遇到过同样的问题。
就我而言,我创建了一个kotlin
库,并尝试使用Java项目添加。因此,请确保应为库配置kotlin
。
现在对我有用。
答案 4 :(得分:0)
安德烈·索萨(AndréSousa)投票最多的答案是正确的,但这仅在您不直接使用库中的任何依赖项时才有帮助。
常见的情况是您有一个“通用”模块,该模块可能会导入一些通用库(Joda DateTime,firebase等)。在这种情况下,库中的所有此类依赖项都需要使用“ api”声明,而不是“实现”。这样可以确保当您的应用程序导入Common模块时,这些类也可用。
答案 5 :(得分:-1)
因为SDK是客户端所在的库,所以支持@Aolphn用implementation project(path: ':SDK')
替换api project(path: ':SDK')
。