Ответ
Dependency Injection (DI, внедрение зависимостей) — это паттерн, при котором зависимости объекта (сервисы, репозитории, конфигурации) предоставляются ему извне, обычно через конструктор, метод или свойство, а не создаются внутри самого объекта.
Проблема без DI (жесткая связь):
class UserService {
constructor() {
// Зависимость создается внутри класса, что усложняет тестирование и замену.
this.userRepository = new PostgreSQLUserRepository();
}
async getUser(id) {
return this.userRepository.findById(id);
}
}
Решение с DI (гибкая связь):
class UserService {
// Зависимость внедряется извне.
constructor(userRepository) {
this.userRepository = userRepository;
}
async getUser(id) {
return this.userRepository.findById(id);
}
}
// Где-то в точке входа в приложение (например, index.js или контейнере DI) собираем объекты:
const userRepository = new PostgreSQLUserRepository();
const userService = new UserService(userRepository);
// Теперь для тестов легко подменить репозиторий на мок:
const mockRepository = { findById: jest.fn(() => ({ id: 1, name: 'Test' })) };
const testUserService = new UserService(mockRepository);
В Node.js-экосистеме DI часто используется с:
- Фреймворками: NestJS имеет мощную встроенную систему DI на основе декораторов.
- Библиотеками: InversifyJS, Awilix, TSyringe.
- Ручной инъекцией: Простая передача зависимостей через конструкторы, что часто достаточно для небольших проектов.
Основные преимущества: повышение тестируемости, уменьшение связанности кода, упрощение рефакторинга и конфигурации.
Видео-ответы
▶