{"version":3,"file":"indexed-db-wrapper.cjs","sources":["../../src/indexed-db-wrapper.ts"],"sourcesContent":["import { codedMessage, devBuild } from './error-message'\n/**\n * IndexedDB Database Wrapper\n *\n * This module provides promise-based utilities for working with IndexedDB.\n * All functions return promises and wrap IndexedDB errors with descriptive messages.\n */\n\n/**\n * Gets the IndexedDB factory, with cross-environment support.\n * @param idbFactory - Optional custom IDBFactory for testing\n * @returns The IDBFactory to use\n * @throws Error if IndexedDB is not available\n */\nfunction getIDBFactory(idbFactory?: IDBFactory): IDBFactory {\n  if (idbFactory) {\n    return idbFactory\n  }\n\n  // Try window.indexedDB first (browser environment)\n  // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition -- runtime check needed\n  if (typeof window !== 'undefined' && window.indexedDB) {\n    return window.indexedDB\n  }\n\n  // Try globalThis.indexedDB (modern environments, including Node.js with polyfill)\n  // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition -- runtime check needed\n  if (typeof globalThis !== 'undefined' && globalThis.indexedDB) {\n    return globalThis.indexedDB\n  }\n\n  throw new Error(\n    devBuild() && process.env.NODE_ENV !== `production`\n      ? 'IndexedDB is not available in this environment. ' +\n          'Ensure you are running in a browser or provide a custom IDBFactory for testing.'\n      : codedMessage(179),\n  )\n}\n\nfunction executeRequest<T>(\n  createRequest: () => IDBRequest<T>,\n  /** The whole message, given the native failure's text. */\n  describeFailure: (cause: string) => string,\n): Promise<T> {\n  return new Promise((resolve, reject) => {\n    let request: IDBRequest<T>\n    try {\n      request = createRequest()\n    } catch (error) {\n      reject(\n        new Error(\n          describeFailure(\n            error instanceof Error ? error.message : String(error),\n          ),\n          { cause: error },\n        ),\n      )\n      return\n    }\n    request.onsuccess = () => resolve(request.result)\n    request.onerror = () => {\n      const errorMessage = request.error?.message || 'Unknown error'\n      reject(\n        new Error(describeFailure(errorMessage), {\n          cause: request.error,\n        }),\n      )\n    }\n  })\n}\n\n/**\n * Opens an IndexedDB database with the specified name and version.\n * A blocked request stays pending until native success or error. The caller\n * owns the returned connection and must close it when no longer needed.\n *\n * @param name - The name of the database to open\n * @param version - The version number of the database schema\n * @param onUpgrade - Optional callback that runs during the onupgradeneeded event.\n *                    Use this to create object stores and indexes.\n * @param idbFactory - Optional IDBFactory for testing/mocking (defaults to window.indexedDB or globalThis.indexedDB)\n * @param onBlocked - Optional diagnostic callback for native blocked events. The request stays pending.\n * @returns A promise that resolves to the IDBDatabase instance\n *\n * @example\n * ```typescript\n * const db = await openDatabase('myApp', 1, (db, oldVersion, newVersion, transaction) => {\n *   if (oldVersion < 1) {\n *     db.createObjectStore('todos', { keyPath: 'id' })\n *   }\n * })\n * ```\n */\nexport function openDatabase(\n  name: string,\n  version: number,\n  onUpgrade?: (\n    db: IDBDatabase,\n    oldVersion: number,\n    newVersion: number,\n    transaction: IDBTransaction,\n  ) => void,\n  idbFactory?: IDBFactory,\n  onBlocked?: (event: IDBVersionChangeEvent) => void,\n): Promise<IDBDatabase> {\n  return new Promise((resolve, reject) => {\n    const factory = getIDBFactory(idbFactory)\n\n    let request: IDBOpenDBRequest\n    try {\n      request = factory.open(name, version)\n    } catch (error) {\n      reject(\n        new Error(\n          devBuild() && process.env.NODE_ENV !== `production`\n            ? `Failed to open IndexedDB database \"${name}\": ${error instanceof Error ? error.message : String(error)}`\n            : codedMessage(182, { name, error }),\n          { cause: error },\n        ),\n      )\n      return\n    }\n\n    request.onupgradeneeded = (event) => {\n      const db = request.result\n      const transaction = request.transaction\n      if (onUpgrade && transaction) {\n        try {\n          onUpgrade(\n            db,\n            event.oldVersion,\n            event.newVersion ?? version,\n            transaction,\n          )\n        } catch (error) {\n          // If the upgrade callback throws, abort the transaction\n          transaction.abort()\n          reject(\n            new Error(\n              devBuild() && process.env.NODE_ENV !== `production`\n                ? `Database upgrade failed for \"${name}\": ${error instanceof Error ? error.message : String(error)}`\n                : codedMessage(183, { name, error }),\n              { cause: error },\n            ),\n          )\n        }\n      }\n    }\n\n    if (onBlocked) request.addEventListener('blocked', onBlocked)\n\n    request.onsuccess = () => {\n      resolve(request.result)\n    }\n\n    request.onerror = () => {\n      const errorMessage = request.error?.message || 'Unknown error'\n      reject(\n        new Error(\n          devBuild() && process.env.NODE_ENV !== `production`\n            ? `Failed to open IndexedDB database \"${name}\": ${errorMessage}`\n            : codedMessage(184, { name, errorMessage }),\n          { cause: request.error },\n        ),\n      )\n    }\n  })\n}\n\n/**\n * Creates an object store during a database upgrade.\n *\n * This function must be called within an onupgradeneeded callback\n * (i.e., within a versionchange transaction). Calling it outside of\n * an upgrade context will throw an error.\n *\n * @param db - The IDBDatabase instance\n * @param storeName - The name of the object store to create\n * @param options - Optional configuration for the object store (keyPath, autoIncrement)\n * @returns The created IDBObjectStore\n * @throws Error if not called during a version change transaction\n *\n * @example\n * ```typescript\n * const db = await openDatabase('myApp', 1, (db) => {\n *   createObjectStore(db, 'todos', { keyPath: 'id' })\n *   createObjectStore(db, 'users', { keyPath: 'id', autoIncrement: true })\n * })\n * ```\n */\nexport function createObjectStore(\n  db: IDBDatabase,\n  storeName: string,\n  options?: IDBObjectStoreParameters,\n): IDBObjectStore {\n  try {\n    return db.createObjectStore(storeName, options)\n  } catch (error) {\n    // Check if this is being called outside of a version change transaction\n    if (error instanceof DOMException && error.name === 'InvalidStateError') {\n      throw new Error(\n        devBuild() && process.env.NODE_ENV !== `production`\n          ? `Cannot create object store \"${storeName}\": This operation is only allowed during a database upgrade. ` +\n              'Ensure you are calling createObjectStore within the onUpgrade callback of openDatabase.'\n          : codedMessage(185, { storeName }),\n        { cause: error },\n      )\n    }\n\n    // Check if the object store already exists\n    if (error instanceof DOMException && error.name === 'ConstraintError') {\n      throw new Error(\n        devBuild() && process.env.NODE_ENV !== `production`\n          ? `Object store \"${storeName}\" already exists in the database. ` +\n              'Check the database version and only create stores when needed.'\n          : codedMessage(186, { storeName }),\n        { cause: error },\n      )\n    }\n\n    throw new Error(\n      devBuild() && process.env.NODE_ENV !== `production`\n        ? `Failed to create object store \"${storeName}\": ${error instanceof Error ? error.message : String(error)}`\n        : codedMessage(187, { storeName, error }),\n      { cause: error },\n    )\n  }\n}\n\n/**\n * Executes a callback within an IndexedDB transaction.\n *\n * This function handles transaction lifecycle automatically:\n * - Creates the transaction with the specified mode\n * - Provides the transaction and object stores to the callback\n * - Waits for both the callback and the transaction to complete (or abort)\n * - Returns the callback's result or rejects with an error\n *\n * IndexedDB can commit while an async callback is still pending. If that callback\n * later rejects, this function rejects but cannot undo the committed writes.\n *\n * @template T - The return type of the callback\n * @param db - The IDBDatabase instance\n * @param storeNames - A single store name or array of store names to include in the transaction\n * @param mode - The transaction mode ('readonly', 'readwrite', or 'readwriteflush')\n * @param callback - A function that performs operations within the transaction.\n *                   Receives the transaction and a record of object stores keyed by name.\n *                   Can be sync or async.\n * @returns A promise that resolves to the callback's return value when the transaction completes\n *\n * @example\n * ```typescript\n * // Single store\n * const result = await executeTransaction(db, 'todos', 'readwrite', (tx, stores) => {\n *   stores.todos.put({ id: 1, text: 'Buy milk' })\n *   return 'done'\n * })\n *\n * // Multiple stores\n * await executeTransaction(db, ['todos', 'users'], 'readwrite', (tx, stores) => {\n *   stores.todos.put({ id: 1, text: 'Task' })\n *   stores.users.put({ id: 1, name: 'Alice' })\n * })\n * ```\n */\nexport function executeTransaction<T>(\n  db: IDBDatabase,\n  storeNames: string | Array<string>,\n  mode: IDBTransactionMode,\n  callback: (\n    transaction: IDBTransaction,\n    stores: Record<string, IDBObjectStore>,\n  ) => T | Promise<T>,\n): Promise<T> {\n  return new Promise((resolve, reject) => {\n    const storeNamesArray = Array.isArray(storeNames)\n      ? storeNames\n      : [storeNames]\n    let transaction: IDBTransaction\n\n    try {\n      transaction = db.transaction(storeNamesArray, mode)\n    } catch (error) {\n      reject(\n        new Error(\n          devBuild() && process.env.NODE_ENV !== `production`\n            ? `Failed to create transaction for stores [${storeNamesArray.join(', ')}]: ${error instanceof Error ? error.message : String(error)}`\n            : codedMessage(188, { storeNames: storeNamesArray, error }),\n          { cause: error },\n        ),\n      )\n      return\n    }\n\n    // Build the stores record\n    const stores: Record<string, IDBObjectStore> = {}\n    for (const storeName of storeNamesArray) {\n      try {\n        stores[storeName] = transaction.objectStore(storeName)\n      } catch (error) {\n        reject(\n          new Error(\n            devBuild() && process.env.NODE_ENV !== `production`\n              ? `Object store \"${storeName}\" not found in the database. ` +\n                  'Ensure the store was created during the database upgrade.'\n              : codedMessage(189, { storeName }),\n            { cause: error },\n          ),\n        )\n        return\n      }\n    }\n\n    // Success requires both obligations: callback result AND transaction\n    // completion. Request success alone is not a durability receipt.\n    const completed = new Promise<void>((complete, abort) => {\n      // The callback may also set native event-handler properties.\n      transaction.addEventListener('complete', () => complete())\n      transaction.addEventListener('abort', () =>\n        abort(\n          transaction.error ??\n            new Error(\n              devBuild() && process.env.NODE_ENV !== `production`\n                ? 'Transaction was aborted'\n                : codedMessage(190),\n            ),\n        ),\n      )\n      // Request errors normally bubble before abort. Let abort report the\n      // transaction outcome; callback rejection retains its original cause.\n    })\n    let result: T | Promise<T>\n    try {\n      result = callback(transaction, stores)\n    } catch (error) {\n      result = Promise.reject(error)\n    }\n    const callbackResult = Promise.resolve(result).catch((error) => {\n      try {\n        transaction.abort()\n      } catch {\n        // An async callback may settle after the native transaction has ended.\n      }\n      throw error\n    })\n    Promise.all([callbackResult, completed]).then(\n      ([value]) => resolve(value),\n      reject,\n    )\n  })\n}\n\n/**\n * Retrieves all items from an object store.\n *\n * Uses the native `getAll()` method for efficient bulk retrieval.\n *\n * @template T - The type of items in the object store\n * @param objectStore - The IDBObjectStore to read from\n * @returns A promise that resolves to an array of all items in the store\n *\n * @example\n * ```typescript\n * await executeTransaction(db, 'todos', 'readonly', async (tx, stores) => {\n *   const allTodos = await getAll<Todo>(stores.todos)\n *   console.log('All todos:', allTodos)\n * })\n * ```\n */\nexport function getAll<T>(objectStore: IDBObjectStore): Promise<Array<T>> {\n  return executeRequest<Array<T>>(\n    () => objectStore.getAll(),\n    (cause) =>\n      devBuild() && process.env.NODE_ENV !== `production`\n        ? `Failed to get all items from object store \"${objectStore.name}\": ${cause}`\n        : codedMessage(204, { name: objectStore.name, cause }),\n  )\n}\n\n/**\n * Retrieves all keys from an object store.\n *\n * Uses the native `getAllKeys()` method for efficient bulk key retrieval.\n *\n * @param objectStore - The IDBObjectStore to read keys from\n * @returns A promise that resolves to an array of all keys in the store\n *\n * @example\n * ```typescript\n * await executeTransaction(db, 'todos', 'readonly', async (tx, stores) => {\n *   const allKeys = await getAllKeys(stores.todos)\n *   console.log('All keys:', allKeys)\n * })\n * ```\n */\nexport function getAllKeys(\n  objectStore: IDBObjectStore,\n): Promise<Array<IDBValidKey>> {\n  return executeRequest(\n    () => objectStore.getAllKeys(),\n    (cause) =>\n      devBuild() && process.env.NODE_ENV !== `production`\n        ? `Failed to get all keys from object store \"${objectStore.name}\": ${cause}`\n        : codedMessage(200, { name: objectStore.name, cause }),\n  )\n}\n\n/**\n * Retrieves a single item by its key from an object store.\n *\n * @template T - The type of the item\n * @param objectStore - The IDBObjectStore to read from\n * @param key - The key of the item to retrieve\n * @returns A promise that resolves to the item, or undefined if not found\n *\n * @example\n * ```typescript\n * await executeTransaction(db, 'todos', 'readonly', async (tx, stores) => {\n *   const todo = await getByKey<Todo>(stores.todos, 1)\n *   if (todo) {\n *     console.log('Found todo:', todo)\n *   }\n * })\n * ```\n */\nexport function getByKey<T>(\n  objectStore: IDBObjectStore,\n  key: IDBValidKey,\n): Promise<T | undefined> {\n  return executeRequest<T | undefined>(\n    () => objectStore.get(key),\n    (cause) =>\n      devBuild() && process.env.NODE_ENV !== `production`\n        ? `Failed to get item with key \"${String(key)}\" from object store \"${objectStore.name}\": ${cause}`\n        : codedMessage(205, {\n            key: String(key),\n            name: objectStore.name,\n            cause,\n          }),\n  )\n}\n\n/**\n * Writes an item to an object store using upsert semantics.\n *\n * If an item with the same key exists, it will be replaced.\n * If no item with the key exists, a new one will be created.\n *\n * @template T - The type of the item\n * @param objectStore - The IDBObjectStore to write to\n * @param value - The item to write\n * @param key - Optional key for the item. Required if the object store doesn't have a keyPath.\n * @returns A promise that resolves to the key of the written item\n *\n * @example\n * ```typescript\n * // With keyPath (key extracted from value)\n * await executeTransaction(db, 'todos', 'readwrite', async (tx, stores) => {\n *   const key = await put(stores.todos, { id: 1, text: 'Buy milk' })\n *   console.log('Wrote item with key:', key)\n * })\n *\n * // Without keyPath (explicit key)\n * await executeTransaction(db, 'items', 'readwrite', async (tx, stores) => {\n *   const key = await put(stores.items, { text: 'Some data' }, 'myKey')\n *   console.log('Wrote item with key:', key)\n * })\n * ```\n */\nexport function put<T>(\n  objectStore: IDBObjectStore,\n  value: T,\n  key?: IDBValidKey,\n): Promise<IDBValidKey> {\n  return executeRequest(\n    () =>\n      key !== undefined ? objectStore.put(value, key) : objectStore.put(value),\n    (cause) =>\n      devBuild() && process.env.NODE_ENV !== `production`\n        ? `Failed to write item to object store \"${objectStore.name}\": ${cause}`\n        : codedMessage(201, { name: objectStore.name, cause }),\n  )\n}\n\n/**\n * Deletes an item by its key from an object store.\n *\n * @param objectStore - The IDBObjectStore to delete from\n * @param key - The key of the item to delete\n * @returns A promise that resolves when the item is deleted\n *\n * @example\n * ```typescript\n * await executeTransaction(db, 'todos', 'readwrite', async (tx, stores) => {\n *   await deleteByKey(stores.todos, 1)\n *   console.log('Todo deleted')\n * })\n * ```\n */\nexport function deleteByKey(\n  objectStore: IDBObjectStore,\n  key: IDBValidKey,\n): Promise<void> {\n  return executeRequest(\n    () => objectStore.delete(key),\n    (cause) =>\n      devBuild() && process.env.NODE_ENV !== `production`\n        ? `Failed to delete item with key \"${String(key)}\" from object store \"${objectStore.name}\": ${cause}`\n        : codedMessage(202, {\n            key: String(key),\n            name: objectStore.name,\n            cause,\n          }),\n  )\n}\n\n/**\n * Removes all items from an object store.\n *\n * @param objectStore - The IDBObjectStore to clear\n * @returns A promise that resolves when all items are removed\n *\n * @example\n * ```typescript\n * await executeTransaction(db, 'todos', 'readwrite', async (tx, stores) => {\n *   await clear(stores.todos)\n *   console.log('All todos cleared')\n * })\n * ```\n */\nexport function clear(objectStore: IDBObjectStore): Promise<void> {\n  return executeRequest(\n    () => objectStore.clear(),\n    (cause) =>\n      devBuild() && process.env.NODE_ENV !== `production`\n        ? `Failed to clear object store \"${objectStore.name}\": ${cause}`\n        : codedMessage(203, { name: objectStore.name, cause }),\n  )\n}\n\n/**\n * Deletes an entire IndexedDB database.\n * A blocked request stays pending until native success or error.\n *\n * Use with caution - this removes the database and all of its object stores and data.\n *\n * @param name - The name of the database to delete\n * @param idbFactory - Optional IDBFactory for testing/mocking\n * @param onBlocked - Optional diagnostic callback for native blocked events. The request stays pending.\n * @returns A promise that resolves when the database is deleted\n *\n * @example\n * ```typescript\n * await deleteDatabase('myApp')\n * console.log('Database deleted')\n * ```\n */\nexport function deleteDatabase(\n  name: string,\n  idbFactory?: IDBFactory,\n  onBlocked?: (event: IDBVersionChangeEvent) => void,\n): Promise<void> {\n  return new Promise((resolve, reject) => {\n    const factory = getIDBFactory(idbFactory)\n\n    let request: IDBOpenDBRequest\n    try {\n      request = factory.deleteDatabase(name)\n    } catch (error) {\n      reject(\n        new Error(\n          devBuild() && process.env.NODE_ENV !== `production`\n            ? `Failed to delete IndexedDB database \"${name}\": ${error instanceof Error ? error.message : String(error)}`\n            : codedMessage(191, { name, error }),\n          { cause: error },\n        ),\n      )\n      return\n    }\n\n    if (onBlocked) request.addEventListener('blocked', onBlocked)\n\n    request.onsuccess = () => {\n      resolve()\n    }\n\n    request.onerror = () => {\n      const errorMessage = request.error?.message || 'Unknown error'\n      reject(\n        new Error(\n          devBuild() && process.env.NODE_ENV !== `production`\n            ? `Failed to delete IndexedDB database \"${name}\": ${errorMessage}`\n            : codedMessage(192, { name, errorMessage }),\n          { cause: request.error },\n        ),\n      )\n    }\n  })\n}\n"],"names":["devBuild","codedMessage","errorMessage"],"mappings":"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"}