Ответ
Хранение всех зависимостей в одном компоненте Dagger приводит к нескольким проблемам:
-
Производительность - при каждом изменении графа зависимостей пересобирается весь компонент, что замедляет сборку.
-
Читаемость - большой монолитный компонент сложно поддерживать и понимать.
-
Избыточность - зависимости могут создаваться даже когда они не нужны.
Лучше разбивать на логические подкомпоненты:
@Singleton
@Component(modules = [AppModule::class])
interface AppComponent {
fun sessionComponent(): SessionComponent.Factory
}
@SessionScope
@Subcomponent(modules = [SessionModule::class])
interface SessionComponent {
@Subcomponent.Factory
interface Factory {
fun create(): SessionComponent
}
}
Такой подход улучшает модульность, ускоряет инкрементальные сборки и делает код чище.
Ответ 18+ 🔞
А, ну это классика, блядь! Смотри, как обычно бывает: сидит чувак, пишет приложение, и ему в голову приходит гениальная идея — а давай-ка я все свои зависимости, все эти сервисы, репозитории и прочую хуету, засуну в один здоровенный компонент Dagger! Ёпта, удобно же — всё в одном месте, как в большой сумке!
И вроде бы работает, но потом начинается пиздец. Представь: ты меняешь одну маленькую зависимость в модуле авторизации, а компилятор начинает пересобирать весь этот монстр-компонент, от корки до корки. Это как если бы у тебя спустило колесо на машине, а ты разбираешь весь двигатель, чтобы его подкачать. Овердохуища времени уходит, терпения ноль ебать!
И читать этот код — это отдельный вид ебушки-воробушки. Открываешь файл на 500 строк, а там такая каша из @Provides и @Binds, что глаза разбегаются. Хуй поймёшь, где что лежит и зачем. Чистая манда с ушами, а не архитектура.
А самое смешное, что половина этих зависимостей может вообще не понадобиться в конкретном сценарии. Но они всё равно создаются, как будто на дворе 2002-й год и ресурсов дохуя. Зачем тебе в сплеш-скрине инжектить модуль работы с базой данных? Да похуй, создадим на всякий случай!
Так делать — это вы ходите по охуенно тонкому льду. Рано или поздно всё накроется медным тазом.
Вот смотри, как умные люди делают. Берут и разбивают этот монолит на логические куски — подкомпоненты.
@Singleton
@Component(modules = [AppModule::class])
interface AppComponent {
// Не создаём всё сразу, а даём фабрику для создания SessionComponent, когда он понадобится
fun sessionComponent(): SessionComponent.Factory
}
// Отдельная область видимости для всего, что связано с сессией пользователя
@SessionScope
@Subcomponent(modules = [SessionModule::class])
interface SessionComponent {
@Subcomponent.Factory
interface Factory {
fun create(): SessionComponent
}
}
В чём прикол? Сам от себя охуел, когда понял.
- Скорость. Изменил что-то в сессионных модулях? Пересобирается только
SessionComponent. ОсновнойAppComponentостаётся нетронутым. Инкрементальные сборки летают. - Порядок. Каждый компонент отвечает за свою зону. В
AppModule— глобальные штуки вродеRetrofitилиSharedPreferences. ВSessionModule— всё, что нужно авторизованному пользователю. Никакой хитрой жопы, всё на своих местах. - Эффективность.
SessionComponentсоздаётся только когда пользователь залогинился. Пока он на экране логина — этих зависимостей просто не существует. Не тратятся память и процессорное время.
В общем, чувак, мораль проста: не лепи всё в одну кучу. Дели граф зависимостей на осмысленные части, и жить станет проще, а код перестанет быть пиздопроебибной кашей. Поверь, оно того стоит.