Для генерации кода Hilt требуется доступ ко всем модулям Gradle, использующим Hilt. Модуль Gradle, который компилирует ваш класс Application
, должен иметь в своих транзитивных зависимостях все модули Hilt и классы, внедренные конструктором.
Если ваш многомодульный проект состоит из обычных модулей Gradle, вы можете использовать Hilt, как описано в разделе «Внедрение зависимостей с помощью Hilt» . Однако это не относится к приложениям, которые включают функциональные модули .
Рукоять в функциональных модулях
В функциональных модулях способ, которым модули обычно зависят друг от друга, перевернут. Следовательно, Hilt не может обрабатывать аннотации в функциональных модулях. Вы должны использовать Dagger для внедрения зависимостей в ваши функциональные модули.
Чтобы решить эту проблему с помощью функциональных модулей, необходимо использовать зависимости компонентов. Выполните следующие действия:
- Объявите интерфейс
@EntryPoint
в модулеapp
(или в любом другом модуле, который может обрабатываться Hilt) с зависимостями, необходимыми функциональному модулю. - Создайте компонент Dagger, который зависит от интерфейса
@EntryPoint
. - Используйте Dagger, как обычно, в функциональном модуле.
Рассмотрим пример со страницы «Внедрение зависимостей с помощью Hilt» . Предположим, вы добавляете в свой проект модуль функции login
. Вы реализуете функцию входа в систему с помощью действия под названием LoginActivity
. Это означает, что вы можете получить привязки только из компонента приложения.
Для этой функции вам понадобится OkHttpClient
с привязкой authInterceptor
.
Сначала создайте интерфейс @EntryPoint
, установленный в SingletonComponent
с привязками, необходимыми модулю login
:
Котлин
// LoginModuleDependencies.kt - File in the app module. @EntryPoint @InstallIn(SingletonComponent::class) interface LoginModuleDependencies { @AuthInterceptorOkHttpClient fun okHttpClient(): OkHttpClient }
Ява
// LoginModuleDependencies.java - File in the app module. @EntryPoint @InstallIn(SingletonComponent.class) public interface LoginModuleDependencies { @AuthInterceptorOkHttpClient OkHttpClient okHttpClient(); }
Чтобы выполнить внедрение полей в LoginActivity
, создайте компонент Dagger, который зависит от интерфейса @EntryPoint
:
Котлин
// LoginComponent.kt - File in the login module. @Component(dependencies = [LoginModuleDependencies::class]) interface LoginComponent { fun inject(activity: LoginActivity) @Component.Builder interface Builder { fun context(@BindsInstance context: Context): Builder fun appDependencies(loginModuleDependencies: LoginModuleDependencies): Builder fun build(): LoginComponent } }
Ява
// LoginComponent.java - File in the login module. @Component(dependencies = LoginModuleDependencies.class) public interface LoginComponent { void inject(LoginActivity loginActivity); @Component.Builder interface Builder { Builder context(@BindsInstance Context context); Builder appDependencies(LoginModuleDependencies loginModuleDependencies); LoginComponent build(); } }
После завершения этих шагов используйте Dagger, как обычно, в своем функциональном модуле. Например, вы можете использовать привязки из SingletonComponent
как зависимость класса:
Котлин
// LoginAnalyticsAdapter.kt - File in the login module. class LoginAnalyticsAdapter @Inject constructor( @AuthInterceptorOkHttpClient okHttpClient: OkHttpClient ) { ... }
Ява
// LoginAnalyticsAdapter.java - File in the login module. public class LoginAnalyticsAdapter { private final OkHttpClient okHttpClient; @Inject LoginAnalyticsAdapter( @AuthInterceptorOkHttpClient OkHttpClient okHttpClient ) { this.okHttpClient = okHttpClient; } ... }
Чтобы выполнить внедрение полей, создайте экземпляр компонента Dagger, используя applicationContext
, чтобы получить зависимости SingletonComponent
:
Котлин
// LoginActivity.kt - File in the login module. class LoginActivity : AppCompatActivity() { @Inject lateinit var loginAnalyticsAdapter: LoginAnalyticsAdapter override fun onCreate(savedInstanceState: Bundle?) { DaggerLoginComponent.builder() .context(this) .appDependencies( EntryPointAccessors.fromApplication( applicationContext, LoginModuleDependencies::class.java ) ) .build() .inject(this) super.onCreate(savedInstanceState) ... } }
Ява
// LoginActivity.java - File in the login module. public class LoginActivity extends AppCompatActivity { @Inject LoginAnalyticsAdapter loginAnalyticsAdapter; @Override protected void onCreate(Bundle savedInstanceState) { DaggerLoginComponent.builder() .context(this) .appDependencies( EntryPointAccessors.fromApplication( getApplicationContext(), LoginModuleDependencies.class ) ) .build() .inject(this); super.onCreate(savedInstanceState); ... } }
Дополнительную информацию о зависимостях модулей в функциональных модулях см. в разделе Зависимости компонентов от функциональных модулей .
Дополнительную информацию о Dagger на Android см. в разделе «Использование Dagger в приложениях Android» .