##// END OF EJS Templates
code comments
code comments

File last commit:

r2:154d88dba49c default
r2:154d88dba49c default
Show More
interfaces.ts
121 lines | 5.3 KiB | video/mp2t | TypeScriptLexer
import { ActivationContext } from "./ActivationContext";
export type primitive = number | string | null | undefined | symbol;
export interface IDestroyable {
destroy(): void;
}
/**
* @template S Карта доступных зависимостей
*/
export interface Resolver<S extends object> {
/**
* Функция для разрешения зависимостей, поддерживает создание фабричных методов,
* отложенную активацию и значение по-умолчанию для сервисов
* @template K Ключ сервиса из {@link S}
* @template O Тип параметра {@link opts} используется для выведения типа
* возвращаемого значения.
* @param name Ключ сервиса, который будет разрешен.
* @param {boolean=} opts.lazy Признак того, что требуется отложенная активация,
* будет возвращен фабричный метод для получения зависимости. Если не указан,
* то считается `false`.
* @param {any=} opts.default Значение по умолчанию, если в контейнере указанный
* сервис не зарегистрирован
* @returns Либо фабричный метод для получения зависимости, либо значение зависимости
* @throws Error Если зависимость не найдена и не предоставлено значение по-умолчанию
*/
<K extends keyof S, O extends { lazy: true; default?: unknown }>(name: K, opts?: O): () => (O extends { default: infer T } ? T : never) | NonNullable<S[K]>;
<K extends keyof S, O extends { lazy?: false; default?: unknown }>(name: K, opts?: O): (O extends { default: infer T } ? T : never) | NonNullable<S[K]>;
}
export interface DescriptorBuilder<S extends object, T> {
/**
*
* @param f
*/
factory(f: (resolve: Resolver<S>) => T): void;
override<K extends ConfigurableKeys<S>>(name: K, builder: RegistrationBuilder<S, NonNullable<S[K]>>): this;
override<K extends ConfigurableKeys<S>>(services: { [name in K]: RegistrationBuilder<S, NonNullable<S[K]>> }): this;
lifetime(lifetime: "singleton", typeId: string | number | object): this;
lifetime(lifetime: ILifetime<T> | Exclude<ActivationType, "singleton">): this;
cleanup(cb: (item: T) => void): this;
value(v: T): void;
}
export type RegistrationBuilder<S extends object, T> = (d: DescriptorBuilder<S, T>) => void;
export type RegistrationBuildersMap<S extends object, K extends ConfigurableKeys<S> = ConfigurableKeys<S>> = {
[k in K]-?: RegistrationBuilder<ContainerServices<S>, NonNullable<ConfigurableServices<S>[k]>>
};
export interface Descriptor<S extends object, T> {
activate(context: ActivationContext<S>): T;
}
export type ConfigurableDescriptor<S extends object, K extends ConfigurableKeys<S>> = Descriptor<ContainerServices<S>, ConfigurableServices<S>[K]>;
export type RegistrationMap<S extends object, K extends keyof S = keyof S> = {
[k in K]-?: Descriptor<S, S[k]>;
};
export interface ProvidedServices<S extends object> {
container: ServiceLocator<ContainerServices<S>>;
childContainer: ServiceContainer<S>;
}
export type ProvidedKeys = keyof ProvidedServices<object>;
export type ContainerKeys<S extends object> = keyof ContainerServices<S>;
export type Mix<S, X> = { [k in keyof (S & X)]: k extends keyof X ? X[k] : S[k & keyof S] };
export type ContainerServices<S extends object> = Mix<S, ProvidedServices<S>>;
export type ConfigurableKeys<S extends object> = Exclude<keyof S, ProvidedKeys>;
export type ConfigurableServices<S extends object> = Pick<S, ConfigurableKeys<S>>;
export interface ServiceLocator<S extends object> {
resolve<K extends keyof S>(name: K): NonNullable<S[K]>;
resolve<K extends keyof S, T>(name: K, def: T): NonNullable<S[K]> | T;
}
export interface LifetimeContainer {
createLifetime<T>(): ILifetime<T>;
}
export interface ServiceContainer<S extends object> extends ServiceLocator<ContainerServices<S>>, LifetimeContainer, IDestroyable {
register<K extends ConfigurableKeys<S>>(name: K, service: ConfigurableDescriptor<S, K>): void;
register<K extends ConfigurableKeys<S>>(services: { [k in K]: ConfigurableDescriptor<S, K> }): void;
createChildContainer(): ServiceContainer<S>;
}
export type ActivationType = "singleton" | "container" | "hierarchy" | "context" | "call";
/**
* Интерфейс для управления жизнью экземпляра объекта. Каждая регистрация имеет
* свой собственный объект `ILifetime`, который создается при первой активации
*/
export interface ILifetime<T> {
/** Проверяет, что уже создан экземпляр объекта */
has(): boolean;
get(): T;
initialize(context: ActivationContext<object>): void;
store(item: T, cleanup?: (item: T) => void): void;
}
export type ExtractRequired<T, K extends keyof T = keyof T> = { [p in K as (undefined extends T[p] ? never : p)]-?: T[p] };