【问题标题】:How to prevent Hilt from picking dependency from a library?如何防止 Hilt 从库中选择依赖项?
【发布时间】:2020-08-06 04:31:44
【问题描述】:

好的,让我们把这个简单点。

我创建了一个名为my-network-library 的简单库,其中包含两个类。第一个是名为 BaseNetworkModule 的 Hilt 模块

@Module
@InstallIn(ApplicationComponent::class)
object BaseNetworkModule {

    // Client
    @Singleton
    @Provides
    fun provideOkHttpClient(): OkHttpClient {
        return OkHttpClient.Builder()
            // my default okhttp setup goes here 
            .build()
    }
}

第二个是一个简单的类。

class MyAwesomeClass {
    fun doMagic() {
        // magic code goes here
    }
}

现在我想在我的一个应用程序中使用MyAwesomeClass。所以我在应用中添加了依赖。

implementation "com.theapache64:my-awesome-library-1.0.0"

我也有一些网络调用实现,我不想使用来自my-network-libraryOkHttpClient。所以我在应用程序中创建了一个模块来获取我自己的OkHttpClient 实例。

@Module
@InstallIn(ApplicationComponent::class)
object NetworkModule {

    @Singleton
    @Provides
    fun provideOkHttpClient(): OkHttpClient {
        return OkHttpClient.Builder()
            // CUSTOM CONFIG GOES HERE 
            .build()
    }
}

现在出现以下错误。

错误:[Dagger/DuplicateBindings] okhttp3.OkHttpClient 已绑定 多次:

我知道这是因为my-network-library 中声明了@Provides,但我没有将includes 指定给@Module 注释以从BaseNetworkModule 继承依赖关系。可以使用 @Qualifier 注释解决此问题,但 IMO,这将是一种解决方法。

所以我的问题是

  • 为什么在不使用includes@Module 的情况下,来自库模块的依赖项会进入应用模块?
  • 如何告诉 Hilt “不要在外部库中查找 @Provides(gradle 依赖项)?”除非我用@Module(includes = XXXModule) 标记模块

【问题讨论】:

  • This 可能会有所帮助。
  • 用匕首,它工作正常。要继承依赖关系,我们必须手动使用@Module 注释的includes 选项。但是有了hilt,我不知道为什么它默认包含代码库中的所有依赖项。
  • 你应该在模块中使用标记为internal的限定符,这样它就不会泄漏到外面
  • @EpicPandaForce 创建类internal 将完全阻止从应用程序访问它。我希望可以通过includes 访问该类以维护模块继承。
  • 可以使用命名注解

标签: android dependency-injection dagger-2 dagger dagger-hilt


【解决方案1】:

为什么在不使用 @Module 的情况下,来自库模块的依赖项会进入应用模块?

因为 Hilt 的设计目的是让普通的 android 开发人员尽可能简单。

Hilt 是一个简单的家伙:他在编译的代码中看到@Module @InstallIn,他使用它。将@InstallIn 视为常规 Dagger2 中的include。只是放在不同的位置。


如何告诉 Hilt “不要在外部库中寻找 @Provides(gradle 依赖项)?”除非我用 @Module(includes = XXXModule) 标记模块

不可能。您不必用@Module @InstallIn(...) 标记它。

一般来说,我很难理解您为什么要这样做。您如何使用 my-network-library 中的 Hilt 功能?它是不同应用程序之间的共享模块吗?您想在其中一些应用程序中包含该模块,但不是全部?

【讨论】:

  • > why you would want that? - 将my-network-library 视为简单样板代码的集合。感谢您回复@Bartek。
【解决方案2】:

您是否尝试使用限定符?

@Qualifier
@Retention(AnnotationRetention.BINARY)
annotation class MyOkHttpClient

@Module
@InstallIn(ApplicationComponent::class)
object BaseNetworkModule {

    // Client
    @MyOkHttpClient
    @Singleton
    @Provides
    fun provideOkHttpClient(): OkHttpClient {
        return OkHttpClient.Builder()
            // my default okhttp setup goes here 
            .build()
    }
}

您可以通过这种方式分离 OkHttpClients 并继续利用 hilt。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2023-04-02
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-08-25
    • 1970-01-01
    • 1970-01-01
    • 2023-03-09
    相关资源
    最近更新 更多