Hilt, Inject types with multiple scopes

Viewed 1263

I'm doing dependency injection with dagger hilt. Most of my types are singletons so I have my hilt module installed in the SingletonComponent like this:

@Module
@InstallIn(SingletonComponent::class)
object MyAppModule {
   @Provides
    fun provideUserService(service: UserServiceImpl): UserService {
        return service
    }
    // And a bunch of other "provides" functions exactly like this one.
}

As for type declarations I go like this:

@Singleton
class UserServiceImpl @Inject constructor(/* dependencies go here */): UserService {}

It all worked as expected until I needed to inject an activity class in my LocationService using the @ActivityContext and as you know that one can't be a singleton. So I made the location service @ActivityScoped

@ActivityScoped
class LocationProviderImpl @Inject constructor(
    @ActivityContext private val activity: ComponentActivity
)

but putting a provides function for this one in the module above breaks the app with this error

MyApplication_HiltComponents.java:134: error: [Dagger/IncompatiblyScopedBindings] com.example.app.di.MyApplication_HiltComponents.SingletonC scoped with @Singleton may not reference bindings with different scopes:
  public abstract static class SingletonC implements MyApplication_GeneratedInjector,
                         ^
      @dagger.hilt.android.scopes.ActivityScoped class com.example.app.services.LocationServiceImpl

So I thought maybe I should put provides for location service in a separate module that was installed in the activity component...

@Module
@InstallIn(ActivityComponent::class)
class MyActivityModule {
    @Provides
    fun locationService(locationService: LocationServiceImpl): LocationService {
        return locationService
    }
}

And it only got me a different error:

MyApplication_HiltComponents.java:134: error: [Dagger/MissingBinding] com.example.app.services.LocationService cannot be provided without an @Provides-annotated method.
  public abstract static class SingletonC implements MyApplication_GeneratedInjector,
                         ^
      com.example.app.services.LocationService is injected at
          com.example.app.viewmodels.MapScreenViewModel(�, locationService)
      com.example.app.viewmodels.MapScreenViewModel is injected at
          com.example.app.viewmodels.MapScreenViewModel_HiltModules.BindsModule.binds(vm)
      @dagger.hilt.android.internal.lifecycle.HiltViewModelMap java.util.Map<java.lang.String,javax.inject.Provider<androidx.lifecycle.ViewModel>> is requested at
          dagger.hilt.android.internal.lifecycle.HiltViewModelFactory.ViewModelFactoriesEntryPoint.getHiltViewModelMap() [com.example.app.di.MyApplication_HiltComponents.SingletonC ? com.example.app.di.MyApplication_HiltComponents.ActivityRetainedC ? com.example.app.di.MyApplication_HiltComponents.ViewModelC]

I sure do have a @Provides-annotated method so I guess it's ignoring the MyActivityModule that I just declared.

So I was wondering if anyone knows the right way to go about this problem.

0 Answers
Related