import { Descriptor, ILifetime, ConfigurableKeys, Resolver } from "./interfaces"; import { ActivationContext } from "./ActivationContext"; import { ContextResolver } from "./ContextResolver"; import { each } from "./traits"; export type RegistrationOverridesMap = { [k in ConfigurableKeys]?: Descriptor> }; export interface DescriptorImplArgs { lifetime: ILifetime; factory: (resolve: Resolver) => T; cleanup?: (item: T) => void; overrides?: RegistrationOverridesMap; } export class DescriptorImpl implements Descriptor { private readonly _overrides?: RegistrationOverridesMap; private readonly _lifetime: ILifetime; private readonly _factory: (resolve: Resolver) => T; private readonly _cleanup?: (item: T) => void; constructor(args: DescriptorImplArgs) { this._lifetime = args.lifetime; this._factory = args.factory; if (args.cleanup) this._cleanup = args.cleanup; if (args.overrides) this._overrides = args.overrides; } activate(context: ActivationContext): T { if (this._lifetime.has()) return this._lifetime.get(); this._lifetime.initialize(context); if (this._overrides) each(this._overrides, (v, k) => context.register(k, v)); const resolver = new ContextResolver(context); const instance = this._factory.call(undefined, resolver.resolve.bind(resolver)); this._lifetime.store(instance, this._cleanup); return instance; } toString() { return `[object DescriptorImpl, lifetime=${String(this._lifetime)}]`; } }