1 В избранное 0 Ответвления 0

OSCHINA-MIRROR/Happyxx-TypescriptDependencyInjection

Присоединиться к Gitlife
Откройте для себя и примите участие в публичных проектах с открытым исходным кодом с участием более 10 миллионов разработчиков. Приватные репозитории также полностью бесплатны :)
Присоединиться бесплатно
Клонировать/Скачать
Внести вклад в разработку кода
Синхронизировать код
Отмена
Подсказка: Поскольку Git не поддерживает пустые директории, создание директории приведёт к созданию пустого файла .keep.
Loading...
Readme.md

Внедрение зависимостей для TypeScript

Теги: TS DI TypeScript Dependency-Injection


При изучении Angular2 столкнулся с внедрением зависимостей, и обнаружил, что это очень полезная вещь. Поэтому я попытался реализовать его самостоятельно.

API

На данный момент существует несколько API:

  • @Injectable()
  • @Singleton()
  • @Inject()
  • @Inject(()=>Type)
  • Injector.get()

Пример

@Injectable()

@Injectable()
class A {
}

@Injectable()
class B {
    private val = '1234';

    constructor(private a: A) {
    }

    getVal() {
        return this.val;
    }

    setVal(newval) {
        this.val = newval;
    }
}

// Использование Injector.get(), можно получить экземпляр без предоставления параметров
let b = Injector.get(B);
let b2 = Injector.get(B);

// Тестирование: один и тот же класс может быть инстанцирован несколько раз, каждый экземпляр является отдельным объектом.
let newVal = 'zzzz';
b.setVal(newVal);

assert.equal(b.getVal(), newVal);
assert.equal(b2.getVal(), '1234');

####@Inject() И @Injectable(), используется для украшения свойств.

@Injectable()
class A {
    @Inject()
    b: ClassB;
}

####@Singleton

@Singleton()
class SingletonClass {
    private val = '1234';

    constructor(private a: A) {
    }

    get() {
        return this.val;
    }

    set(newval) {
        this.val = newval;
    }
}

let b = Injector.get(SingletonClass);
let b2 = Injector.get(SingletonClass);

// Тестирование: класс, украшенный @Singleton(), все дескрипторы должны указывать на один и тот же объект
let newVal = 'zzzz';
b.set(newVal);

assert.equal(b.get(), newVal);
assert.equal(b2.get(), newVal);

####@Inject(()=>Type) @Injectable() не может обрабатывать A->B->A такие циклические зависимости. Когда A и B являются одиночными, их взаимная зависимость очень распространена. И @Inject(()=>Type) был создан для решения этой проблемы. Используя @Inject(()=>Type), пока в цикле существует один синглтон, все экземпляры в цикле могут быть правильно созданы.

// singleton_class.ts
import {ClassA} from "./class_a"
@Singleton()
class SingletonClass{
}

// class_a.ts
import {SingletonClass} from "./singleton_class"
@Injectable()
class ClassA {
    @Inject(()=>SingletonClass)
    s: SingletonClass;
}

Что касается того, почему необходимо добавить функцию, возвращающую тип, в качестве параметра для решения проблемы циклической зависимости, это потому, что TypeScript при включении двух файлов друг в друга обязательно будет иметь неопределенный тип по крайней мере для одного класса. Добавление параметра фактически является вынужденным решением.

Сборка и тестирование

npm install npm test

Почему @Injectable, а не @Injectable()?

Декоратор не требует добавления скобок. Вот так:

@Injectable
class A{}

Добавление скобок принудительно сделано для соответствия декораторам Angular2; также для обеспечения лучшей расширяемости. Например, @Inject() может принимать параметр, решая проблему циклических зависимостей.

Комментарии ( 0 )

Вы можете оставить комментарий после Вход в систему

Введение

Описание недоступно Развернуть Свернуть
MIT
Отмена

Обновления

Пока нет обновлений

Участники

все

Недавние действия

Загрузить больше
Больше нет результатов для загрузки
1
https://api.gitlife.ru/oschina-mirror/Happyxx-TypescriptDependencyInjection.git
git@api.gitlife.ru:oschina-mirror/Happyxx-TypescriptDependencyInjection.git
oschina-mirror
Happyxx-TypescriptDependencyInjection
Happyxx-TypescriptDependencyInjection
master