{"version":3,"sources":["../src/db/index.js","../src/errors.js","../src/db/ensure.js"],"sourcesContent":["import knex from \"knex\";\nimport { ParamError } from \"../errors.js\";\n\nexport {\n    ensureExtension,\n    ensureTable,\n    ensureIndex,\n    ensureSchema,\n    ensureSchemaEverywhere,\n} from \"./ensure.js\";\n\nconst KNEX_DEFAULTS = {\n    testConnection: true,\n    // min: 0 avoids holding idle sockets that go stale during long-running CLIs\n    pool: { min: 0, max: 10, idleTimeoutMillis: 30_000 },\n    acquireConnectionTimeout: 10000,\n    ssl: { rejectUnauthorized: false },\n};\n\n/** Node / pg / knex signals that the socket or pool is dead and a reconnect may help. */\nconst CONNECTION_ERROR_CODES = new Set([\n    \"ECONNRESET\",\n    \"ECONNREFUSED\",\n    \"EPIPE\",\n    \"ETIMEDOUT\",\n    \"ENOTFOUND\",\n    \"EHOSTUNREACH\",\n    \"ENETUNREACH\",\n    \"ECONNABORTED\",\n    \"CONNECTION_ENDED\",\n    \"CONNECTION_CLOSED\",\n    // PostgreSQL SQLSTATE class 08xxx (connection exception) + admin shutdowns\n    \"08000\",\n    \"08001\",\n    \"08003\",\n    \"08004\",\n    \"08006\",\n    \"08007\",\n    \"08P01\",\n    \"57P01\",\n    \"57P02\",\n    \"57P03\",\n]);\n\n// Note: \"Timeout acquiring a connection\" is pool contention (all slots busy),\n// not a dead socket — reconnecting destroys healthy clients and makes it worse.\nconst CONNECTION_ERROR_MESSAGE_RE =\n    /connection (terminated|ended|closed|destroyed|reset|refused|not open)|Connection (terminated|ended) unexpectedly|Client has encountered a connection error|server closed the connection|Cannot use a pool after calling end|This socket has been ended|connect ECONNRESET/i;\n\nexport class Db {\n    static async init(context, options = {}) {\n        const buildConfig = async () => {\n            const defs = {\n                dbName: \"string\",\n                dbProfile: \"boolean default false\",\n                /** Cap knex pool size (default 10). Size ≈ expected concurrency + headroom. */\n                dbPoolMax: \"number\",\n            };\n            const discovered = context?.params?.getAllForModule?.(\"db\", defs) ?? {};\n            const merged = { ...discovered, ...options };\n\n            let { dbName, dbProfile } = merged;\n            let dbConnectionString = options.dbConnectionString ?? options.connectionString;\n            let connectionParam = dbConnectionString ? \"options\" : null;\n\n            if (!dbConnectionString) {\n                const src = context?.args?.getSource?.(\"dbConnectionString\");\n                if (src === \"cli\" || src === \"overrides\" || src === \"config\") {\n                    dbConnectionString = await context.params.get(\"dbConnectionString\", \"string\");\n                    connectionParam = \"dbConnectionString\";\n                }\n            }\n\n            if (!dbConnectionString && dbName && /^(postgresql|mysql):\\/\\//.test(dbName)) {\n                dbConnectionString = dbName;\n                dbName = undefined;\n            }\n\n            if (!dbConnectionString && dbName) {\n                const paramName = `dbConnectionString${capitalizeFirstLetter(dbName)}`;\n                dbConnectionString = await context.params.get(paramName, \"string\");\n                connectionParam = paramName;\n                if (!dbConnectionString) {\n                    throw new ParamError(\n                        `Db: cannot find dbConnectionString for dbName=\"${dbName}\" (looked for param \"${paramName}\")`\n                    );\n                }\n            }\n\n            if (!dbConnectionString) {\n                dbConnectionString = await context.params.get(\"dbConnectionString\", \"string\");\n                if (dbConnectionString) {\n                    connectionParam = \"dbConnectionString\";\n                }\n            }\n\n            if (!dbConnectionString) {\n                if (!dbName) {\n                    const env = context?.args?.env;\n                    // Never silently fall back to \"local\" on production/stage — that\n                    // masked missing DB_NAME_* / --dbName as a localhost:6032 connect.\n                    if (env && String(env).toLowerCase() !== \"local\") {\n                        throw new ParamError(\n                            `Db: dbName not set for env=\"${env}\" (set --dbName or DB_NAME_${String(env).toUpperCase()})`\n                        );\n                    }\n                    dbName = \"local\";\n                }\n                const paramName = `dbConnectionString${capitalizeFirstLetter(dbName)}`;\n                dbConnectionString = await context.params.get(paramName, \"string\");\n                connectionParam = paramName;\n                if (!dbConnectionString) {\n                    throw new ParamError(\n                        `Db: cannot find dbConnectionString for dbName=\"${dbName}\" (looked for param \"${paramName}\")`\n                    );\n                }\n            }\n\n            const displayName = resolveDbDisplayName(\n                dbName,\n                connectionParam,\n                context?.args?.env,\n                merged.name\n            );\n\n            const poolMaxRaw = merged.dbPoolMax ?? merged.pool?.max;\n            const poolMax = Number(poolMaxRaw);\n            const pool = {\n                ...KNEX_DEFAULTS.pool,\n                ...(merged.pool && typeof merged.pool === \"object\" ? merged.pool : {}),\n            };\n            if (Number.isFinite(poolMax) && poolMax >= 1) {\n                pool.max = Math.floor(poolMax);\n            }\n\n            return {\n                ...KNEX_DEFAULTS,\n                connectionString: dbConnectionString,\n                name: displayName,\n                profile: !!dbProfile,\n                logger: context.logger,\n                pool,\n                ...(merged.acquireConnectionTimeout != null\n                    ? { acquireConnectionTimeout: merged.acquireConnectionTimeout }\n                    : {}),\n            };\n        };\n\n        const config = context?.params?.runWithModuleAsync\n            ? await context.params.runWithModuleAsync(\"db\", buildConfig)\n            : await buildConfig();\n\n        return dbConnect(context, config);\n    }\n\n    /**\n     * Initialize a SIBLING database handler: a database that lives on the same\n     * server with the same credentials/options as an existing (\"base\") one, and\n     * differs only by its database name. Typical use: a per-tenant / per-subject\n     * database alongside a main database that keeps the shared tables.\n     *\n     *   context.db = await Db.init(context);                       // main\n     *   const sub  = await Db.initSibling(context, \"src_bright\");  // sibling\n     *\n     * LOCATION-AGNOSTIC BY DESIGN — the call gracefully falls back to the main\n     * database, so callers can use it for all subject data without knowing what\n     * has been migrated where:\n     *   - empty `siblingName`            → the main handler (same as Db.init)\n     *   - sibling DB does not exist yet  → the main handler (data not migrated;\n     *     it still lives in the main database)\n     * Callers that must not fall back can check `handler === context.db`.\n     *\n     * Connection string resolution for an actual sibling, in order:\n     *   1. Explicit override — param `dbConnectionStringSib<SiblingName>` (env\n     *      `DB_CONNECTION_STRING_SIB_<SIBLING_NAME>`, e.g. `src_bright` →\n     *      `DB_CONNECTION_STRING_SIB_SRC_BRIGHT`). Nobody needs this on day\n     *      one; it is the escape hatch for when a sibling later moves to its\n     *      own server — one env var, no code changes (the `SIB_` namespace\n     *      both overrides the connection and declares that the sibling\n     *      exists, so it never falls back to main).\n     *   2. Derived — take the base connection string and swap the database\n     *      name (after confirming the database exists on that server). The\n     *      base is `options.baseDb` (a Db handler), then\n     *      `options.baseConnectionString`, then `context.db`.\n     *\n     * Handlers are cached per name on the context (`context.siblingDbs`), so\n     * any number of components asking for the same sibling share one pool —\n     * including the \"falls back to main\" answer, which is remembered for the\n     * lifetime of the process (a mid-run migration is picked up on restart).\n     * Disconnect is registered via `context.registerCleanup`, same as the\n     * main handler.\n     *\n     * @param {object} context - context with params/logger (and usually .db)\n     * @param {string} [siblingName] - the sibling's database name (e.g. \"src_bright\")\n     * @param {object} [options] - { baseDb, baseConnectionString, dbProfile }\n     * @returns {Promise<Db>} connected handler (same proxy shape as Db.init)\n     */\n    static async initSibling(context, siblingName, options = {}) {\n        // Empty name → the main database, so call sites stay location-agnostic.\n        if (!siblingName) {\n            return resolveMainHandler(context, options);\n        }\n        if (!/^[a-zA-Z0-9_]+$/.test(siblingName)) {\n            throw new ParamError(\n                `Db.initSibling: invalid sibling database name \"${siblingName}\" (letters, digits and _ only)`\n            );\n        }\n\n        if (!context.siblingDbs) {\n            context.siblingDbs = new Map();\n        }\n        const cached = context.siblingDbs.get(siblingName);\n        if (cached) {\n            return cached;\n        }\n\n        // 1. explicit override: dbConnectionStringSib<SiblingName> param / env var.\n        // Its presence also DECLARES the sibling (it may live on another server),\n        // so the existence check below is skipped.\n        const overrideParam = `dbConnectionStringSib${camelizeDbName(siblingName)}`;\n        let connectionString = await context?.params?.get?.(overrideParam, \"string\");\n        if (connectionString) {\n            context.logger?.debug?.(\n                `[Db] sibling \"${siblingName}\": using override param \"${overrideParam}\"`\n            );\n        } else {\n            // 2. derive from the base connection string\n            const baseHandle = options.baseDb ?? context.db;\n            const base =\n                baseHandle?.config?.connectionString ?? options.baseConnectionString;\n            if (!base) {\n                throw new ParamError(\n                    `Db.initSibling: no base connection to derive \"${siblingName}\" from — ` +\n                        `init the main Db first (context.db = await Db.init(context)), ` +\n                        `or pass options.baseDb / options.baseConnectionString, ` +\n                        `or set the ${overrideParam} param (env ${toEnvKey(overrideParam)})`\n                );\n            }\n\n            // Not migrated yet? Fall back to the main database so the caller's\n            // code works the same before and after the split.\n            const exists = await databaseExistsOnServer(baseHandle, base, siblingName);\n            if (!exists) {\n                context.logger?.debug?.(\n                    `[Db] sibling \"${siblingName}\" does not exist — falling back to the main database`\n                );\n                const main = await resolveMainHandler(context, options);\n                context.siblingDbs.set(siblingName, main);\n                return main;\n            }\n\n            connectionString = replaceDatabaseName(base, siblingName);\n            context.logger?.debug?.(\n                `[Db] sibling \"${siblingName}\": derived from base (${formatConnectionEndpoint(base) ?? \"?\"})`\n            );\n        }\n\n        const config = {\n            ...KNEX_DEFAULTS,\n            connectionString,\n            name: siblingName,\n            profile: !!options.dbProfile,\n            logger: context.logger,\n        };\n\n        const handler = await dbConnect(context, config);\n        context.siblingDbs.set(siblingName, handler);\n        return handler;\n    }\n\n    /**\n     * Discover the sibling databases that are \"currently in use\", by name.\n     * Two sources, merged (env wins on duplicates):\n     *\n     *   1. ENV-DECLARED — every `DB_CONNECTION_STRING_SIB_<NAME>` env var\n     *      (the dedicated `SIB_` namespace) whose decoded name matches. This\n     *      covers siblings that moved to their own server: the same var that\n     *      overrides the connection also *registers* the database, so `.env`\n     *      stays the single convenient list.\n     *   2. SAME-SERVER SCAN — `SELECT datname FROM pg_database` on the base\n     *      server (PostgreSQL only), filtered the same way.\n     *\n     * The caller says what \"matches\": `{ prefix: \"src_\" }` or\n     * `{ match: /^src_/ }` — the toolkit does not guess a naming convention.\n     *\n     * @param {object} context - needs context.db (or options.baseDb) for the server scan\n     * @param {{ prefix?: string, match?: RegExp, baseDb?: object, env?: object }} options\n     * @returns {Promise<Array<{ name: string, origin: \"env\"|\"server\" }>>} sorted by name\n     */\n    static async discoverSiblings(context, options = {}) {\n        const { prefix, match, env = process.env } = options;\n        if (!prefix && !match) {\n            throw new ParamError(`Db.discoverSiblings: pass { prefix: \"...\" } or { match: /.../ }`);\n        }\n        const matches = match instanceof RegExp ? (n) => match.test(n) : (n) => n.startsWith(prefix);\n\n        const found = new Map();\n\n        // 1. env-declared siblings (possibly on other servers) — SIB_ namespace\n        for (const key of Object.keys(env)) {\n            const m = /^DB_CONNECTION_STRING_SIB_(.+)$/.exec(key);\n            if (!m || !env[key]) continue;\n            const name = m[1].toLowerCase();\n            if (matches(name)) {\n                found.set(name, \"env\");\n            }\n        }\n\n        // 2. same-server scan (PostgreSQL)\n        const base = options.baseDb ?? context?.db;\n        if (base) {\n            const connectionString = String(base.config?.connectionString ?? \"\");\n            if (connectionString.startsWith(\"postgresql\")) {\n                const { rows } = await base.raw(\n                    \"SELECT datname FROM pg_database WHERE datistemplate = false\",\n                );\n                for (const { datname } of rows) {\n                    if (matches(datname) && !found.has(datname)) {\n                        found.set(datname, \"server\");\n                    }\n                }\n            } else {\n                context?.logger?.warn?.(\n                    \"[Db] discoverSiblings: server scan supported for PostgreSQL only; using env-declared siblings\",\n                );\n            }\n        }\n\n        return [...found]\n            .map(([name, origin]) => ({ name, origin }))\n            .sort((a, b) => a.name.localeCompare(b.name));\n    }\n\n    /**\n     * Discover + connect: one handler per active sibling (cached, pooled —\n     * see initSibling). Pass `includeMain: true` to get `[context.db, ...]`,\n     * which is the usual shape for \"apply this DDL everywhere\" loops:\n     *\n     *   const dbs = await Db.initAllSiblings(context, { prefix: \"src_\", includeMain: true });\n     *   await ensureSchemaEverywhere(dbs, spec, { logger: context.logger });\n     *\n     * @param {object} context\n     * @param {{ prefix?: string, match?: RegExp, includeMain?: boolean, baseDb?: object, env?: object }} options\n     * @returns {Promise<Function[]>} connected handlers\n     */\n    static async initAllSiblings(context, options = {}) {\n        const discovered = await Db.discoverSiblings(context, options);\n        const handlers = [];\n        for (const { name } of discovered) {\n            handlers.push(await Db.initSibling(context, name, options));\n        }\n        return options.includeMain && context.db ? [context.db, ...handlers] : handlers;\n    }\n\n    constructor(config) {\n        if (!config || !config.connectionString) {\n            throw new ParamError(\"Db: connectionString is required\");\n        }\n\n        this.knexInstance = null;\n        this.isConnected = false;\n        this.queriesLog = [];\n        this._reconnectPromise = null;\n        /** Set by disconnect(); blocks reconnect and connect so exit does not hang. */\n        this._closed = false;\n        /** Every knex client we created — reconnect can leave extras that disconnect must kill. */\n        this._liveKnex = new Set();\n        /** After a failed reconnect, skip further attempts until this timestamp. */\n        this._reconnectCooldownUntil = 0;\n        /** Shorter acquire timeout used only while reconnecting. */\n        this._reconnectAcquireTimeoutMs = null;\n\n        this.config = {\n            testConnection: true,\n            profile: false,\n            pool: { min: 0, max: 10, idleTimeoutMillis: 30_000 },\n            acquireConnectionTimeout: 10000,\n            ssl: { rejectUnauthorized: false },\n            logger: console,\n            ...config,\n        };\n\n        this.logger = this.config.logger;\n\n        const instance = this;\n        const callableWrapper = function () {\n            throw new Error(\"This should never be called directly\");\n        };\n        callableWrapper._instance = instance;\n\n        return new Proxy(callableWrapper, {\n            apply: (target, _thisArg, argumentsList) => {\n                const inst = target._instance;\n                if (!inst.knexInstance) {\n                    throw new Error(\"Db: Not connected. Call connect() first.\");\n                }\n                return inst.wrapQueryBuilder(inst.knexInstance(...argumentsList));\n            },\n            get: (target, prop) => {\n                if (prop === \"_instance\") {\n                    return target._instance;\n                }\n\n                const inst = target._instance;\n\n                const ownMethods = [\n                    \"connect\",\n                    \"disconnect\",\n                    \"reconnect\",\n                    \"testConnection\",\n                    \"tableExists\",\n                    \"raw\",\n                    \"withConnectionRetry\",\n                    \"isConnectionError\",\n                    \"getQueryLog\",\n                    \"getKnex\",\n                    \"isConnectedToDb\",\n                    \"getErrorMessage\",\n                    \"detectClient\",\n                    \"attachProfiler\",\n                ];\n\n                if (prop in inst) {\n                    const value = inst[prop];\n                    if (typeof value === \"function\" && ownMethods.includes(prop)) {\n                        return value.bind(inst);\n                    }\n                    if (typeof value !== \"function\") {\n                        return value;\n                    }\n                }\n\n                if (inst.knexInstance) {\n                    const knexProp = inst.knexInstance[prop];\n                    if (typeof knexProp === \"function\") {\n                        if (prop === \"raw\") {\n                            return (...args) => inst.raw(...args);\n                        }\n                        return knexProp.bind(inst.knexInstance);\n                    }\n                    return knexProp;\n                }\n\n                if (prop in inst) {\n                    const method = inst[prop];\n                    if (typeof method === \"function\") {\n                        return method.bind(inst);\n                    }\n                    return method;\n                }\n\n                return undefined;\n            },\n        });\n    }\n\n    detectClient(connectionString) {\n        if (connectionString.match(/^postgresql/)) {\n            return \"pg\";\n        }\n        if (connectionString.match(/^mysql/)) {\n            return \"mysql2\";\n        }\n        return null;\n    }\n\n    async connect() {\n        if (this._closed) {\n            throw new ParamError(\"Db: Connection closed\");\n        }\n        if (this.isConnected && this.knexInstance) {\n            this.logger.warn?.(\"[Db] Already connected\");\n            return;\n        }\n\n        const client = this.detectClient(this.config.connectionString);\n        if (!client) {\n            throw new ParamError(\n                \"Db: Cannot determine client type from connection string. Expected postgresql:// or mysql://\"\n            );\n        }\n\n        try {\n            const connectionConfig = {\n                connectionString: this.config.connectionString,\n                family: 4,\n            };\n\n            const acquireTimeout = this._reconnectAcquireTimeoutMs\n                ?? this.config.acquireConnectionTimeout;\n            this.knexInstance = knex({\n                client,\n                connection: connectionConfig,\n                pool: this.config.pool,\n                acquireConnectionTimeout: acquireTimeout,\n                ...(this.config.ssl && { ssl: this.config.ssl }),\n            });\n            this._liveKnex.add(this.knexInstance);\n            this.knexInstance.on?.(\"error\", (err) => {\n                if (this._closed) return;\n                this.logger.warn?.(\n                    `[Db] Connection error (${this.getErrorMessage(err)})`\n                );\n            });\n\n            if (this._closed) {\n                await this._destroyKnex(this.knexInstance, \"connect aborted (closed)\");\n                this.knexInstance = null;\n                throw new ParamError(\"Db: Connection closed\");\n            }\n\n            if (this.config.profile) {\n                this.attachProfiler();\n            }\n\n            if (this.config.testConnection) {\n                await this.testConnection();\n            }\n\n            if (this._closed) {\n                await this._destroyKnex(this.knexInstance, \"connect aborted (closed)\");\n                this.knexInstance = null;\n                throw new ParamError(\"Db: Connection closed\");\n            }\n\n            this.isConnected = true;\n            this.logger.debug?.(formatDbConnectMessage(this.config.name, this.config.connectionString));\n        } catch (error) {\n            // Always tear down a half-open pool (e.g. testConnection ENOTFOUND),\n            // otherwise the next reconnect/disconnect waits on a dead knex forever.\n            const failed = this.knexInstance;\n            this.knexInstance = null;\n            this.isConnected = false;\n            if (failed) {\n                await this._destroyKnex(failed, \"connect failed\");\n            }\n            if (error instanceof ParamError) {\n                throw error;\n            }\n            const errorMsg = this.getErrorMessage(error);\n            throw new ParamError(`Db: Connection failed - ${errorMsg}`);\n        }\n    }\n\n    /**\n     * Destroy a knex pool without hanging exit on stuck TCP sockets (ETIMEDOUT).\n     * @param {import(\"knex\").Knex | null | undefined} knexInst\n     * @param {string} [reason]\n     * @param {number} [timeoutMs]\n     */\n    async _destroyKnex(knexInst, reason = \"destroy\", timeoutMs = 3_000) {\n        if (!knexInst || typeof knexInst.destroy !== \"function\") return;\n        this._liveKnex.delete(knexInst);\n        try {\n            await Promise.race([\n                knexInst.destroy(),\n                new Promise((_, reject) => {\n                    const t = setTimeout(\n                        () => reject(new Error(`Db: ${reason} timed out after ${timeoutMs}ms`)),\n                        timeoutMs,\n                    );\n                    t.unref?.();\n                }),\n            ]);\n        } catch (error) {\n            this.logger.debug?.(\n                `[Db] ${reason}: ${this.getErrorMessage(error)}`\n            );\n        }\n    }\n\n    async disconnect() {\n        this._closed = true;\n        this.isConnected = false;\n        this.knexInstance = null;\n        this.queriesLog = [];\n\n        // Do not await an in-flight reconnect — connect() may be stuck in\n        // testConnection / DNS for acquireConnectionTimeout (often 60s).\n        // Tear down every knex we created, including ones spawned mid-reconnect.\n        const all = [...this._liveKnex];\n        this._liveKnex.clear();\n        await Promise.all(all.map((inst) => this._destroyKnex(inst, \"disconnect\")));\n        if (all.length > 0) {\n            this.logger.debug?.(formatDbDisconnectMessage(this.config.name, this.config.connectionString));\n        }\n    }\n\n    /**\n     * True when the error indicates a dead socket / pool that a fresh connect may fix.\n     * Safe to call as `Db.prototype.isConnectionError(err)` or via a connected handle.\n     */\n    isConnectionError(error) {\n        if (!error) {\n            return false;\n        }\n\n        if (error instanceof AggregateError && Array.isArray(error.errors)) {\n            return error.errors.some((e) => this.isConnectionError(e));\n        }\n\n        const code = error.code ?? error.errno;\n        if (code != null && CONNECTION_ERROR_CODES.has(String(code))) {\n            return true;\n        }\n\n        const msg = error instanceof Error ? error.message : String(error);\n        return CONNECTION_ERROR_MESSAGE_RE.test(msg);\n    }\n\n    /**\n     * Destroy the current knex pool and open a new one. Concurrent callers share one attempt.\n     * No-ops once disconnect() has closed the handle.\n     */\n    async reconnect() {\n        if (this._closed) {\n            return;\n        }\n        if (this._reconnectCooldownUntil && Date.now() < this._reconnectCooldownUntil) {\n            return;\n        }\n        if (this._reconnectPromise) {\n            await this._reconnectPromise;\n            return;\n        }\n\n        this._reconnectPromise = (async () => {\n            if (this._closed) return;\n\n            const old = this.knexInstance;\n            this.isConnected = false;\n            this.knexInstance = null;\n            this.queriesLog = [];\n\n            if (old) {\n                await this._destroyKnex(old, \"destroy during reconnect\");\n            }\n\n            if (this._closed) return;\n            // Don't inherit the caller's 60s acquire timeout while the host is down.\n            this._reconnectAcquireTimeoutMs = 3_000;\n            try {\n                await this.connect();\n                this._reconnectCooldownUntil = 0;\n            } catch (error) {\n                this._reconnectCooldownUntil = Date.now() + 5_000;\n                throw error;\n            } finally {\n                this._reconnectAcquireTimeoutMs = null;\n            }\n        })();\n\n        try {\n            await this._reconnectPromise;\n        } finally {\n            this._reconnectPromise = null;\n        }\n    }\n\n    async reconnectAfterConnectionError(error) {\n        if (this._closed) {\n            return;\n        }\n        if (this._reconnectCooldownUntil && Date.now() < this._reconnectCooldownUntil) {\n            return;\n        }\n        this.logger.warn?.(\n            `[Db] Connection lost (${this.getErrorMessage(error)}) — reconnecting…`\n        );\n        try {\n            await this.reconnect();\n        } catch {\n            // connect() already logged the test failure; caller retries or throws.\n        }\n    }\n\n    /**\n     * Run `fn`; on a connection error, reconnect once (by default) and retry `fn`.\n     * `fn` should look up `this.knexInstance` each call so the retry uses the new client.\n     */\n    async withConnectionRetry(fn, { retries = 1 } = {}) {\n        let lastError;\n        for (let attempt = 0; attempt <= retries; attempt++) {\n            try {\n                return await fn();\n            } catch (error) {\n                lastError = error;\n                if (this._closed || !this.isConnectionError(error) || attempt >= retries) {\n                    throw error;\n                }\n                await this.reconnectAfterConnectionError(error);\n                if (this._closed) {\n                    throw error;\n                }\n            }\n        }\n        throw lastError;\n    }\n\n    /**\n     * Wrap a knex QueryBuilder / Raw so that awaiting it retries once after reconnect\n     * when the first attempt dies with a connection error.\n     */\n    wrapQueryBuilder(builder) {\n        if (!builder || typeof builder.then !== \"function\" || builder.__dbReconnectWrapped) {\n            return builder;\n        }\n\n        builder.__dbReconnectWrapped = true;\n        const inst = this;\n        const protoThen = Object.getPrototypeOf(builder)?.then;\n        if (typeof protoThen !== \"function\") {\n            return builder;\n        }\n\n        builder.then = function (onFulfilled, onRejected) {\n            const run = async () => {\n                try {\n                    return await protoThen.call(builder);\n                } catch (error) {\n                    if (inst._closed || !inst.isConnectionError(error)) {\n                        throw error;\n                    }\n                    await inst.reconnectAfterConnectionError(error);\n                    if (inst._closed || !inst.knexInstance) {\n                        throw error;\n                    }\n\n                    if (typeof builder.clone === \"function\") {\n                        const retry = builder.clone();\n                        retry.client = inst.knexInstance.client;\n                        return await protoThen.call(retry);\n                    }\n\n                    if (typeof builder.toSQL === \"function\" && inst.knexInstance) {\n                        const sql = builder.toSQL();\n                        const statements = Array.isArray(sql) ? sql : [sql];\n                        let last;\n                        for (const stmt of statements) {\n                            last = await inst.knexInstance.raw(stmt.sql, stmt.bindings);\n                        }\n                        return last;\n                    }\n\n                    throw error;\n                }\n            };\n            return run().then(onFulfilled, onRejected);\n        };\n\n        return builder;\n    }\n\n    /** knex.raw with auto-reconnect on dead connections. */\n    raw(...args) {\n        if (!this.knexInstance) {\n            throw new Error(\"Db: Not connected. Call connect() first.\");\n        }\n        return this.wrapQueryBuilder(this.knexInstance.raw(...args));\n    }\n\n    getErrorMessage(error) {\n        if (error instanceof AggregateError) {\n            const errors = error.errors || [];\n\n            if (errors.length > 0) {\n                const firstError = errors[0];\n                const firstErrorMsg =\n                    firstError instanceof Error ? firstError.message : String(firstError);\n\n                const allSimilar = errors.every((e) => {\n                    const msg = e instanceof Error ? e.message : String(e);\n                    const codeMatch = msg.match(/^(\\w+)\\s/);\n                    const firstCodeMatch = firstErrorMsg.match(/^(\\w+)\\s/);\n                    return codeMatch && firstCodeMatch && codeMatch[1] === firstCodeMatch[1];\n                });\n\n                if (allSimilar && errors.length > 1) {\n                    const addresses = errors\n                        .map((e) => {\n                            const msg = e instanceof Error ? e.message : String(e);\n                            const addrMatch = msg.match(/([:\\d.]+:\\d+)/);\n                            return addrMatch ? addrMatch[1] : null;\n                        })\n                        .filter(Boolean);\n\n                    if (addresses.length > 0) {\n                        const codeMatch = firstErrorMsg.match(/^(\\w+)\\s/);\n                        const code = codeMatch ? codeMatch[1] : \"Connection error\";\n                        return `${code} (tried: ${addresses.join(\", \")})`;\n                    }\n                }\n\n                const uniqueMessages = [\n                    ...new Set(\n                        errors.map((e) => (e instanceof Error ? e.message : String(e)))\n                    ),\n                ];\n\n                if (uniqueMessages.length === 1) {\n                    return uniqueMessages[0];\n                }\n\n                return uniqueMessages.join(\"; \");\n            }\n\n            return error.message || \"Multiple errors occurred\";\n        }\n\n        if (error instanceof Error) {\n            const code = error.code;\n            if (code) {\n                return `${code}: ${error.message || String(error)}`;\n            }\n            return error.message || String(error);\n        }\n\n        if (typeof error === \"string\") {\n            return error;\n        }\n\n        if (error && typeof error === \"object\" && \"message\" in error) {\n            const msg = String(error.message);\n            const code = error.code;\n            if (code) {\n                return `${code}: ${msg}`;\n            }\n            return msg;\n        }\n\n        return String(error) || \"Unknown error\";\n    }\n\n    async testConnection() {\n        if (!this.knexInstance) {\n            throw new Error(\"Db: Not connected. Call connect() first.\");\n        }\n\n        try {\n            const result = await this.knexInstance.raw(\"SELECT 2+3 AS result\");\n            const isOk = result.rows?.[0]?.result === 5 || result[0]?.[0]?.result === 5;\n            this.logger.debug?.(`[Db] Connection test: ${isOk ? \"OK\" : \"FAILED\"}`);\n            return isOk;\n        } catch (error) {\n            const errorMsg = this.getErrorMessage(error);\n            this.logger.error?.(`[Db] Connection test failed: ${errorMsg}`);\n            throw new ParamError(`Db: Connection test failed - ${errorMsg}`);\n        }\n    }\n\n    attachProfiler() {\n        if (!this.knexInstance) {\n            return;\n        }\n\n        this.queriesLog = [];\n        this.knexInstance.queriesLog = this.queriesLog;\n\n        // Knex emits fresh Object.assign(...) copies on \"query\" and \"query-response\",\n        // so __startTime on the query object does not survive — track per-connection FIFO.\n        const startsByConnection = new Map();\n\n        const pushStart = (query) => {\n            const uid = query?.__knexUid ?? \"\";\n            if (!startsByConnection.has(uid)) {\n                startsByConnection.set(uid, []);\n            }\n            startsByConnection.get(uid).push(process.hrtime());\n        };\n\n        const popStart = (query) => {\n            const uid = query?.__knexUid ?? \"\";\n            const stack = startsByConnection.get(uid);\n            if (!stack?.length) {\n                return null;\n            }\n            return stack.pop();\n        };\n\n        const isTimeoutError = (error) =>\n            error?.name === \"KnexTimeoutError\" ||\n            /query timeout|timeout exceeded/i.test(String(error?.message ?? \"\"));\n\n        const logQueryEntry = (query, start, { error } = {}) => {\n            let executionTimeMs;\n            if (start) {\n                const [seconds, nanoseconds] = process.hrtime(start);\n                executionTimeMs = (seconds * 1000 + nanoseconds / 1e6).toFixed(2);\n            } else if (error?.timeout != null) {\n                executionTimeMs = Number(error.timeout).toFixed(2);\n            } else {\n                executionTimeMs = \"?\";\n            }\n\n            let status = \"ok\";\n            if (error) {\n                status = isTimeoutError(error) ? \"timeout\" : \"error\";\n            }\n\n            const logEntry = {\n                sql: query?.sql,\n                bindings: query?.bindings || [],\n                executionTimeMs,\n                status,\n            };\n            if (error) {\n                logEntry.error = error.message ?? String(error);\n            }\n\n            this.queriesLog.push(logEntry);\n            const suffix = error ? ` | ${status}: ${logEntry.error}` : \"\";\n            this.logger.debug?.(\n                `[Db] Query: ${query?.sql} | Duration: ${executionTimeMs}ms${suffix}`,\n            );\n        };\n\n        const handleQueryError = (error, query) => {\n            const start = popStart(query);\n            logQueryEntry(query, start, { error });\n            this.logger.error?.(`[Db] Query failed: ${query?.sql}`, error);\n        };\n\n        this.knexInstance.on(\"query\", (query) => {\n            pushStart(query);\n        });\n\n        this.knexInstance.on(\"query-response\", (_response, query) => {\n            const start = popStart(query);\n            if (!start) {\n                return;\n            }\n            logQueryEntry(query, start);\n        });\n\n        this.knexInstance.on(\"query-error\", (error, query) => {\n            handleQueryError(error, query);\n        });\n\n        // Builder queries emit \"query\" / \"query-error\" on the builder, not always on client.\n        const hookBuilder = (builder) => {\n            if (!builder || builder.__dbProfilerHooked) {\n                return;\n            }\n            builder.__dbProfilerHooked = true;\n            builder.on(\"query\", pushStart);\n            builder.on(\"query-error\", handleQueryError);\n        };\n\n        const client = this.knexInstance.client;\n        if (client && !client.__dbProfilerPatched) {\n            client.__dbProfilerPatched = true;\n            if (typeof client.queryBuilder === \"function\") {\n                const origQueryBuilder = client.queryBuilder.bind(client);\n                client.queryBuilder = (...args) => {\n                    const builder = origQueryBuilder(...args);\n                    hookBuilder(builder);\n                    return builder;\n                };\n            }\n        }\n    }\n\n    getQueryLog() {\n        return [...this.queriesLog];\n    }\n\n    async tableExists(tableName) {\n        if (!this.knexInstance) {\n            throw new Error(\"Db: Not connected. Call connect() first.\");\n        }\n\n        try {\n            return await this.withConnectionRetry(() =>\n                this.knexInstance.schema.hasTable(tableName)\n            );\n        } catch (error) {\n            this.logger.error?.(`[Db] Error checking table existence: ${error.message}`);\n            throw error;\n        }\n    }\n\n    getKnex() {\n        if (!this.knexInstance) {\n            throw new Error(\"Db: Not connected. Call connect() first.\");\n        }\n        return this.knexInstance;\n    }\n\n    isConnectedToDb() {\n        return this.isConnected && this.knexInstance !== null;\n    }\n}\n\nfunction capitalizeFirstLetter(str) {\n    return str.charAt(0).toUpperCase() + str.slice(1);\n}\n\n/**\n * The main database handler, for initSibling's fallbacks: the base handle when\n * one was passed, otherwise `context.db` (initialized on demand, so an\n * initSibling-only script still works).\n */\nasync function resolveMainHandler(context, options = {}) {\n    if (options.baseDb) {\n        return options.baseDb;\n    }\n    if (!context.db) {\n        context.db = await Db.init(context);\n    }\n    return context.db;\n}\n\n/**\n * Does `databaseName` exist on the base server? Checked via an existing handle\n * when available (no extra connection), else a short-lived one. Non-PostgreSQL\n * bases skip the check (returns true — connection will tell).\n */\nasync function databaseExistsOnServer(baseHandle, baseConnectionString, databaseName) {\n    if (!String(baseConnectionString).startsWith(\"postgresql\")) {\n        return true;\n    }\n    const query = \"SELECT 1 FROM pg_database WHERE datname = ?\";\n    if (baseHandle) {\n        const { rows } = await baseHandle.raw(query, [databaseName]);\n        return rows.length > 0;\n    }\n    const shortLived = knex({\n        client: \"pg\",\n        connection: { connectionString: baseConnectionString },\n        pool: { min: 0, max: 1 },\n    });\n    try {\n        const { rows } = await shortLived.raw(query, [databaseName]);\n        return rows.length > 0;\n    } finally {\n        await shortLived.destroy();\n    }\n}\n\n/**\n * Database name → camelCase param suffix: \"src_bright\" → \"SrcBright\",\n * so the override param becomes dbConnectionStringSibSrcBright\n * (env DB_CONNECTION_STRING_SIB_SRC_BRIGHT).\n */\nfunction camelizeDbName(name) {\n    return name\n        .split(/[_-]+/)\n        .filter(Boolean)\n        .map(capitalizeFirstLetter)\n        .join(\"\");\n}\n\n/** camelCase param name → its SNAKE_CASE env var (for error messages only). */\nfunction toEnvKey(key) {\n    return key.replace(/([A-Z])/g, \"_$1\").toUpperCase();\n}\n\n/**\n * Replace the database name in a connection string, keeping everything else\n * (credentials, host, port, query options like sslmode) intact.\n * Exported for reuse (e.g. database-splitting tools) and tests.\n */\nexport function replaceDatabaseName(connectionString, databaseName) {\n    let url;\n    try {\n        url = new URL(connectionString);\n    } catch {\n        throw new ParamError(\n            `Db: cannot parse connection string to derive a sibling database from it`\n        );\n    }\n    url.pathname = `/${databaseName}`;\n    return url.toString();\n}\n\nfunction resolveDbDisplayName(dbName, connectionParam, argsEnv, mergedName) {\n    if (dbName) {\n        return dbName;\n    }\n    if (mergedName) {\n        return mergedName;\n    }\n    if (\n        connectionParam?.startsWith(\"dbConnectionString\") &&\n        connectionParam.length > \"dbConnectionString\".length\n    ) {\n        return connectionParam.slice(\"dbConnectionString\".length).toLowerCase();\n    }\n    if (connectionParam === \"dbConnectionString\" && argsEnv) {\n        return argsEnv;\n    }\n    return undefined;\n}\n\nfunction formatDbConnectMessage(name, connectionString) {\n    const endpointSuffix = formatConnectionEndpointSuffix(connectionString);\n    if (name) {\n        return `[Db] Connected to database \"${name}\"${endpointSuffix}`;\n    }\n    return `[Db] Connected${endpointSuffix}`;\n}\n\nfunction formatDbDisconnectMessage(name, connectionString) {\n    const endpointSuffix = formatConnectionEndpointSuffix(connectionString);\n    if (name) {\n        return `[Db] Disconnected from database \"${name}\"${endpointSuffix}`;\n    }\n    return `[Db] Disconnected${endpointSuffix}`;\n}\n\nfunction formatDbInstanceMessage(action, name) {\n    if (name) {\n        return `[Db] instance \"${name}\" ${action}`;\n    }\n    return `[Db] instance ${action}`;\n}\n\nfunction formatConnectionEndpointSuffix(connectionString) {\n    const endpoint = formatConnectionEndpoint(connectionString);\n    return endpoint ? ` (${endpoint})` : \"\";\n}\n\nfunction formatConnectionEndpoint(connectionString) {\n    try {\n        const url = new URL(connectionString);\n        const host = url.hostname;\n        if (!host) {\n            return null;\n        }\n\n        let port = url.port;\n        if (!port) {\n            if (url.protocol === \"postgresql:\") {\n                port = \"5432\";\n            } else if (url.protocol === \"mysql:\") {\n                port = \"3306\";\n            }\n        }\n\n        return port ? `${host}:${port}` : host;\n    } catch {\n        return null;\n    }\n}\n\nasync function dbConnect(context, config) {\n    try {\n        const db = new Db(config);\n\n        context.registerCleanup(async () => {\n            await db.disconnect();\n            context.logger.debug?.(formatDbInstanceMessage(\"disconnected\", config.name));\n        });\n\n        await db.connect();\n\n        context.logger.debug?.(formatDbInstanceMessage(\"initialized\", config.name));\n\n        return db;\n    } catch (error) {\n        if (error instanceof ParamError) {\n            throw error;\n        }\n        const errorMsg = error instanceof Error ? error.message : String(error);\n        throw new ParamError(`[Db] connect error: ${errorMsg}`);\n    }\n}\n","/**\n * Error classes for the CLI toolkit\n */\n\nexport class FrameworkError extends Error {\n    constructor(message) {\n        super(message);\n        this.name = \"FrameworkError\";\n    }\n}\n\nexport class ParamError extends FrameworkError {\n    constructor(message) {\n        super(message);\n        this.name = \"ParamError\";\n    }\n}\n\nexport class InitError extends FrameworkError {\n    constructor(message) {\n        super(message);\n        this.name = \"InitError\";\n    }\n}\n\nexport class CriticalRequestError extends FrameworkError {\n    constructor(message) {\n        super(message);\n        this.name = \"CriticalRequestError\";\n    }\n}\n\nexport class ControlFlowError extends Error {\n    constructor(message) {\n        super(message);\n        this.name = \"ControlFlowError\";\n    }\n}\n\nexport class HttpClientError extends FrameworkError {\n    constructor(message,   cause) {\n        super(message);this.cause = cause;;\n        this.name = \"HttpClientError\";\n    }\n}\n\nexport class FileDatabaseError extends FrameworkError {\n    constructor(message) {\n        super(message);\n        this.name = \"FileDatabaseError\";\n    }\n}\n\n","/**\n * Declarative, idempotent DDL — \"make sure this schema exists\" helpers.\n *\n * Components describe the schema they need (tables, columns, indexes,\n * extensions) once, as data; `ensureSchema` diffs that spec against a live\n * database and applies only what's missing:\n *\n *   - table missing            → CREATE TABLE with all columns + indexes\n *   - table there, column not  → ALTER TABLE ADD COLUMN (never drops/changes)\n *   - index/unique missing     → CREATE [UNIQUE] INDEX IF NOT EXISTS\n *   - extension missing        → CREATE EXTENSION IF NOT EXISTS\n *\n * Because the input is a spec (not imperative code), the same call can be\n * repeated over any number of databases — the main one and every sibling —\n * and each gets exactly the DDL it lacks. See Db.initSibling /\n * Db.discoverSiblings for getting those handles.\n *\n * Spec shape:\n *\n *   {\n *       extensions: [\"uuid-ossp\"],\n *       tables: {\n *           my_table: {\n *               columns: {\n *                   id:   (t, db) => t.uuid(\"id\").primary().defaultTo(db.raw(\"uuid_generate_v4()\")),\n *                   name: (t) => t.text(\"name\").notNullable(),\n *               },\n *               indexes: [\n *                   { columns: [\"name\"], name: \"my_table_name_idx\" },\n *                   { columns: [\"a\", \"b\"], name: \"my_table_ab_uniq\", unique: true },\n *               ],\n *           },\n *       },\n *   }\n *\n * Every function accepts `{ dryRun: true }` and then only *reports* what it\n * would do (returned in the report, logged when a logger is given) without\n * touching the database.\n */\n\n/** @typedef {{ columns: Record<string, Function>, indexes?: Array<{ columns: string[], name: string, unique?: boolean }> }} TableSpec */\n/** @typedef {{ extensions?: string[], tables?: Record<string, TableSpec> }} SchemaSpec */\n\nconst dbLabel = (db) => db?.config?.name ?? \"db\";\n\n/**\n * CREATE EXTENSION IF NOT EXISTS (PostgreSQL). No-op report entry on dryRun.\n *\n * @param {Function} db - a connected Db/knex handle\n * @param {string} name - extension name, e.g. \"uuid-ossp\"\n * @param {{ dryRun?: boolean, logger?: object }} [options]\n * @returns {Promise<{ action: string }>}\n */\nexport async function ensureExtension(db, name, options = {}) {\n    const action = `CREATE EXTENSION IF NOT EXISTS \"${name}\"`;\n    if (!options.dryRun) {\n        await db.raw(action);\n    }\n    options.logger?.silly?.(`[ensure] ${dbLabel(db)}: ${action}${options.dryRun ? \" (dryRun)\" : \"\"}`);\n    return { action };\n}\n\n/**\n * Create a table when missing; when it exists, add any missing columns and\n * indexes from the spec. Never drops or alters existing columns.\n *\n * @param {Function} db\n * @param {string} tableName\n * @param {TableSpec} spec\n * @param {{ dryRun?: boolean, logger?: object }} [options]\n * @returns {Promise<string[]>} human-readable list of applied (or planned) DDL\n */\nexport async function ensureTable(db, tableName, spec, options = {}) {\n    const { dryRun = false, logger } = options;\n    const actions = [];\n    const exists = await db.tableExists(tableName);\n\n    if (!exists) {\n        actions.push(`CREATE TABLE ${tableName} (${Object.keys(spec.columns).length} columns)`);\n        if (!dryRun) {\n            await db.schema.createTable(tableName, (t) => {\n                for (const define of Object.values(spec.columns)) {\n                    define(t, db);\n                }\n            });\n        }\n    } else {\n        // Column-level ensure: add whatever the spec has that the table lacks.\n        const missing = [];\n        for (const column of Object.keys(spec.columns)) {\n            if (!(await db.schema.hasColumn(tableName, column))) {\n                missing.push(column);\n            }\n        }\n        if (missing.length > 0) {\n            actions.push(`ALTER TABLE ${tableName} ADD COLUMN ${missing.join(\", \")}`);\n            if (!dryRun) {\n                await db.schema.alterTable(tableName, (t) => {\n                    for (const column of missing) {\n                        spec.columns[column](t, db);\n                    }\n                });\n            }\n        }\n    }\n\n    for (const index of spec.indexes ?? []) {\n        const indexActions = await ensureIndex(db, tableName, index, options);\n        actions.push(...indexActions);\n    }\n\n    for (const action of actions) {\n        logger?.silly?.(`[ensure] ${dbLabel(db)}: ${action}${dryRun ? \" (dryRun)\" : \"\"}`);\n    }\n    return actions;\n}\n\n/**\n * Ensure a (unique) index exists. On PostgreSQL this is a real existence check\n * (`CREATE [UNIQUE] INDEX IF NOT EXISTS`); other dialects fall back to\n * attempt-and-tolerate-\"already exists\".\n *\n * @param {Function} db\n * @param {string} tableName\n * @param {{ columns: string[], name: string, unique?: boolean }} index\n * @param {{ dryRun?: boolean, logger?: object }} [options]\n * @returns {Promise<string[]>}\n */\nexport async function ensureIndex(db, tableName, index, options = {}) {\n    const { dryRun = false } = options;\n    const kind = index.unique ? \"UNIQUE INDEX\" : \"INDEX\";\n    const cols = index.columns.map((c) => `\"${c}\"`).join(\", \");\n    const isPg = String(db?.config?.connectionString ?? \"\").startsWith(\"postgresql\");\n\n    if (isPg) {\n        const sql = `CREATE ${kind} IF NOT EXISTS \"${index.name}\" ON \"${tableName}\" (${cols})`;\n        const { rows } = await db.raw(`SELECT 1 FROM pg_indexes WHERE indexname = ?`, [index.name]);\n        if (rows.length > 0) return [];\n        if (!dryRun) await db.raw(sql);\n        return [sql];\n    }\n\n    // Non-pg fallback: try, and treat \"already exists\" as success.\n    const sql = `CREATE ${kind} ${index.name} ON ${tableName} (${cols})`;\n    if (!dryRun) {\n        try {\n            await db.raw(sql);\n        } catch (error) {\n            if (!/already exists|duplicate/i.test(error?.message ?? \"\")) throw error;\n            return [];\n        }\n    }\n    return [sql];\n}\n\n/**\n * Apply a full schema spec to ONE database. Returns the list of applied\n * (or, with dryRun, planned) DDL statements — empty when everything is\n * already in place.\n *\n * @param {Function} db\n * @param {SchemaSpec} spec\n * @param {{ dryRun?: boolean, logger?: object }} [options]\n * @returns {Promise<{ database: string, actions: string[] }>}\n */\nexport async function ensureSchema(db, spec, options = {}) {\n    const actions = [];\n    for (const extension of spec.extensions ?? []) {\n        // Extensions are cheap no-ops when present; report only in dryRun.\n        const { action } = await ensureExtension(db, extension, options);\n        if (options.dryRun) actions.push(action);\n    }\n    for (const [tableName, tableSpec] of Object.entries(spec.tables ?? {})) {\n        actions.push(...(await ensureTable(db, tableName, tableSpec, options)));\n    }\n    return { database: dbLabel(db), actions };\n}\n\n/**\n * Apply a schema spec to MANY databases (e.g. the main DB plus every sibling).\n * Convenience loop over {@link ensureSchema} with a combined report and\n * per-database info logging.\n *\n * @param {Function[]} dbs - connected handles (see Db.initAllSiblings)\n * @param {SchemaSpec} spec\n * @param {{ dryRun?: boolean, logger?: object }} [options]\n * @returns {Promise<Array<{ database: string, actions: string[] }>>}\n */\nexport async function ensureSchemaEverywhere(dbs, spec, options = {}) {\n    const reports = [];\n    for (const db of dbs) {\n        const report = await ensureSchema(db, spec, options);\n        if (report.actions.length > 0) {\n            options.logger?.info?.(\n                `[ensure] ${report.database}: ${options.dryRun ? \"would apply\" : \"applied\"} ${report.actions.length} DDL statement(s)`,\n            );\n        }\n        reports.push(report);\n    }\n    return reports;\n}\n"],"mappings":"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","names":["sql","knex"]}