UNPKG

opinionated-machine

Version:

Very opinionated DI framework for fastify, built on top of awilix

124 lines (123 loc) 5.59 kB
import type { AwilixContainer, NameAndRegistrationPair } from 'awilix'; import { AwilixManager } from 'awilix-manager'; import type { FastifyInstance } from 'fastify'; import type { AbstractModule } from './AbstractModule.js'; import { type NestedPartial } from './configUtils.js'; import type { ENABLE_ALL } from './diConfigUtils.js'; import { type BuildGatewayManifestOptions, type GatewayManifest } from './gateway/index.js'; import { type RegisterDualModeRoutesOptions, type RegisterSSERoutesOptions } from './routes/index.js'; export type RegisterDependenciesParams<Dependencies, Config, ExternalDependencies> = { modules: readonly AbstractModule<unknown, ExternalDependencies>[]; secondaryModules?: readonly AbstractModule<unknown, ExternalDependencies>[]; dependencyOverrides?: NameAndRegistrationPair<Dependencies>; configOverrides?: NestedPartial<Config>; configDependencyId?: string; }; export type DependencyInjectionOptions = { jobQueuesEnabled?: false | typeof ENABLE_ALL | string[]; enqueuedJobWorkersEnabled?: false | typeof ENABLE_ALL | string[]; messageQueueConsumersEnabled?: false | typeof ENABLE_ALL | string[]; periodicJobsEnabled?: false | typeof ENABLE_ALL | string[]; /** * Enable SSE test mode features like connection spying. * Only relevant for SSE controllers. Set to true in test environments. * @default false */ isTestMode?: boolean; }; export declare class DIContext<Dependencies extends object, Config extends object, ExternalDependencies = undefined> { private readonly options; readonly awilixManager: AwilixManager; readonly diContainer: AwilixContainer<Dependencies>; private readonly controllerResolvers; private readonly sseControllerNames; private readonly dualModeControllerNames; private readonly apiControllerNames; private readonly appConfig; constructor(diContainer: AwilixContainer<Dependencies>, options: DependencyInjectionOptions, appConfig: Config, awilixManager?: AwilixManager); private registerControllers; private registerModule; registerDependencies(params: RegisterDependenciesParams<Dependencies, Config, ExternalDependencies>, externalDependencies: ExternalDependencies, resolveControllers?: boolean): void; registerRoutes(app: FastifyInstance<any, any, any, any>): void; /** * Build a vendor-neutral gateway manifest from all registered REST and * api-contract controllers. Routes carrying gateway metadata (attached via * `withGatewayMetadata()`) get that metadata merged with controller-level * `gatewayDefaults` and the `defaults` passed here. Routes without any * metadata still appear in the manifest with empty metadata. * * The returned object is JSON-serializable; pass it to a generator package * like `@opinionated-machine/gateway-envoy` or * `@opinionated-machine/gateway-krakend` to produce a config. * * SSE and dual-mode controllers are not included in v1. * * @example * ```ts * const manifest = context.buildGatewayManifest({ * service: 'users-api', * defaults: { cors: { origins: ['https://app.example.com'] } }, * }) * const envoy = renderEnvoyConfig(manifest, { listenPort: 8080, clusters: { 'users-service': { hosts: ['users:8081'] } } }) * writeFileSync('envoy.yaml', envoy.yaml) * ``` */ buildGatewayManifest(options: BuildGatewayManifestOptions): GatewayManifest; /** * Check if any SSE controllers are registered. * Use this to conditionally call registerSSERoutes(). */ hasSSEControllers(): boolean; /** * Check if any dual-mode controllers are registered. * Use this to conditionally call registerDualModeRoutes(). */ hasDualModeControllers(): boolean; /** * Register SSE routes with the Fastify app. * * Must be called separately from registerRoutes(). * Requires @fastify/sse plugin to be registered on the app. * * @param app - Fastify instance with @fastify/sse registered * @param options - Optional configuration for SSE routes * * @example * ```typescript * // Register @fastify/sse plugin first * await app.register(fastifySSE, { heartbeatInterval: 30000 }) * * // Then register SSE routes * context.registerSSERoutes(app) * ``` */ registerSSERoutes(app: FastifyInstance<any, any, any, any>, options?: RegisterSSERoutesOptions): void; /** * Register dual-mode routes with the Fastify app. * * Dual-mode routes handle both SSE streaming and JSON responses on the * same path, automatically branching based on the `Accept` header. * * Must be called separately from registerRoutes() and registerSSERoutes(). * Requires @fastify/sse plugin to be registered on the app. * * @param app - Fastify instance with @fastify/sse registered * @param options - Optional configuration for dual-mode routes * * @example * ```typescript * // Register @fastify/sse plugin first * await app.register(fastifySSE, { heartbeatInterval: 30000 }) * * // Then register dual-mode routes * context.registerDualModeRoutes(app) * ``` */ registerDualModeRoutes(app: FastifyInstance<any, any, any, any>, options?: RegisterDualModeRoutesOptions): void; private applyDualModeRouteOptions; private applySSERouteOptions; private applyPreHandlers; private applyRateLimit; destroy(): Promise<void>; init(): Promise<void>; }