import type { BootstrapHandler, LinkDefinition, Subscriber } from "@voyant-travel/core"; import type { ApiExtension, ApiModule } from "./module.js"; /** * Reusable server API contribution surface. * * `@voyant-travel/hono` is Voyant's sole server API runtime implementation. * `ApiBundle` describes packages that contribute {@link ApiModule} / * {@link ApiExtension} wrappers carrying HTTP routes. * * Registered via `createApp({ plugins: [...] })` — the app factory expands * each bundle into the underlying modules, extensions, subscribers, and link * definitions before mounting them. */ export interface ApiBundle { /** Unique bundle identifier (e.g. "payload-cms", "bokun"). */ name: string; /** Optional version tag for diagnostics. */ version?: string; /** Optional lazy runtime bootstrap executed once per app/isolate. */ bootstrap?: BootstrapHandler; /** API modules (module + routes) contributed by the plugin. */ modules?: ApiModule[]; /** API extensions (extension + routes) contributed by the plugin. */ extensions?: ApiExtension[]; /** Event subscribers wired to the caller's event bus, when provided. */ subscribers?: Subscriber[]; /** Link definitions contributed by the plugin. */ links?: LinkDefinition[]; /** * Absolute API paths this bundle exposes that are reachable WITHOUT a session * (ADR-0008). Unlike a module/extension's `anonymous` (relative to its * `/v1/public` mount), bundle routes can mount anywhere — e.g. a payment * processor's webhook at `/v1/finance/providers/netopia/callback`, which the * processor's servers POST to without a cookie or bearer. Declaring it here * keeps the "reachable-without-auth" decision with the plugin that owns the * route, instead of in every deployment's `publicPaths`. The framework folds * these into the assembled anonymous allow-list. */ anonymous?: string[]; } declare const LAZY_API_BUNDLE: unique symbol; /** * Lazy bundle declaration. The bundle's heavy runtime graph is imported only * when a declared route matcher is hit, unless `loadOnBootstrap` asks the app * to load it during request/headless bootstrap. `name` and `anonymous` remain * eager metadata so duplicate checks and auth allow-lists stay fail-closed. */ export interface LazyApiBundle { readonly [LAZY_API_BUNDLE]: true; /** Unique bundle identifier matching the loaded bundle's `name`. */ name: string; /** Optional version tag for diagnostics. */ version?: string; /** * Absolute unauthenticated paths contributed by the eventual bundle. Declare * webhook/callback paths here so the first matching request can pass auth * before the bundle has been imported. */ anonymous?: string[]; /** * Absolute route matchers the eventual bundle may serve. Required for lazy * bundles that contribute HTTP routes because Hono routes must be registered * before the first request builds the matcher. */ routes?: readonly string[]; /** * Module names whose lazy-loaded routes must receive a transaction-capable DB * client. This is eager metadata so the first matching request is routed to * `dbTransactional` before the bundle implementation is imported. */ transactionalModules?: readonly string[]; /** * Absolute API path prefixes whose lazy-loaded routes must receive the * transaction-capable DB client. Use this when only a subset of the lazy * bundle's explicit `routes` require transactions. */ transactionalPaths?: readonly string[]; /** * Load this bundle during app bootstrap instead of waiting for a declared * route matcher. Set this for lazy bundles that contribute subscribers, * container services, or bootstraps needed before a bundle-owned route is hit. */ loadOnBootstrap?: boolean; /** Loads and constructs the real bundle. Memoized by `mountApp`. */ load: () => Promise; } export type ApiBundleInput = ApiBundle | LazyApiBundle; /** * Identity helper — returns the bundle unchanged, purely for IDE inference. */ export declare function defineApiBundle

(bundle: P): P; export declare function defineLazyApiBundle

>(bundle: P): P & LazyApiBundle; export declare function isLazyApiBundle(bundle: ApiBundleInput): bundle is LazyApiBundle; export interface ExpandedApiBundles { modules: ApiModule[]; extensions: ApiExtension[]; subscribers: Subscriber[]; links: LinkDefinition[]; /** Absolute anonymous-access paths declared by bundles (ADR-0008). */ anonymousPaths: string[]; } /** * Flatten a list of {@link ApiBundle} values into their constituent pieces. * * Throws if two bundles declare the same `name`. */ export declare function expandApiBundles(bundles: ReadonlyArray): ExpandedApiBundles; export {};