简体   繁体   English

用Dagger 2注入子类型的类的最佳方法是什么?

[英]What is the best way to inject a class of a child type with Dagger 2?

Is it just to provide the child type in the module ? 仅仅是在模块中提供子类型? or is there a more direct way eg by using constructor injection with some parameter ? 还是有更直接的方法,例如通过使用带有某些参数的构造函数注入?

@Module
class TestModule() {

  @Provides
  @Singleton
  fun provideDummy(): Dummy = DummyChild()

}

class MainActivity : AppCompatActivity() {
    @Inject
    lateinit var dummy: Dumy

    override fun onCreate(savedInstanceState: Bundle?) {
       ...
    }

    ...
}

That's how it needs to be done. 这就是需要做的事情。 The Module provides components that can be injected. 该模块提供了可以注入的组件。

In the above case TestModule is the module which can provide DummyChild . 在上述情况下, TestModule是可以提供DummyChild的模块。 It becomes a complicated if the constructor of DummyChild required a parameter. 如果DummyChild的构造DummyChild需要一个参数,它将变得很复杂。 In that case the parameter needs to be injected as well. 在这种情况下,还需要注入参数。

@Module
class TestModule() {

@Provides
@Singleton
fun provideDummy(Context context): Dummy = DummyChild(context)
}

In the above case, context needs to be provided as well. 在上述情况下,还需要提供context You should have an exposed Provides method that can provide Context. 您应该有一个可以提供上下文的公开Provides方法。

or is there a more direct way eg by using constructor injection with some parameter ? 还是有更直接的方法,例如通过使用带有某些参数的构造函数注入?

Absolutely! 绝对!

@Module
class TestModule() {

  @Provides
  @Singleton
  fun provideDummy(): Dummy = DummyChild() // bad, we construct it ourselves!

}

You should let Dagger care about where the object comes from, so calling the constructor is usually not a good idea (unless this is really what you want). 您应该让Dagger关心对象的来源,因此调用构造函数通常不是一个好主意(除非这确实是您想要的)。 The proper way to bind an implementation is by using a @Provides method and requesting the child, directly returning it, or just using the @Binds annotation which will do effectively the same, but possibly more optimized than @Provides . 绑定实现的正确方法是使用@Provides方法并请求子级,直接返回该子级,或者仅使用@Binds批注,其效果相同,但可能比@Provides优化。

@Module
class TestModule() {

  @Provides
  fun provideDummy(implementation : DummyChild): Dummy = implementation // better!

  // or with @Binds

  @Binds
  abstract fun provideDummy(implementation : DummyChild): Dummy // also good

}

@Singleton class DummyChild @Inject constructor()

Notice that I removed the @Singleton from the methods, as this is usually an implementation detail of DummyChild , rather than the interface, but you can of course still add it to the method if you wish to do so. 请注意,我从方法中删除了@Singleton ,因为这通常是DummyChild的实现细节,而不是接口,但是如果您愿意,您当然也可以将其添加到方法中。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM