
Внедрение зависимости от трепета
7 августа 2025 г.Прежде чем продолжить эту статью, убедитесь, что у вас есть четкое представление о том, что такое зависимость и какова инъекция зависимости.
По мере того, как ваше приложение Flutter растет, управление услугами, такими как API, хранение, аутентификация и бизнес -логика, становится все труднее и требует более чистого способа внедрить все зависимости в ваше приложение без необходимости вручную передавать объекты через конструкторы или деревья виджетов.
Вот гдеGetIt
Входит. Это простой и очень мощный пакет локаторов обслуживания и делает инъекцию зависимостей чистым, централизованным и легким. Это приводит к:
- Более чистый код
- Более легкое тестирование
- Лучшая масштабируемость
Зачем инъекции зависимости?
Инъекция зависимостей отделяет проблемы в вашем приложении и позволяет вам центрально вводить зависимости без необходимости проходить их для зависимых классов отдельно.
Инъекция зависимости-общие способы
Наиболее часто используемые способы впрыскивания зависимостей в трепетание - через конструктор и сеттер, его простые и простые для понимания и полезные в небольших проектах. Для понимания целей мы рассмотрим примерApiService
класс, как упомянуто ниже:
class ApiService {
void fetchData() {
print('Fetching data...');
}
}
Теперь давайте посмотрим на инъекцию конструктора и инъекцию сеттера с помощью этогоApiService
сорт.
Инъекция конструктора
Как упоминается имя, инъекция конструктора относится к процессу передачи зависимостей через конструкторы класса. Рассмотрим пример ниже для лучшего понимания:
class HomeController {
final ApiService apiService;
// Constructor injection
HomeController(this.apiService);
}
void main() {
final apiService = ApiService(); // Create dependency
final controller = HomeController(apiService); // Inject via constructor
}
Как вы можете видеть в примере выше, зависимостьApiService
был передан вHomeController
Использование конструктораHomeController
сорт.
Инъекция сеттера
Инъекция сеттера - это процесс передачи зависимостей с помощью сеттера. Рассмотрим пример ниже для лучшего понимания:
class HomeController {
ApiService? _apiService;
// Setter injection
set apiService(ApiService service) {
_apiService = service;
}
}
void main() {
final apiService = ApiService();
final controller = HomeController();
controller.apiService = apiService; // Inject after construction
}
В примере выше, сеттерapiService
используется для передачи зависимостиHomeController
Полем
Теперь, когда мы видели общие способы инъекций зависимостей, давайте теперь проведем инъекцию зависимостейGetIt
Пакет в пошаговом гиде.
Шаг 1: добавитьget_it
к вашему проекту
Добавлятьget_it: latest_version
в ваш проектpubspec.yaml
Файл, как ниже:
dependencies:
get_it: ^7.6.0
Шаг 2: Создание и регистрация служб
Предположим, у нас есть услуга API
class ApiService {
void fetchData() {
print('Fetching data...');
}
}
Теперь давайте создадим локатор сервиса:
import 'package:get_it/get_it.dart';
final getIt = GetIt.I;
void setupLocator() {
getIt.registerLazySingleton<ApiService>(() => ApiService());
}
Теперь позвоните в этот локатор услуг в своемmain()
доrunApp()
void main() {
setupLocator();
runApp(MyApp());
}
Шаг 3: Используйте сервис в любом месте
Теперь вы можете использовать инъекционныеApiService
в любом месте вашего проекта, используяGetIt.I.<ApiService>()
без необходимости переосмыслить его. Ниже приведен пример этого:
class HomeScreen extends StatelessWidget {
final api = GetIt.I.get<ApiService>();
@override
Widget build(BuildContext context) {
return Scaffold(
body: Center(
child: ElevatedButton(
onPressed: () => api.fetchData(),
child: Text('Fetch Data'),
),
),
);
}
}
ОбзорGetIt
Методы регистрации
Ниже приведена таблица основных методов регистрации, доступная вGetIt
:
Метод | Описание | Использование |
---|---|---|
| Регистрирует уже созданный экземпляр. Мгновенно доступен. | Легкие услуги необходимы немедленно (например, конфигурация). |
| Регистрирует фабричную функцию. Экземпляр созданна первом доступе, затем повторно использовал. | Тяжелые или редко используемые услуги (например, дБ, сеть). |
| Возвращает ановый экземпляркаждый раз | Блоки, контроллеры или что-нибудь недолгое. |
| Регистры Anасинхрофабрика. Экземпляр ожидается во время | Услуги, которые требуют асинхронной настройки (например, чтение с диска). |
| Возвращает ановый экземпляр Asyncкаждый раз. | Свежие асинхронные экземпляры для использования (менее распространены). |
Тестирование с инъекцией зависимостей
Как упоминалось ранее, инъекция зависимостей также облегчает проверку нашего кода, мы увидим его в действии сейчас. Предположим, у нас есть контроллер, который зависит отApiService()
:
class HomeController {
final ApiService apiService;
HomeController(this.apiService);
}
Для тестирования мы будем использовать фиктивную службу API, которая будет проститься отApiService()
:
class MockApiService extends ApiService {
@override
void fetchData() {
print('Mock fetch');
}
}
void main() {
final controller = HomeController(MockApiService());
controller.apiService.fetchData();
}
Нет необходимости изменять код Apiservice (), проходная зависимость через конструктор будет хорошо запускать наши тесты.
Обычные методы против getit
Особенность | Обычный ди | Возьми |
---|---|---|
Видимость зависимости | Прозрачный | Скрытый (глобальный поиск) |
Тестируемость | Очень хороший | Нужно больше настройки |
Шаблон | Выше | Минимальный |
Глобальный доступ | Нет | Да |
Весы хорошо | Нет (без дополнительных инструментов) | Да |
Нулевая безопасность | Сильный | Зависит от использования |
Необходимы внешние пакеты | Нет | Да ( |
Lazy/Singleton Rading | Руководство | Встроенный |
Когда использовать что?
Традиционные методы инъекции зависимостей лучше всего работают, когда:
- Тестируемость является приоритетом
- Приложение мало масштабируется
- Вы не хотите полагаться на сторонние пакеты
GetIt
работает лучше всего, когда:
- Приложение увеличивается по размеру и сложности
- Есть много глобальных зависимостей, чтобы положиться на
- Хочу сохранить дерево виджетов в чистоте, избегая передачи зависимостей через конструкторы
Лучшие практики и советы
- Не регистрируйте все в Getit, только общие зависимости
- Предпочитаю использовать
registerFactory
При использовании переходной логики, такой как блок - Не забудьте позвонить
GetIt.I.reset()
в настройке теста для изоляции
Последние мысли
Инъекция зависимости играет ключевую роль в создании масштабируемого, тестируемого и простых в управлении кодом. Он очищает ваши классы, разделяя конфигурации и логику и при использовании мощного локатора обслуживания, какGetIt
зависимости вашего проекта становятся централизованно управляемыми, и это заставляет вас обходить необходимость передавать зависимости через конструкторы, поскольку у вас есть доступ к зависимостям во всем мире. Кроме того, это увеличивает тестируемость кода.
Таким образом, сочетание принципов инъекции зависимости сGetIt
Не только способствует более чистой архитектуре, но и повышает скорость развития, повышает модульность и готовит вашу кодовую базу для долгосрочного роста.
Оригинал