UNPKG

alepha

Version:

Easy-to-use modern TypeScript framework for building many kind of applications.

60 lines (52 loc) 1.69 kB
import { Primitive } from "../helpers/primitive.ts"; import type { InstantiableClass, Service } from "../interfaces/Service.ts"; import { $context } from "./$context.ts"; /** * Get the instance of the specified type from the context. * * ```ts * class A { } * class B { * a = $inject(A); * } * ``` */ export const $inject = <T extends object>( type: Service<T>, opts: InjectOptions<T> = {}, ): T => { const { alepha, service } = $context(); // _ = $inject(Alepha) if (type === alepha.constructor) { return alepha as T; } return alepha.inject(type, { // keep the parent for better error messages and circular dependencies detection parent: service ?? (alepha.constructor as Service), ...opts, }); }; export class InjectPrimitive extends Primitive {} export interface InjectOptions<T extends object = any> { /** * - 'transient' → Always a new instance on every inject. Zero caching. * - 'singleton' → One instance per Alepha runtime (per-thread). Never disposed until Alepha shuts down. (default) * - 'scoped' → One instance per AsyncLocalStorage context. * - A new scope is created when Alepha handles a request, a scheduled job, a queue worker task... * - You can also start a manual scope via alepha.context.run(() => { ... }). * - When the scope ends, the scoped registry is discarded. * * @default "singleton" */ lifetime?: "transient" | "singleton" | "scoped"; /** * Constructor arguments to pass when creating a new instance. */ args?: ConstructorParameters<InstantiableClass<T>>; /** * Parent that requested the instance. * * @internal */ parent?: Service | null; }