{"version":3,"sources":["../node_modules/tsup/assets/esm_shims.js","../src/index.ts","../src/stack-path.ts","../src/dirname.ts","../src/lru-cache.ts","../src/sql-tag-store.ts","../src/transaction.ts","../src/enhance.ts"],"sourcesContent":["// Shim globals in esm bundle\nimport path from 'node:path'\nimport { fileURLToPath } from 'node:url'\n\nconst getFilename = () => fileURLToPath(import.meta.url)\nconst getDirname = () => path.dirname(getFilename())\n\nexport const __dirname = /* @__PURE__ */ getDirname()\nexport const __filename = /* @__PURE__ */ getFilename()\n","// Load the native binding with support for both CJS and ESM\nimport nodeGypBuild from \"node-gyp-build\";\nimport { join } from \"node:path\";\nimport { _dirname } from \"./dirname\";\nimport { SQLTagStore } from \"./sql-tag-store\";\nimport {\n  DatabaseSyncInstance,\n  DatabaseSyncLimits,\n} from \"./types/database-sync-instance\";\nimport { DatabaseSyncOptions } from \"./types/database-sync-options\";\nimport { SQLTagStoreInstance } from \"./types/sql-tag-store-instance\";\nimport { SqliteAuthorizationActions } from \"./types/sqlite-authorization-actions\";\nimport { SqliteAuthorizationResults } from \"./types/sqlite-authorization-results\";\nimport { SqliteChangesetConflictTypes } from \"./types/sqlite-changeset-conflict-types\";\nimport { SqliteChangesetResolution } from \"./types/sqlite-changeset-resolution\";\nimport { SqliteOpenFlags } from \"./types/sqlite-open-flags\";\nimport { StatementSyncInstance } from \"./types/statement-sync-instance\";\n\nexport type { AggregateOptions } from \"./types/aggregate-options\";\nexport type { ChangesetApplyOptions } from \"./types/changeset-apply-options\";\nexport type {\n  DatabaseSyncInstance,\n  DatabaseSyncLimits,\n} from \"./types/database-sync-instance\";\nexport type { DatabaseSyncOptions } from \"./types/database-sync-options\";\nexport type { PragmaOptions } from \"./types/pragma-options\";\nexport type { SessionOptions } from \"./types/session-options\";\nexport type { SQLTagStoreInstance } from \"./types/sql-tag-store-instance\";\nexport type { SqliteAuthorizationActions } from \"./types/sqlite-authorization-actions\";\nexport type { SqliteAuthorizationResults } from \"./types/sqlite-authorization-results\";\nexport type { SqliteChangesetConflictTypes } from \"./types/sqlite-changeset-conflict-types\";\nexport type { SqliteChangesetResolution } from \"./types/sqlite-changeset-resolution\";\nexport type { SqliteOpenFlags } from \"./types/sqlite-open-flags\";\nexport type {\n  StatementColumnMetadata,\n  StatementSyncInstance,\n} from \"./types/statement-sync-instance\";\nexport type { TransactionFunction, TransactionMode } from \"./types/transaction\";\nexport type { UserFunctionOptions } from \"./types/user-functions-options\";\n\n// Enhancement utilities for adding better-sqlite3-style methods to any compatible database\nexport {\n  enhance,\n  isEnhanced,\n  type EnhanceableDatabaseSync,\n  type EnhancedDatabaseSync,\n  type EnhancedMethods,\n  type EnhancedStatementMethods,\n} from \"./enhance\";\n\n// Use _dirname() helper that works in both CJS/ESM and Jest\nconst binding = nodeGypBuild(join(_dirname(), \"..\"));\n\n/**\n * All SQLite constants exported by this module.\n *\n * This is a union of all constant category interfaces:\n * - {@link SqliteOpenFlags} - Database open flags (extension beyond `node:sqlite`)\n * - {@link SqliteChangesetResolution} - Changeset conflict resolution values\n * - {@link SqliteChangesetConflictTypes} - Changeset conflict type codes\n * - {@link SqliteAuthorizationResults} - Authorization return values\n * - {@link SqliteAuthorizationActions} - Authorization action codes\n *\n * **Note:** The categorized interfaces (`SqliteOpenFlags`, etc.) are extensions\n * provided by `@photostructure/sqlite`. The `node:sqlite` module exports only\n * a flat `constants` object without these type categories.\n */\nexport type SqliteConstants = SqliteOpenFlags &\n  SqliteChangesetResolution &\n  SqliteChangesetConflictTypes &\n  SqliteAuthorizationResults &\n  SqliteAuthorizationActions;\n\n/**\n * Options for creating a prepared statement.\n *\n * **Note:** The per-statement override options (`readBigInts`, `returnArrays`,\n * `allowBareNamedParameters`, `allowUnknownNamedParameters`) are a **Node.js v25+**\n * feature. On Node.js v24 and earlier, `node:sqlite` silently ignores these options.\n * This library implements them for forward compatibility with Node.js v25+.\n */\nexport interface StatementOptions {\n  /** If true, the prepared statement's expandedSQL property will contain the expanded SQL. @default false */\n  readonly expandedSQL?: boolean;\n  /** If true, anonymous parameters are enabled for the statement. @default false */\n  readonly anonymousParameters?: boolean;\n  /**\n   * If true, read integer values as JavaScript BigInt. Overrides database-level setting.\n   * **Node.js v25+ feature** - silently ignored by `node:sqlite` on v24 and earlier.\n   * @default database default\n   */\n  readonly readBigInts?: boolean;\n  /**\n   * If true, return results as arrays rather than objects. Overrides database-level setting.\n   * **Node.js v25+ feature** - silently ignored by `node:sqlite` on v24 and earlier.\n   * @default database default\n   */\n  readonly returnArrays?: boolean;\n  /**\n   * If true, allows bare named parameters (without prefix). Overrides database-level setting.\n   * **Node.js v25+ feature** - silently ignored by `node:sqlite` on v24 and earlier.\n   * @default database default\n   */\n  readonly allowBareNamedParameters?: boolean;\n  /**\n   * If true, unknown named parameters are ignored. Overrides database-level setting.\n   * **Node.js v25+ feature** - silently ignored by `node:sqlite` on v24 and earlier.\n   * @default database default\n   */\n  readonly allowUnknownNamedParameters?: boolean;\n}\n\nexport interface Session {\n  /**\n   * Generate a changeset containing all changes recorded by the session.\n   * @returns A Uint8Array containing the changeset data.\n   */\n  changeset(): Uint8Array;\n  /**\n   * Generate a patchset containing all changes recorded by the session.\n   * @returns A Uint8Array containing the patchset data.\n   */\n  patchset(): Uint8Array;\n  /**\n   * Close the session and release its resources.\n   */\n  close(): void;\n}\n\n/**\n * The main SQLite module interface.\n */\nexport interface SqliteModule {\n  /**\n   * The DatabaseSync class represents a synchronous connection to a SQLite database.\n   * All operations are performed synchronously, blocking until completion.\n   */\n  DatabaseSync: new (\n    location?: string | Buffer | URL,\n    options?: DatabaseSyncOptions,\n  ) => DatabaseSyncInstance;\n  /**\n   * The StatementSync class represents a synchronous prepared statement.\n   * This class should not be instantiated directly; use Database.prepare() instead.\n   */\n  StatementSync: new (\n    database: DatabaseSyncInstance,\n    sql: string,\n    options?: StatementOptions,\n  ) => StatementSyncInstance;\n  /**\n   * The Session class for recording database changes.\n   * This class should not be instantiated directly; use Database.createSession() instead.\n   */\n  Session: new () => Session;\n  /**\n   * SQLite constants for various operations and flags.\n   * @see {@link SqliteConstants} for the type definition\n   * @see {@link SqliteOpenFlags} for database open flags (extension beyond `node:sqlite`)\n   * @see {@link SqliteChangesetResolution} for changeset conflict resolution values\n   * @see {@link SqliteChangesetConflictTypes} for changeset conflict type codes\n   * @see {@link SqliteAuthorizationResults} for authorization return values\n   * @see {@link SqliteAuthorizationActions} for authorization action codes\n   */\n  constants: SqliteConstants;\n}\n\n/**\n * The DatabaseSync class represents a synchronous connection to a SQLite database.\n * All database operations are performed synchronously, blocking the thread until completion.\n *\n * @example\n * ```typescript\n * import { DatabaseSync } from '@photostructure/sqlite';\n *\n * // Create an in-memory database\n * const db = new DatabaseSync(':memory:');\n *\n * // Create a file-based database\n * const fileDb = new DatabaseSync('./mydata.db');\n *\n * // Create with options\n * const readOnlyDb = new DatabaseSync('./data.db', { readOnly: true });\n * ```\n */\n// Store the native binding's DatabaseSync\nconst _DatabaseSync = binding.DatabaseSync;\n// Wrapper around the native constructor to enforce usage of `new` with the correct error code.\n// We use a function wrapper instead of a Proxy for better performance and explicit prototype handling.\nexport const DatabaseSync = function DatabaseSync(this: any, ...args: any[]) {\n  if (!new.target) {\n    const err = new TypeError(\"Cannot call constructor without `new`\");\n    (err as NodeJS.ErrnoException).code = \"ERR_CONSTRUCT_CALL_REQUIRED\";\n    throw err;\n  }\n  return Reflect.construct(_DatabaseSync, args, new.target);\n} as unknown as SqliteModule[\"DatabaseSync\"];\nObject.setPrototypeOf(DatabaseSync, _DatabaseSync);\nDatabaseSync.prototype = _DatabaseSync.prototype;\n\n// node:sqlite implements createTagStore and SQLTagStore entirely in native C++.\n// We use a TypeScript implementation instead, attached via prototype extension.\n// This maintains API compatibility with node:sqlite while avoiding the complexity\n// of a native LRU cache. Performance is equivalent since the real cost is SQLite\n// execution, not cache lookups - V8's Map is highly optimized for string keys.\n(DatabaseSync.prototype as DatabaseSyncInstance).createTagStore = function (\n  this: DatabaseSyncInstance,\n  capacity?: number,\n): SQLTagStoreInstance {\n  return new SQLTagStore(this, capacity);\n};\n\n// Limit name to SQLite limit ID mapping (matches upstream kLimitMapping order)\nconst LIMIT_MAPPING: ReadonlyArray<{\n  name: keyof DatabaseSyncLimits;\n  id: number;\n}> = [\n  { name: \"length\", id: 0 },\n  { name: \"sqlLength\", id: 1 },\n  { name: \"column\", id: 2 },\n  { name: \"exprDepth\", id: 3 },\n  { name: \"compoundSelect\", id: 4 },\n  { name: \"vdbeOp\", id: 5 },\n  { name: \"functionArg\", id: 6 },\n  { name: \"attach\", id: 7 },\n  { name: \"likePatternLength\", id: 8 },\n  { name: \"variableNumber\", id: 9 },\n  { name: \"triggerDepth\", id: 10 },\n];\n\nconst INT_MAX = 2147483647;\n\n// WeakMap to cache limits objects per database instance\nconst limitsCache = new WeakMap<DatabaseSyncInstance, DatabaseSyncLimits>();\n\nfunction validateLimitValue(value: unknown): number {\n  if (typeof value !== \"number\" || Number.isNaN(value)) {\n    throw new TypeError(\n      \"Limit value must be a non-negative integer or Infinity.\",\n    );\n  }\n  if (value === Infinity) {\n    return INT_MAX;\n  }\n  if (!Number.isFinite(value) || value !== Math.trunc(value)) {\n    throw new TypeError(\n      \"Limit value must be a non-negative integer or Infinity.\",\n    );\n  }\n  if (value < 0) {\n    throw new RangeError(\"Limit value must be non-negative.\");\n  }\n  return value;\n}\n\nfunction createLimitsObject(db: DatabaseSyncInstance): DatabaseSyncLimits {\n  const obj = Object.create(null) as DatabaseSyncLimits;\n  for (const { name, id } of LIMIT_MAPPING) {\n    Object.defineProperty(obj, name, {\n      get() {\n        return db.getLimit(id);\n      },\n      set(value: unknown) {\n        const validated = validateLimitValue(value);\n        db.setLimit(id, validated);\n      },\n      enumerable: true,\n      configurable: false,\n    });\n  }\n  return obj;\n}\n\nif (!Object.getOwnPropertyDescriptor(DatabaseSync.prototype, \"limits\")) {\n  Object.defineProperty(DatabaseSync.prototype, \"limits\", {\n    get(this: DatabaseSyncInstance) {\n      let obj = limitsCache.get(this);\n      if (obj == null) {\n        obj = createLimitsObject(this);\n        limitsCache.set(this, obj);\n      }\n      return obj;\n    },\n    enumerable: true,\n    configurable: true,\n  });\n}\n\n// NOTE: .pragma() and .transaction() are NOT added to the prototype by default.\n// This keeps DatabaseSync 100% API-compatible with node:sqlite.\n// Users who want better-sqlite3-style methods should use enhance():\n//\n//   import { DatabaseSync, enhance } from '@photostructure/sqlite';\n//   const db = enhance(new DatabaseSync(':memory:'));\n//   db.pragma('journal_mode', { simple: true });\n//   db.transaction(() => { ... });\n\n/**\n * The StatementSync class represents a prepared SQL statement.\n * This class should not be instantiated directly; use DatabaseSync.prepare() instead.\n *\n * @example\n * ```typescript\n * const stmt = db.prepare('SELECT * FROM users WHERE id = ?');\n * const user = stmt.get(123);\n * stmt.finalize();\n * ```\n */\n// Store the native binding's StatementSync for internal use\nconst _StatementSync = binding.StatementSync;\n// Export a wrapper that throws ERR_ILLEGAL_CONSTRUCTOR when called directly\n// but preserves instanceof checks and prototype chain\nexport const StatementSync = function StatementSync() {\n  const err = new TypeError(\"Illegal constructor\");\n  (err as NodeJS.ErrnoException).code = \"ERR_ILLEGAL_CONSTRUCTOR\";\n  throw err;\n} as unknown as SqliteModule[\"StatementSync\"];\n// Use the native prototype directly so instanceof checks work correctly\n// (stmt instanceof StatementSync will check if StatementSync.prototype is in stmt's chain)\nStatementSync.prototype = _StatementSync.prototype;\n\n/**\n * The Session class for recording database changes.\n * This class should not be instantiated directly; use DatabaseSync.createSession() instead.\n *\n * @example\n * ```typescript\n * const session = db.createSession({ table: 'users' });\n * // Make some changes to the users table\n * const changeset = session.changeset();\n * session.close();\n * ```\n */\nexport const Session = binding.Session as SqliteModule[\"Session\"];\n\n/**\n * The SQLTagStore class for cached prepared statements via tagged template syntax.\n * This class should not be instantiated directly; use DatabaseSync.createTagStore() instead.\n *\n * @example\n * ```typescript\n * const sql = db.createTagStore();\n * sql.run`INSERT INTO users VALUES (${id}, ${name})`;\n * const user = sql.get`SELECT * FROM users WHERE id = ${id}`;\n * ```\n */\nexport { SQLTagStore };\n\n/**\n * SQLite constants for various operations and flags.\n *\n * @example\n * ```typescript\n * import { constants } from '@photostructure/sqlite';\n *\n * const db = new DatabaseSync('./data.db', {\n *   readOnly: true,\n *   // Uses SQLITE_OPEN_READONLY internally\n * });\n * ```\n */\nexport const constants: SqliteConstants = binding.constants;\n\n/**\n * Options for the backup() function.\n */\nexport interface BackupOptions {\n  /** Number of pages to be transmitted in each batch of the backup. @default 100 */\n  rate?: number;\n  /** Name of the source database. Can be 'main' or any attached database. @default 'main' */\n  source?: string;\n  /** Name of the target database. Can be 'main' or any attached database. @default 'main' */\n  target?: string;\n  /** Callback function that will be called with progress information. */\n  progress?: (info: { totalPages: number; remainingPages: number }) => void;\n}\n\n/**\n * Standalone function to make a backup of a database.\n *\n * This function matches the Node.js `node:sqlite` module API which exports\n * `backup()` as a standalone function in addition to the `db.backup()` method.\n *\n * @param sourceDb The database to backup from.\n * @param destination The path where the backup will be created.\n * @param options Optional configuration for the backup operation.\n * @returns A promise that resolves when the backup is completed.\n *\n * @example\n * ```typescript\n * import { DatabaseSync, backup } from '@photostructure/sqlite';\n *\n * const db = new DatabaseSync('./source.db');\n * await backup(db, './backup.db');\n *\n * // With options\n * await backup(db, './backup.db', {\n *   rate: 10,\n *   progress: ({ totalPages, remainingPages }) => {\n *     console.log(`Progress: ${totalPages - remainingPages}/${totalPages}`);\n *   }\n * });\n * ```\n */\nexport const backup: (\n  sourceDb: DatabaseSyncInstance,\n  destination: string | Buffer | URL,\n  options?: BackupOptions,\n) => Promise<number> = binding.backup;\n\n// Default export for CommonJS compatibility\nexport default binding as SqliteModule;\n","import { dirname } from \"node:path\";\n\nexport function getCallerDirname(): string {\n  const e = new Error();\n  if (e.stack == null) {\n    Error.captureStackTrace(e);\n  }\n  return dirname(extractCallerPath(e.stack as string));\n}\n\n// Comprehensive regex patterns for different stack frame formats\nconst patterns =\n  process.platform === \"win32\"\n    ? [\n        // File URLs: \"at functionName (file:///C:/path/file.js:1:1)\"\n        /\\bat\\s.+?\\((?<path>file:\\/\\/\\/.+?):\\d+:\\d+\\)$/,\n        // File URLs direct: \"at file:///C:/path/file.js:1:1\"\n        /\\bat\\s(?<path>file:\\/\\/\\/.+?):\\d+:\\d+$/,\n        // Standard: \"at functionName (C:\\path\\file.js:1:1)\"\n        /\\bat\\s.+?\\((?<path>[A-Z]:\\\\.+):\\d+:\\d+\\)$/,\n        // direct: \"at C:\\path\\file.js:1:1\"\n        /\\bat\\s(?<path>[A-Z]:\\\\.+):\\d+:\\d+$/,\n        // UNC: \"at functionName (\\\\server\\share\\path\\file.js:1:1)\"\n        /\\bat\\s.+?\\((?<path>\\\\\\\\.+):\\d+:\\d+\\)$/,\n        // direct: \"at \\\\server\\share\\path\\file.js:1:1\"\n        /\\bat\\s(?<path>\\\\\\\\.+):\\d+:\\d+$/,\n      ]\n    : [\n        // Standard: \"at functionName (/path/file.js:1:1)\"\n        /\\bat\\s.+?\\((?<path>\\/.+?):\\d+:\\d+\\)$/,\n        // Anonymous or direct: \"at /path/file.js:1:1\"\n        // eslint-disable-next-line security/detect-unsafe-regex -- Pattern is safe: no nested quantifiers\n        /\\bat\\s(?:[^\\s()]+\\s)?(?<path>\\/[^:]+):\\d+:\\d+$/,\n      ];\n\nconst MaybeUrlRE = /^[a-z]{2,5}:\\/\\//i;\n\n// only exposed for tests:\nexport function extractCallerPath(stack: string): string {\n  const frames = stack.split(\"\\n\").filter(Boolean);\n\n  // First find getCallerDirname() in the stack:\n  const callerFrame = frames.findIndex((frame) =>\n    frame.includes(\"getCallerDirname\"),\n  );\n  if (callerFrame === -1) {\n    throw new Error(\"Invalid stack trace format: missing caller frame\");\n  }\n  for (let i = callerFrame + 1; i < frames.length; i++) {\n    // eslint-disable-next-line security/detect-object-injection -- Index is from controlled for-loop\n    const frame = frames[i];\n    for (const pattern of patterns) {\n      const g = frame?.trim().match(pattern)?.groups;\n      if (g != null && g[\"path\"]) {\n        const path = g[\"path\"];\n        // Windows requires us to check if it's a reasonable URL, as URL accepts\n        // \"C:\\\\path\\\\file.txt\" as valid (!!)\n        if (MaybeUrlRE.test(path)) {\n          try {\n            return new URL(path).pathname;\n          } catch {\n            // ignore\n          }\n        }\n        return path;\n      }\n    }\n  }\n  throw new Error(\"Invalid stack trace format: no parsable frames\");\n}\n","import { getCallerDirname } from \"./stack-path\";\n\n// Thanks to tsup shims, __dirname should always be defined except when run by\n// jest (which will use the stack_path shim)\nexport function _dirname() {\n  try {\n    if (typeof __dirname !== \"undefined\") return __dirname;\n  } catch {\n    // ignore\n  }\n  // we must be in jest. Use the stack_path ~~hack~~ shim:\n  return getCallerDirname();\n}\n","/**\n * Simple LRU (Least Recently Used) cache implementation.\n * Uses Map's insertion order to track recency - first key is oldest.\n */\nexport class LRUCache<K, V> {\n  private cache = new Map<K, V>();\n  private readonly maxCapacity: number;\n\n  constructor(capacity: number) {\n    if (capacity < 1) {\n      throw new RangeError(\"LRU cache capacity must be at least 1\");\n    }\n    this.maxCapacity = capacity;\n  }\n\n  /**\n   * Get a value from the cache.\n   * If found, moves the entry to the end (most recently used).\n   */\n  get(key: K): V | undefined {\n    const value = this.cache.get(key);\n    if (value !== undefined) {\n      // Move to end (most recently used) by reinserting\n      this.cache.delete(key);\n      this.cache.set(key, value);\n    }\n    return value;\n  }\n\n  /**\n   * Set a value in the cache.\n   * If key exists, updates and moves to end.\n   * If at capacity, evicts the oldest entry first.\n   */\n  set(key: K, value: V): void {\n    if (this.cache.has(key)) {\n      // Update existing - delete and reinsert at end\n      this.cache.delete(key);\n    } else if (this.cache.size >= this.maxCapacity) {\n      // Evict oldest (first key in Map iteration order)\n      const oldestKey = this.cache.keys().next().value;\n      if (oldestKey !== undefined) {\n        this.cache.delete(oldestKey);\n      }\n    }\n    this.cache.set(key, value);\n  }\n\n  /**\n   * Delete an entry from the cache.\n   */\n  delete(key: K): boolean {\n    return this.cache.delete(key);\n  }\n\n  /**\n   * Check if a key exists in the cache.\n   * Does NOT update recency.\n   */\n  has(key: K): boolean {\n    return this.cache.has(key);\n  }\n\n  /**\n   * Clear all entries from the cache.\n   */\n  clear(): void {\n    this.cache.clear();\n  }\n\n  /**\n   * Get the current number of entries in the cache.\n   */\n  size(): number {\n    return this.cache.size;\n  }\n\n  /**\n   * Get the maximum capacity of the cache.\n   */\n  capacity(): number {\n    return this.maxCapacity;\n  }\n}\n","import { LRUCache } from \"./lru-cache\";\nimport { DatabaseSyncInstance } from \"./types/database-sync-instance\";\nimport type { StatementSyncInstance } from \"./types/statement-sync-instance\";\n\n/**\n * Default capacity for the statement cache.\n * Matches Node.js SQLTagStore default.\n */\nconst DEFAULT_CAPACITY = 1000;\n\n/**\n * SQLTagStore provides cached prepared statements via tagged template syntax.\n *\n * @example\n * ```js\n * const sql = db.createTagStore();\n * sql.run`INSERT INTO users VALUES (${id}, ${name})`;\n * const user = sql.get`SELECT * FROM users WHERE id = ${id}`;\n * ```\n */\nexport class SQLTagStore {\n  private readonly database: DatabaseSyncInstance;\n  private readonly cache: LRUCache<string, StatementSyncInstance>;\n  private readonly maxCapacity: number;\n\n  constructor(db: DatabaseSyncInstance, capacity: number = DEFAULT_CAPACITY) {\n    if (!db.isOpen) {\n      const err = new Error(\"database is not open\");\n      (err as NodeJS.ErrnoException).code = \"ERR_INVALID_STATE\";\n      throw err;\n    }\n    this.database = db;\n    this.maxCapacity = capacity;\n    this.cache = new LRUCache(capacity);\n  }\n\n  /**\n   * Returns the associated database instance.\n   */\n  get db(): DatabaseSyncInstance {\n    return this.database;\n  }\n\n  /**\n   * Returns the maximum capacity of the statement cache.\n   */\n  get capacity(): number {\n    return this.maxCapacity;\n  }\n\n  /**\n   * Returns the current number of cached statements.\n   */\n  get size(): number {\n    return this.cache.size();\n  }\n\n  /**\n   * Clears all cached statements.\n   */\n  clear(): void {\n    this.cache.clear();\n  }\n\n  /**\n   * Execute an INSERT, UPDATE, DELETE or other statement that doesn't return rows.\n   * Returns an object with `changes` and `lastInsertRowid`.\n   */\n  run(\n    strings: TemplateStringsArray,\n    ...values: unknown[]\n  ): { changes: number; lastInsertRowid: number | bigint } {\n    const stmt = this.getOrPrepare(strings);\n    return stmt.run(...values);\n  }\n\n  /**\n   * Execute a query and return the first row, or undefined if no rows.\n   */\n  get(strings: TemplateStringsArray, ...values: unknown[]): unknown {\n    const stmt = this.getOrPrepare(strings);\n    return stmt.get(...values);\n  }\n\n  /**\n   * Execute a query and return all rows as an array.\n   */\n  all(strings: TemplateStringsArray, ...values: unknown[]): unknown[] {\n    const stmt = this.getOrPrepare(strings);\n    return stmt.all(...values);\n  }\n\n  /**\n   * Execute a query and return an iterator over the rows.\n   */\n  iterate(\n    strings: TemplateStringsArray,\n    ...values: unknown[]\n  ): IterableIterator<unknown> {\n    const stmt = this.getOrPrepare(strings);\n    return stmt.iterate(...values);\n  }\n\n  /**\n   * Get a cached statement or prepare a new one.\n   */\n  private getOrPrepare(strings: TemplateStringsArray): StatementSyncInstance {\n    if (!this.database.isOpen) {\n      throw new Error(\"database is not open\");\n    }\n\n    const sql = this.buildSQL(strings);\n\n    // Check cache\n    const cached = this.cache.get(sql);\n    if (cached) {\n      return cached;\n    }\n\n    // Prepare new statement and cache it\n    const stmt = this.database.prepare(sql);\n    this.cache.set(sql, stmt);\n    return stmt;\n  }\n\n  /**\n   * Build the SQL string by joining template parts with `?` placeholders.\n   */\n  private buildSQL(strings: TemplateStringsArray): string {\n    let sql = strings[0] ?? \"\";\n    for (let i = 1; i < strings.length; i++) {\n      // eslint-disable-next-line security/detect-object-injection -- Index is from controlled for-loop\n      sql += \"?\" + (strings[i] ?? \"\");\n    }\n    return sql;\n  }\n}\n","import type { DatabaseSyncInstance } from \"./types/database-sync-instance\";\nimport type { TransactionFunction, TransactionMode } from \"./types/transaction\";\n\n/**\n * Internal counter for generating unique savepoint names.\n * Using a global counter ensures uniqueness even with deeply nested transactions.\n */\nlet savepointCounter = 0;\n\n/**\n * Creates a transaction-wrapped version of a function.\n *\n * When the returned function is called, it will:\n * 1. Begin a transaction (or create a savepoint if already in a transaction)\n * 2. Execute the wrapped function\n * 3. Commit the transaction (or release the savepoint) on success\n * 4. Rollback the transaction (or rollback to savepoint) on error\n *\n * The wrapped function **must not** return a Promise. SQLite transactions are\n * synchronous, and allowing async operations would leave the transaction open\n * across event loop ticks, which is dangerous and can cause deadlocks.\n *\n * @example\n * ```typescript\n * const db = new DatabaseSync(':memory:');\n * db.exec('CREATE TABLE items (id INTEGER PRIMARY KEY, name TEXT)');\n *\n * const insert = db.prepare('INSERT INTO items (name) VALUES (?)');\n *\n * // Create a transaction function\n * const insertMany = db.transaction((names: string[]) => {\n *   for (const name of names) {\n *     insert.run(name);\n *   }\n *   return names.length;\n * });\n *\n * // Execute - automatically wrapped in BEGIN/COMMIT\n * const count = insertMany(['Alice', 'Bob', 'Charlie']);\n * console.log(count); // 3\n *\n * // If an error occurs, automatically rolls back\n * try {\n *   insertMany(['Dave', 'FAIL']); // Assume this throws\n * } catch (e) {\n *   // Transaction was rolled back, Dave was not inserted\n * }\n *\n * // Use different transaction modes\n * insertMany.immediate(['Eve']); // BEGIN IMMEDIATE\n * insertMany.exclusive(['Frank']); // BEGIN EXCLUSIVE\n * ```\n *\n * @param db - The database connection\n * @param fn - The function to wrap in a transaction\n * @returns A transaction function with `.deferred`, `.immediate`, and `.exclusive` variants\n */\nexport function createTransaction<F extends (...args: any[]) => any>(\n  db: DatabaseSyncInstance,\n  fn: F,\n): TransactionFunction<F> {\n  if (typeof fn !== \"function\") {\n    throw new TypeError(\"Expected first argument to be a function\");\n  }\n\n  // Create all four variants\n  const variants = {\n    deferred: createVariant(db, fn, \"deferred\"),\n    immediate: createVariant(db, fn, \"immediate\"),\n    exclusive: createVariant(db, fn, \"exclusive\"),\n  };\n\n  // The default function uses DEFERRED mode (SQLite's default)\n  const defaultFn = variants.deferred as TransactionFunction<F>;\n\n  // Set up the variant properties on each function\n  // Each variant has access to all other variants\n  for (const variant of Object.values(variants)) {\n    Object.defineProperties(variant, {\n      deferred: { value: variants.deferred, enumerable: true },\n      immediate: { value: variants.immediate, enumerable: true },\n      exclusive: { value: variants.exclusive, enumerable: true },\n      database: { value: db, enumerable: true },\n    });\n  }\n\n  return defaultFn;\n}\n\n/**\n * Creates a single transaction variant for a specific mode.\n */\nfunction createVariant<F extends (...args: any[]) => any>(\n  db: DatabaseSyncInstance,\n  fn: F,\n  mode: TransactionMode,\n): (...args: Parameters<F>) => ReturnType<F> {\n  const beginStatement = getBeginStatement(mode);\n\n  return function transactionWrapper(\n    this: unknown,\n    ...args: Parameters<F>\n  ): ReturnType<F> {\n    // Check if we're already in a transaction (nested transaction)\n    const isNested = db.isTransaction;\n\n    let begin: string;\n    let commit: string;\n    let rollback: string;\n\n    if (isNested) {\n      // Use savepoints for nested transactions\n      // The savepoint name uses backticks to allow special characters\n      // and a counter to ensure uniqueness\n      const savepointName = `\\`_txn_${++savepointCounter}\\``;\n      begin = `SAVEPOINT ${savepointName}`;\n      commit = `RELEASE ${savepointName}`;\n      rollback = `ROLLBACK TO ${savepointName}`;\n    } else {\n      // Top-level transaction\n      begin = beginStatement;\n      commit = \"COMMIT\";\n      rollback = \"ROLLBACK\";\n    }\n\n    // Begin the transaction or savepoint\n    db.exec(begin);\n\n    try {\n      // Execute the wrapped function\n      const result = fn.apply(this, args);\n\n      // Check for promises - async functions break transaction semantics\n      if (result !== null && typeof result === \"object\" && \"then\" in result) {\n        throw new TypeError(\n          \"Transaction function must not return a Promise. \" +\n            \"SQLite transactions are synchronous and cannot span across async operations. \" +\n            \"Use synchronous code within transactions.\",\n        );\n      }\n\n      // Commit the transaction or release the savepoint\n      db.exec(commit);\n\n      return result;\n    } catch (error) {\n      // Only attempt rollback if we're still in a transaction\n      // (SQLite may have already rolled back due to constraint violations, etc.)\n      if (db.isTransaction) {\n        db.exec(rollback);\n        // For nested transactions, we also need to release the savepoint\n        // after rolling back to it (the savepoint still exists after ROLLBACK TO)\n        if (isNested) {\n          db.exec(commit);\n        }\n      }\n\n      throw error;\n    }\n  };\n}\n\n/**\n * Returns the appropriate BEGIN statement for a transaction mode.\n */\nfunction getBeginStatement(mode: TransactionMode): string {\n  switch (mode) {\n    case \"deferred\":\n      return \"BEGIN DEFERRED\";\n    case \"immediate\":\n      return \"BEGIN IMMEDIATE\";\n    case \"exclusive\":\n      return \"BEGIN EXCLUSIVE\";\n    default:\n      // TypeScript should catch this, but just in case\n      throw new Error(`Unknown transaction mode: ${mode}`);\n  }\n}\n","/**\n * Enhancement utilities for adding better-sqlite3-style methods to any\n * compatible database, including `node:sqlite` DatabaseSync and this package's\n * DatabaseSync.\n *\n * This module provides the `enhance()` function which adds `.pragma()`,\n * `.transaction()`, and statement modes (`.pluck()`, `.raw()`, `.expand()`)\n * to database instances that don't have them (e.g., node:sqlite DatabaseSync).\n */\n\nimport { createTransaction } from \"./transaction\";\nimport type { PragmaOptions } from \"./types/pragma-options\";\nimport type { TransactionFunction } from \"./types/transaction\";\n\n/**\n * Minimal interface for a database that can be enhanced. This matches the\n * subset of functionality needed by pragma() and transaction().\n */\nexport interface EnhanceableDatabaseSync {\n  /** Execute SQL without returning results */\n  exec(sql: string): void;\n  /** Prepare a statement that can return results */\n  prepare(sql: string): { all(): unknown[] };\n  /** Whether the database connection is open */\n  readonly isOpen?: boolean;\n  /** Whether a transaction is currently active */\n  readonly isTransaction: boolean;\n}\n\n/**\n * Statement mode matching better-sqlite3's mutually exclusive modes.\n * - \"flat\": Default — rows as `{ column: value }` objects\n * - \"pluck\": First column value only\n * - \"raw\": Rows as arrays of values\n * - \"expand\": Rows namespaced by table, e.g. `{ users: { id: 1 }, posts: { title: \"...\" } }`\n */\ntype StatementMode = \"flat\" | \"pluck\" | \"raw\" | \"expand\";\n\n/**\n * A statement enhanced with better-sqlite3-style `.pluck()`, `.raw()`, and\n * `.expand()` methods. These are mutually exclusive — enabling one disables\n * the others.\n */\nexport interface EnhancedStatementMethods {\n  /**\n   * Causes the statement to return only the first column value of each row.\n   *\n   * When plucking is turned on, raw and expand modes are turned off.\n   *\n   * @param toggle Enable (true) or disable (false) pluck mode. Defaults to true.\n   * @returns The same statement for chaining.\n   *\n   * @example\n   * ```typescript\n   * const count = db.prepare(\"SELECT COUNT(*) FROM users\").pluck().get();\n   * // Returns: 42 (not { \"COUNT(*)\": 42 })\n   *\n   * const names = db.prepare(\"SELECT name FROM users\").pluck().all();\n   * // Returns: [\"Alice\", \"Bob\"] (not [{ name: \"Alice\" }, { name: \"Bob\" }])\n   * ```\n   */\n  pluck(toggle?: boolean): this;\n\n  /**\n   * Causes the statement to return rows as arrays of values instead of objects.\n   *\n   * When raw mode is turned on, pluck and expand modes are turned off.\n   *\n   * @param toggle Enable (true) or disable (false) raw mode. Defaults to true.\n   * @returns The same statement for chaining.\n   *\n   * @example\n   * ```typescript\n   * const rows = db.prepare(\"SELECT id, name FROM users\").raw().all();\n   * // Returns: [[1, \"Alice\"], [2, \"Bob\"]] (not [{ id: 1, name: \"Alice\" }, ...])\n   * ```\n   */\n  raw(toggle?: boolean): this;\n\n  /**\n   * Causes the statement to return data namespaced by table. Each key in a row\n   * object will be a table name, and each corresponding value will be a nested\n   * object containing that table's columns. Columns from expressions or\n   * subqueries are placed under the special `$` namespace.\n   *\n   * When expand mode is turned on, pluck and raw modes are turned off.\n   *\n   * Requires the statement to have a `.columns()` method (available on real\n   * statements but not minimal mocks).\n   *\n   * @param toggle Enable (true) or disable (false) expand mode. Defaults to true.\n   * @returns The same statement for chaining.\n   *\n   * @example\n   * ```typescript\n   * const rows = db.prepare(\"SELECT u.id, u.name, p.title FROM users u JOIN posts p ON ...\").expand().all();\n   * // Returns: [{ users: { id: 1, name: \"Alice\" }, posts: { title: \"Hello\" } }]\n   * ```\n   */\n  expand(toggle?: boolean): this;\n\n  /** The database instance this statement was prepared from. */\n  readonly database: EnhanceableDatabaseSync;\n}\n\n/**\n * Interface for an enhanced database with pragma() and transaction() methods.\n */\nexport interface EnhancedMethods {\n  /**\n   * Executes a PRAGMA statement and returns its result.\n   *\n   * @param source The PRAGMA command (without \"PRAGMA\" prefix)\n   * @param options Optional configuration\n   * @returns Array of rows, or single value if `simple: true`\n   *\n   * @example\n   * ```typescript\n   * db.pragma('cache_size', { simple: true }); // -16000\n   * db.pragma('journal_mode = wal');\n   * ```\n   */\n  pragma(source: string, options?: PragmaOptions): unknown;\n\n  /**\n   * Creates a function that always runs inside a transaction.\n   *\n   * @param fn The function to wrap in a transaction\n   * @returns A transaction function with `.deferred`, `.immediate`,\n   * `.exclusive` variants\n   *\n   * @example\n   * ```typescript\n   * const insertMany = db.transaction((items) => {\n   *   for (const item of items) insert.run(item);\n   * });\n   * insertMany(['a', 'b', 'c']); // All in one transaction\n   * ```\n   */\n  transaction<F extends (...args: any[]) => any>(fn: F): TransactionFunction<F>;\n}\n\n/**\n * A database instance that has been enhanced with pragma(), transaction(),\n * and statement modes (pluck/raw/expand) on statements returned by prepare().\n */\nexport type EnhancedDatabaseSync<T extends EnhanceableDatabaseSync> = Omit<\n  T,\n  \"prepare\"\n> &\n  EnhancedMethods & {\n    prepare(\n      ...args: Parameters<T[\"prepare\"]>\n    ): ReturnType<T[\"prepare\"]> & EnhancedStatementMethods;\n  };\n\n/** Symbol to track whether prepare() has been wrapped */\nconst ENHANCED_PREPARE = Symbol.for(\"@photostructure/sqlite:enhancedPrepare\");\n\n/**\n * Extract the first column value from a row object or array.\n */\nfunction extractFirstColumn(row: unknown): unknown {\n  if (row == null) return row;\n  if (Array.isArray(row)) return row[0];\n  const keys = Object.keys(row as Record<string, unknown>);\n  return keys.length > 0\n    ? (row as Record<string, unknown>)[keys[0]!]\n    : undefined;\n}\n\n/**\n * Build a column-to-table mapping from statement metadata, used by expand mode.\n * Returns an array parallel to column order: each entry is the table name\n * (or \"$\" for expressions/subqueries) and the column name.\n */\nfunction buildColumnTableMap(\n  stmt: any,\n): Array<{ table: string; column: string }> | undefined {\n  if (typeof stmt.columns !== \"function\") return undefined;\n  const cols: Array<{ name: string; table: string | null }> = stmt.columns();\n  return cols.map((c) => ({\n    table: c.table ?? \"$\",\n    column: c.name,\n  }));\n}\n\n/**\n * Transform a row array into a table-namespaced expanded object.\n * Uses array indices to match columns, avoiding data loss from duplicate names.\n */\nfunction expandRowFromArray(\n  row: unknown[],\n  columnMap: Array<{ table: string; column: string }>,\n): Record<string, Record<string, unknown>> {\n  const result: Record<string, Record<string, unknown>> = {};\n  for (let i = 0; i < columnMap.length && i < row.length; i++) {\n    const { table, column } = columnMap[i]!; // eslint-disable-line security/detect-object-injection\n    // eslint-disable-next-line security/detect-object-injection -- table/column from our own columnMap\n    result[table] ??= {};\n    result[table]![column] = row[i]; // eslint-disable-line security/detect-object-injection\n  }\n  return result;\n}\n\n/**\n * Transform a flat row object into a table-namespaced expanded object.\n * Fallback for mocks without setReturnArrays — cannot handle duplicate column\n * names correctly, but mocks typically don't produce them.\n */\nfunction expandRowFromObject(\n  row: Record<string, unknown>,\n  columnMap: Array<{ table: string; column: string }>,\n): Record<string, Record<string, unknown>> {\n  const result: Record<string, Record<string, unknown>> = {};\n  const keys = Object.keys(row);\n  for (let i = 0; i < keys.length && i < columnMap.length; i++) {\n    const { table, column } = columnMap[i]!; // eslint-disable-line security/detect-object-injection\n    // eslint-disable-next-line security/detect-object-injection -- table/column from our own columnMap\n    result[table] ??= {};\n    result[table]![column] = row[keys[i]!]; // eslint-disable-line security/detect-object-injection\n  }\n  return result;\n}\n\n/**\n * Validate a boolean toggle argument, matching better-sqlite3's pattern.\n */\nfunction validateToggle(value: unknown): boolean {\n  const use = value === undefined ? true : value;\n  if (typeof use !== \"boolean\") {\n    throw new TypeError(\"Expected first argument to be a boolean\");\n  }\n  return use;\n}\n\n/**\n * Transform a row based on the current statement mode.\n */\nfunction transformRow(\n  row: unknown,\n  mode: StatementMode,\n  columnMap: Array<{ table: string; column: string }> | undefined,\n): unknown {\n  if (row == null || mode === \"flat\") return row;\n  if (mode === \"pluck\") return extractFirstColumn(row);\n  if (mode === \"expand\") {\n    // columnMap is guaranteed non-null here — setMode() throws if columns() is\n    // unavailable, so we'll never reach this branch with columnMap == null.\n    // Prefer array-based expand (used when setReturnArrays is available)\n    // to correctly handle duplicate column names across tables.\n    // Fall back to object-based expand for mocks without setReturnArrays.\n    if (Array.isArray(row)) {\n      return expandRowFromArray(row, columnMap!);\n    }\n    return expandRowFromObject(row as Record<string, unknown>, columnMap!);\n  }\n  // \"raw\" mode is handled natively by setReturnArrays(), so no transform needed\n  return row;\n}\n\n/**\n * Add `.pluck()`, `.raw()`, and `.expand()` methods to a statement instance.\n * These modes are mutually exclusive — enabling one disables the others,\n * matching better-sqlite3's behavior.\n */\nfunction enhanceStatement<S extends { all(): unknown[] }>(\n  stmt: S,\n): S & EnhancedStatementMethods {\n  // Idempotency: if already enhanced, return as-is\n  if (typeof (stmt as any).pluck === \"function\") {\n    return stmt as S & EnhancedStatementMethods;\n  }\n\n  let mode: StatementMode = \"flat\";\n  let columnMap: Array<{ table: string; column: string }> | undefined;\n\n  // Cast to any to avoid TypeScript strictness around bound method signatures.\n  // At runtime these are native C++ methods that accept variadic bind parameters.\n  const originalGet: any =\n    typeof (stmt as any).get === \"function\"\n      ? (stmt as any).get.bind(stmt)\n      : undefined;\n  const originalAll: any = (stmt as any).all.bind(stmt);\n  const originalIterate: any =\n    typeof (stmt as any).iterate === \"function\"\n      ? (stmt as any).iterate.bind(stmt)\n      : undefined;\n\n  // Toggle helper matching better-sqlite3's mode switching:\n  // enable(true) sets to target mode; enable(false) resets to flat ONLY if\n  // currently in that mode, otherwise leaves mode unchanged.\n  function setMode(target: StatementMode, use: boolean): void {\n    if (use) {\n      mode = target;\n      // Cache column map on first expand() call\n      if (target === \"expand\" && columnMap == null) {\n        columnMap = buildColumnTableMap(stmt);\n        if (columnMap == null) {\n          throw new TypeError(\n            \"expand() requires the statement to have a columns() method\",\n          );\n        }\n      }\n    } else if (mode === target) {\n      mode = \"flat\";\n    }\n    // If use=false and mode !== target, no-op (matches better-sqlite3)\n\n    // Sync native array mode: both raw and expand need arrays from the native layer.\n    // Expand needs arrays to correctly handle duplicate column names across tables.\n    if (typeof (stmt as any).setReturnArrays === \"function\") {\n      (stmt as any).setReturnArrays(mode === \"raw\" || mode === \"expand\");\n    }\n  }\n\n  Object.defineProperty(stmt, \"pluck\", {\n    value: function pluck(toggle?: boolean): S {\n      setMode(\"pluck\", validateToggle(toggle));\n      return stmt;\n    },\n    writable: true,\n    configurable: true,\n    enumerable: false,\n  });\n\n  Object.defineProperty(stmt, \"raw\", {\n    value: function raw(toggle?: boolean): S {\n      setMode(\"raw\", validateToggle(toggle));\n      return stmt;\n    },\n    writable: true,\n    configurable: true,\n    enumerable: false,\n  });\n\n  Object.defineProperty(stmt, \"expand\", {\n    value: function expand(toggle?: boolean): S {\n      setMode(\"expand\", validateToggle(toggle));\n      return stmt;\n    },\n    writable: true,\n    configurable: true,\n    enumerable: false,\n  });\n\n  if (originalGet != null) {\n    Object.defineProperty(stmt, \"get\", {\n      value: (...params: any[]) => {\n        const row = originalGet(...params);\n        return transformRow(row, mode, columnMap);\n      },\n      writable: true,\n      configurable: true,\n      enumerable: false,\n    });\n  }\n\n  Object.defineProperty(stmt, \"all\", {\n    value: (...params: any[]) => {\n      const rows = originalAll(...params);\n      if (mode === \"flat\" || mode === \"raw\") return rows;\n      return rows.map((row: unknown) => transformRow(row, mode, columnMap));\n    },\n    writable: true,\n    configurable: true,\n    enumerable: false,\n  });\n\n  if (originalIterate != null) {\n    Object.defineProperty(stmt, \"iterate\", {\n      value: function* (...params: any[]) {\n        const iter = originalIterate(...params);\n        for (const row of iter) {\n          yield transformRow(row, mode, columnMap);\n        }\n      },\n      writable: true,\n      configurable: true,\n      enumerable: false,\n    });\n  }\n\n  return stmt as S & EnhancedStatementMethods;\n}\n\n/**\n * Implementation of pragma() that works on any EnhanceableDatabaseSync.\n */\nfunction pragmaImpl(\n  this: EnhanceableDatabaseSync,\n  source: string,\n  options?: PragmaOptions,\n): unknown {\n  if (typeof source !== \"string\") {\n    throw new TypeError(\"Expected first argument to be a string\");\n  }\n  if (options != null && typeof options !== \"object\") {\n    throw new TypeError(\"Expected second argument to be an options object\");\n  }\n\n  const simple = options?.simple === true;\n\n  // Validate that simple is a boolean if provided\n  if (\n    options != null &&\n    \"simple\" in options &&\n    typeof options.simple !== \"boolean\"\n  ) {\n    throw new TypeError('Expected the \"simple\" option to be a boolean');\n  }\n\n  const stmt = this.prepare(`PRAGMA ${source}`);\n\n  if (simple) {\n    return extractFirstColumn(stmt.all()[0]);\n  }\n\n  return stmt.all();\n}\n\n/**\n * Implementation of transaction() that works on any EnhanceableDatabaseSync.\n */\nfunction transactionImpl<F extends (...args: any[]) => any>(\n  this: EnhanceableDatabaseSync,\n  fn: F,\n): TransactionFunction<F> {\n  // createTransaction expects DatabaseSyncInstance but only uses the subset\n  // defined in EnhanceableDatabaseSync, so this cast is safe\n  return createTransaction(this as any, fn);\n}\n\n/**\n * Checks if a database instance already has the enhanced methods.\n */\nfunction hasEnhancedMethods(\n  db: EnhanceableDatabaseSync,\n): db is EnhanceableDatabaseSync & EnhancedMethods {\n  return (\n    typeof (db as any).pragma === \"function\" &&\n    typeof (db as any).transaction === \"function\"\n  );\n}\n\n/**\n * Ensures that `.pragma()`, `.transaction()`, and statement modes\n * (`.pluck()`, `.raw()`, `.expand()`) are available on the given database.\n *\n * This function can enhance:\n * - `node:sqlite` DatabaseSync instances (adds the methods)\n * - `@photostructure/sqlite` DatabaseSync instances (adds the methods)\n * - Any object with compatible `exec()`, `prepare()`, and `isTransaction`\n *\n * The enhancement is done by adding methods directly to the instance, not the\n * prototype, so it won't affect other instances or the original class.\n *\n * @param db The database instance to enhance\n * @returns The same instance with `.pragma()`, `.transaction()`, and\n * `.pluck()` / `.raw()` / `.expand()` (on prepared statements) guaranteed\n *\n * @example\n * ```typescript\n * import { DatabaseSync, enhance } from '@photostructure/sqlite';\n *\n * const db = enhance(new DatabaseSync(':memory:'));\n *\n * // better-sqlite3-style pragma\n * db.pragma('journal_mode = wal');\n *\n * // better-sqlite3-style transactions\n * const insertMany = db.transaction((items) => {\n *   for (const item of items) insert.run(item);\n * });\n *\n * // better-sqlite3-style pluck\n * const count = db.prepare(\"SELECT COUNT(*) FROM users\").pluck().get();\n * const names = db.prepare(\"SELECT name FROM users\").pluck().all();\n * ```\n */\nexport function enhance<T extends EnhanceableDatabaseSync>(\n  db: T,\n): EnhancedDatabaseSync<T> {\n  // Add pragma and transaction if not already present\n  if (!hasEnhancedMethods(db)) {\n    // Using Object.defineProperty to make them non-enumerable like native methods\n    Object.defineProperty(db, \"pragma\", {\n      value: pragmaImpl,\n      writable: true,\n      configurable: true,\n      enumerable: false,\n    });\n\n    Object.defineProperty(db, \"transaction\", {\n      value: transactionImpl,\n      writable: true,\n      configurable: true,\n      enumerable: false,\n    });\n  }\n\n  // Wrap prepare() to add pluck() to returned statements\n  // eslint-disable-next-line security/detect-object-injection -- ENHANCED_PREPARE is a Symbol\n  if (!(db as any)[ENHANCED_PREPARE]) {\n    const originalPrepare: any = db.prepare.bind(db);\n\n    Object.defineProperty(db, \"prepare\", {\n      value: (...args: any[]) => {\n        const stmt = originalPrepare(...args);\n        enhanceStatement(stmt);\n        // Add stmt.database back-reference for better-sqlite3 compat\n        Object.defineProperty(stmt, \"database\", {\n          value: db,\n          writable: false,\n          configurable: true,\n          enumerable: false,\n        });\n        return stmt;\n      },\n      writable: true,\n      configurable: true,\n      enumerable: false,\n    });\n\n    Object.defineProperty(db, ENHANCED_PREPARE, {\n      value: true,\n      writable: false,\n      configurable: false,\n      enumerable: false,\n    });\n  }\n\n  return db as unknown as EnhancedDatabaseSync<T>;\n}\n\n/**\n * Type guard to check if a database has enhanced methods.\n *\n * @param db The database to check\n * @returns True if the database has `.pragma()` and `.transaction()` methods\n *\n * @example\n * ```typescript\n * import { isEnhanced } from '@photostructure/sqlite';\n *\n * if (isEnhanced(db)) {\n *   db.pragma('cache_size', { simple: true });\n * }\n * ```\n */\nexport function isEnhanced(\n  db: EnhanceableDatabaseSync,\n): db is EnhanceableDatabaseSync & EnhancedMethods {\n  return hasEnhancedMethods(db);\n}\n"],"mappings":"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","names":["path","DatabaseSync","StatementSync"]}