问题

我正在构建具有动态功能的应用程序。

为了提供我使用的匕首2对主模块和功能模块的所有依赖关系。功能部件取决于主部件,因此,功能部件的作用域与主部件作用域(@Singleton在这种情况下)

注入到主模块中的接口之一在功能模块上实现,并通过反射在主模块中提供。该实现还用于功能模块中。

我的问题是主模块中提供的实例与功能模块中提供的实例不同(由于作用域),但是我只想让一个带有匕首的实例提供。



这里有一些代码,您可以在github中找到整个示例项目

主模块的Dagger配置:

TestModule.kt

@Module
class TestModule {

    @Provides
    @Singleton
    fun provideTestA() : TestA = TestAImplementation()

    private var testCProvider: TestC?= null

    @Provides
    @Singleton
    fun provideTestC(testComponent: TestComponent) : TestC {
        if(testCProvider != null) return testCProvider as TestC

        val provider = Class.forName("com.example.feature.services.TestCImplementation\$Provider").kotlin.objectInstance as TestC.Provider
        return provider
            .get(testComponent)
            .also { testCProvider = it }
    }
}


TestComponent.kt

@Singleton
@Component(modules = [TestModule::class])
interface TestComponent {
    fun inject(activity: MainActivity)

    fun provideTestA() : TestA
}


功能模块的匕首配置:

TestDependencyModule.kt

@Module
class TestDependencyModule {

    @Provides
    @TestScope
    fun provideTestB(): TestB = TestBImplementation()

    @Provides
    @TestScope
    fun provideTestC(testB: TestB): TestC = TestCImplementation(testB)
}


TestDependencyComponent.kt

@TestScope
@Component(
    modules = [TestDependencyModule::class],
    dependencies = [TestComponent::class]
)
interface TestDependencyComponent {
    fun inject(receiver: TestBroadcastReceiver)

    fun testC(): TestC
}


预期结果

接口TestCTestA注入到MainActivity

接口TestBTestA注入到TestBroadcastReceiver

不出所料,TestA实现的实例是唯一的,但是对于TestB的实现不是那样。因为TestC取决于TestB,所以在TestC中注入的内容与在TestBroadcastReceiver中带有@TestScope注释的注入内容不同。

因此,运行示例项目,您可以找到here,我得到以下日志输出

MainActivity中注入的实例

D/TestB: instance 40525431
D/TestC: instance 119319268
D/TestA: instance 60713805


TestBroadcastReceiver中注入的实例

D/TestB: instance 219966227
D/TestA: instance 60713805


我想在两个模块中共享TestB的相同实例。

有什么建议吗?
提前致谢!

最佳答案

由于TestComponent不会在其公共API上公开TestC,因此TestDependencyComponent无法从对TestComponent的组件依赖关系访问TestC。如果在TestComponent上添加fun testC(): TestC,我希望您在处理TestDependencyComponent时会收到重复的绑定异常。从那里,您将需要确定提供TestC实例的正确方法。

08-18 16:42