UNPKG

openclaw

Version:

Multi-channel AI gateway with extensible messaging integrations

139 lines (138 loc) • 5.16 kB
import { a as resolveGlobalSingleton } from "./global-singleton-0m-JziJW.mjs"; import { r as isSqliteWalResetSafeVersion } from "./node-sqlite-DWn4GVXM.mjs"; import { createRequire } from "node:module"; import { existsSync } from "node:fs"; import { posix } from "node:path"; import { getEnvironmentData, isMainThread, setEnvironmentData } from "node:worker_threads"; //#region src/infra/bun-sqlite-library.ts const WORKER_SELECTION_KEY = "openclaw.bunSqliteLibrarySelection"; function probeLibrary(path) { const { dlopen, FFIType } = createRequire(import.meta.url)("bun:ffi"); const library = dlopen(path, { sqlite3_libversion: { args: [], returns: FFIType.cstring }, sqlite3_compileoption_used: { args: [FFIType.cstring], returns: FFIType.i32 } }); try { return { version: String(library.symbols.sqlite3_libversion()), extensionLoadingSupported: library.symbols.sqlite3_compileoption_used(Buffer.from("OMIT_LOAD_EXTENSION\0")) === 0 }; } finally { library.close(); } } function selectLibrary(path) { const { Database } = createRequire(import.meta.url)("bun:sqlite"); Database.setCustomSQLite(path); } function createSelector(deps) { let selection; let failure; return (options = {}) => { if (failure) throw failure; if (selection) return selection; const override = options.explicitPath ?? (deps.env.OPENCLAW_SQLITE_LIBRARY?.trim() || void 0); if (!deps.isBun || deps.platform !== "darwin") { selection = override ? { source: "runtime", ignoredOverride: "OPENCLAW_SQLITE_LIBRARY requires Bun on macOS" } : { source: "runtime" }; return selection; } const prefix = deps.env.HOMEBREW_PREFIX?.trim(); const candidates = override !== void 0 ? [override] : [.../* @__PURE__ */ new Set([ ...prefix ? [posix.join(prefix, "opt/sqlite/lib/libsqlite3.dylib")] : [], "/opt/homebrew/opt/sqlite/lib/libsqlite3.dylib", "/usr/local/opt/sqlite/lib/libsqlite3.dylib", "/opt/local/lib/libsqlite3.dylib" ])]; for (const path of candidates) { let probe; try { try { probe = deps.probe(path); } catch (error) { throw deps.exists(path) ? error : new Error("missing file", { cause: error }); } if (!isSqliteWalResetSafeVersion(probe.version)) throw new Error(`SQLite version ${probe.version} below the WAL safety floor`); if (!probe.extensionLoadingSupported) throw new Error("built with SQLITE_OMIT_LOAD_EXTENSION"); } catch (error) { if (override === void 0) continue; failure = selectionError(path, error); throw failure; } try { deps.select(path); } catch (error) { failure = selectionError(path, error); throw failure; } selection = { source: override === void 0 ? "discovered" : "env", path, version: probe.version, extensionLoadingSupported: true }; return selection; } selection = { source: "runtime" }; return selection; }; } function selectionError(path, error) { return new Error(`Cannot use SQLite library ${path}: ${error instanceof Error ? error.message : String(error)}. Fix or unset OPENCLAW_SQLITE_LIBRARY; install a supported library with brew install sqlite.`, { cause: error }); } function inheritedSelection() { const value = getEnvironmentData(WORKER_SELECTION_KEY); if (value === void 0) return; if (value !== null && typeof value === "object" && !Array.isArray(value)) { const source = "source" in value ? value.source : void 0; if (source === "runtime") return { source: "runtime" }; const path = "path" in value ? value.path : void 0; const version = "version" in value ? value.version : void 0; const extensionLoadingSupported = "extensionLoadingSupported" in value ? value.extensionLoadingSupported : void 0; if ((source === "env" || source === "discovered") && typeof path === "string" && typeof version === "string" && extensionLoadingSupported === true) return { source, path, version, extensionLoadingSupported: true }; } throw new Error("Invalid inherited SQLite library selection"); } function createRuntimeSelector() { const isBun = Boolean(process.versions.bun); const sharedLibrary = isBun && process.platform === "darwin"; const inherited = sharedLibrary && !isMainThread ? inheritedSelection() : void 0; if (inherited) return () => inherited; const select = createSelector({ isBun, platform: process.platform, env: process.env, exists: existsSync, probe: probeLibrary, select: selectLibrary }); let published = false; return (options) => { const selection = select(options); if (sharedLibrary && isMainThread && !published) { setEnvironmentData(WORKER_SELECTION_KEY, Object.freeze({ ...selection })); published = true; } return selection; }; } /** Select once, before any SQLite open; shared across CLI and bundled SDK module graphs. */ function ensureSqliteLibrarySelected(options) { const dependencies = options?.internals; return (dependencies ? dependencies.selector ??= createSelector(dependencies) : resolveGlobalSingleton(Symbol.for("openclaw.bunSqliteLibrarySelection"), createRuntimeSelector))(options); } //#endregion export { ensureSqliteLibrarySelected as t };