【问题标题】:Android library: Class file not found when "implementation project" is used for module dependency of a libraryAndroid库:当“实现项目”用于库的模块依赖时,找不到类文件
【发布时间】:2019-03-25 01:48:41
【问题描述】:

我正在从事一个包含 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 模块的依赖项我使用implementation project(path: ':Common')

在导入SDK 库的客户端应用程序中,编译器显示以下错误

Error: cannot access Foo
class file for com.acme.Foo not found

(Foo是Common模块中的一个类)

为什么当我导入 SDK 时,没有找到来自 Common 模块的类?我期望编译器将两个模块合并为一个模块。有谁知道我如何解决这个问题?

(我知道一个解决方案是在工件上发布Common,但我不想这样做,因为这只是内部通用代码)。

【问题讨论】:

  • 您是否尝试清理和重建您的项目?也许使缓存无效并重新启动?

标签: android gradle android-gradle-plugin dependencies android-library


【解决方案1】:

我也遇到过同样的问题。

就我而言,我创建了一个kotlin 库并尝试使用java 项目添加。所以请确保为库配置kotlin

现在对我有用。

【讨论】:

    【解决方案2】:

    André Sousa 投票最多的答案是正确的,但只有在您不直接使用库中的任何依赖项时才会有所帮助。

    通常情况下,您有一个“通用”模块,它可能会导入一些通用库(Joda DateTime、firebase、...)。在这种情况下,库中的所有此类依赖项都需要使用 'api' 声明,而不是“实现”。这确保当您的应用程序导入您的 Common 模块时,这些类也可用。

    【讨论】:

      【解决方案3】:

      我自己也有类似的问题。

      视觉帮助是使用Android Studio它自己的项目结构视图:

      文件 -> 项目结构

      那么对于您的:app,您可以检查您拥有的modules dependencies

      如果需要,您可以删除当前的模块依赖项并再次添加它们以进行仔细检查。之后,当您单击“确定”时,gradle 将尝试同步其文件。

      这样您就可以让 Android Studio 完成集成所有模块的工作,并希望它能解决您的问题。


      PS:我认为您以错误的方式导入项目。您应该使用api 而不是implementation。来自文档:

      api: 当一个模块包含一个 api 依赖时,它会让 Gradle 知道模块想要将该依赖项传递到 其他模块,以便它们在运行时和 编译时间。此配置的行为就像 compile(即 现在已弃用),您通常应该只在库中使用它 模块。那是因为,如果一个 api 依赖改变了它的外部 API,Gradle 重新编译所有有权访问该依赖项的模块 在编译时。所以,拥有大量的api依赖可以 显着增加构建时间。除非你想暴露一个 依赖项的 API 到单独的测试模块,应用程序模块应该改为 使用实现依赖。

      查看官方文档:https://developer.android.com/studio/build/gradle-plugin-3-0-0-migration.html#new_configurations

      【讨论】:

      • @DiegoPalomar 这能解决您的问题吗?
      • “api”而不是“实施”引用解决了我的问题。谢谢!
      【解决方案4】:

      这是 gradle 模块的预期行为;正如您所推测的,将每个作为单独的工件发布(并在 pom 文件中列出依赖项)是唯一受支持的用法。

      https://github.com/adwiv/android-fat-aar 有一个插件可以满足您的需求,但它不再维护,因此您的里程可能会有所不同。 或者,您可以通过更新您的 SDK sourceSets 以直接指向公共模块源来获得类似的结果,并完全删除 gradle 依赖项。找不到一个好的链接,但它应该是可能的。这确实删除了模块的所有内置处理,但可能更好地匹配您使用模块的方式。

      【讨论】:

        【解决方案5】:

        api project(path: ':Common')替换implementation project(path: ':Common') 关于 api 和 implementation 的区别你可以查看this article

        【讨论】:

        • 它没有解决问题,我仍然得到同样的错误?
        • 请分享您的所有模块 build.gradle 文件
        猜你喜欢
        • 2018-09-08
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2018-09-17
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多