Reputation: 185
I have a Dagger 2 dependency that is provided differently if it’s an Activity
or some other context instance (e.g., a Service
). Both would refer to the same interface but their implementation varies. How could I organise this using Dagger 2?
Right now, I’m trying with two different components, ActivityComponent
and ContextComponent
with their respective modules as follows:
@ActivityScope
@Subcomponent(
modules = {
ActivityModule.class,
ContextModule.class
})
public interface ActivityComponent {
}
@Module
public class ActivityModule {
@Provides
@MyActivityQualifier
public MyObject provideMyObject() {
}
}
@ContextScope
@Subcomponent(
modules = {
ContextModule.class
})
public interface ContextComponent { }
@Module
public class ContextModule.class {
@Provides
public MyObject provideMyObject() {
}
}
Then, if I’m using MyObject
in an Activity
, I have to add the qualifier as follows:
@Inject @MyActivityQualifier MyObject myObject;
This feels wrong but I’m not sure why. Is there a better way?
Upvotes: 3
Views: 1469
Reputation: 34532
You are using subcomponents.
The question is: Can or should both objects be "visible" (usable, injectable, ...) at the same time?
@Subcomponent
in this case, and just don't add the getMyInterface()
method to your parent component.And there aren't any other options, because you have 2 components dependent on each other. So your approach looks fine with the information you provide.
Note you can also just qualify one of your implementations. In my project, I use a qualified @Named("public")
annotation for a common implementation without user data. If I don't add any qualifier I will just get the other one (unqualified).
With independent components, e.g. ActivityAComponent
and ActivityBComponent
you could just switch which implementation gets provided using different modules.
Upvotes: 1