{"version":3,"file":"source-id-bindings.cjs","sources":["../../src/source-id-bindings.ts"],"sourcesContent":["import { BaseQueryBuilder, IR, isCollection } from '@tanstack/db'\nimport type { DbClient } from '@tanstack/db'\n\nconst sourceObjectTokens = new WeakMap<object, number>()\nlet nextSourceObjectToken = 0\n\nexport function getSourceObjectToken(source: object): number {\n  let id = sourceObjectTokens.get(source)\n  if (id === undefined) {\n    id = ++nextSourceObjectToken\n    sourceObjectTokens.set(source, id)\n  }\n  return id\n}\n\nexport function getPreparedSources(\n  preparedValue: unknown,\n): Array<{ id: string }> {\n  if (isCollection(preparedValue)) return [preparedValue]\n  const query =\n    preparedValue instanceof BaseQueryBuilder\n      ? preparedValue\n      : preparedValue &&\n          typeof preparedValue === `object` &&\n          `query` in preparedValue &&\n          preparedValue.query instanceof BaseQueryBuilder\n        ? preparedValue.query\n        : undefined\n  return query\n    ? IR.collectCollectionSources(query._getQuery()).map(\n        ({ collection }) => collection,\n      )\n    : []\n}\n\n/** The source object each Collection ID named while one hook is mounted. */\nexport type SourceIdBindings = {\n  unscoped: Map<string, number>\n  byClient: WeakMap<DbClient, Map<string, number>>\n}\n\nexport function createSourceIdBindings(): SourceIdBindings {\n  return { unscoped: new Map(), byClient: new WeakMap() }\n}\n\n/**\n * Derived query identity names each source by its Collection ID. While a hook\n * is mounted, an ID must keep naming one source object in each client scope,\n * or the hook could reuse a live query that reads the old source. Claims the\n * prepared value's sources, or calls `release` and throws on a collision so a\n * rejected render keeps no sync-start deferral.\n */\nexport function claimSourceIds(\n  bindings: SourceIdBindings,\n  preparedValue: unknown,\n  client: DbClient | undefined,\n  hookName: string,\n  release: () => void,\n): void {\n  const prior = client ? bindings.byClient.get(client) : bindings.unscoped\n  const seen = new Map<string, number>()\n  for (const source of getPreparedSources(preparedValue)) {\n    const token = getSourceObjectToken(source)\n    const previous = seen.get(source.id) ?? prior?.get(source.id)\n    if (previous !== undefined && previous !== token) {\n      release()\n      throw new Error(\n        `[${hookName}] Source Collection \"${source.id}\" was replaced by a different Collection with the same ID while this hook is mounted. Unmount the hook and clean up its previous source and client scope before reusing the ID.`,\n      )\n    }\n    seen.set(source.id, token)\n  }\n  const claimed = prior ?? new Map<string, number>()\n  for (const [id, token] of seen) claimed.set(id, token)\n  if (client) bindings.byClient.set(client, claimed)\n}\n\n/**\n * Resumes every deferred sync start, then rethrows the first startup error, so\n * one failing source cannot keep a later shared source deferred.\n */\nexport function resumeSyncStarts(\n  collections: Set<{ _resumeSyncStart: () => void }>,\n): void {\n  const pending = Array.from(collections)\n  collections.clear()\n  const errors: Array<unknown> = []\n  for (const collection of pending) {\n    try {\n      collection._resumeSyncStart()\n    } catch (error) {\n      errors.push(error)\n    }\n  }\n  if (errors.length) throw errors[0]\n}\n"],"names":["isCollection","BaseQueryBuilder","IR"],"mappings":";;;AAGA,MAAM,yCAAyB,QAAA;AAC/B,IAAI,wBAAwB;AAErB,SAAS,qBAAqB,QAAwB;AAC3D,MAAI,KAAK,mBAAmB,IAAI,MAAM;AACtC,MAAI,OAAO,QAAW;AACpB,SAAK,EAAE;AACP,uBAAmB,IAAI,QAAQ,EAAE;AAAA,EACnC;AACA,SAAO;AACT;AAEO,SAAS,mBACd,eACuB;AACvB,MAAIA,gBAAa,aAAa,EAAG,QAAO,CAAC,aAAa;AACtD,QAAM,QACJ,yBAAyBC,GAAAA,mBACrB,gBACA,iBACE,OAAO,kBAAkB,YACzB,WAAW,iBACX,cAAc,iBAAiBA,sBAC/B,cAAc,QACd;AACR,SAAO,QACHC,GAAAA,GAAG,yBAAyB,MAAM,UAAA,CAAW,EAAE;AAAA,IAC7C,CAAC,EAAE,WAAA,MAAiB;AAAA,EAAA,IAEtB,CAAA;AACN;AAQO,SAAS,yBAA2C;AACzD,SAAO,EAAE,UAAU,oBAAI,IAAA,GAAO,UAAU,oBAAI,UAAQ;AACtD;AASO,SAAS,eACd,UACA,eACA,QACA,UACA,SACM;AACN,QAAM,QAAQ,SAAS,SAAS,SAAS,IAAI,MAAM,IAAI,SAAS;AAChE,QAAM,2BAAW,IAAA;AACjB,aAAW,UAAU,mBAAmB,aAAa,GAAG;AACtD,UAAM,QAAQ,qBAAqB,MAAM;AACzC,UAAM,WAAW,KAAK,IAAI,OAAO,EAAE,KAAK,OAAO,IAAI,OAAO,EAAE;AAC5D,QAAI,aAAa,UAAa,aAAa,OAAO;AAChD,cAAA;AACA,YAAM,IAAI;AAAA,QACR,IAAI,QAAQ,wBAAwB,OAAO,EAAE;AAAA,MAAA;AAAA,IAEjD;AACA,SAAK,IAAI,OAAO,IAAI,KAAK;AAAA,EAC3B;AACA,QAAM,UAAU,SAAS,oBAAI,IAAA;AAC7B,aAAW,CAAC,IAAI,KAAK,KAAK,KAAM,SAAQ,IAAI,IAAI,KAAK;AACrD,MAAI,OAAQ,UAAS,SAAS,IAAI,QAAQ,OAAO;AACnD;AAMO,SAAS,iBACd,aACM;AACN,QAAM,UAAU,MAAM,KAAK,WAAW;AACtC,cAAY,MAAA;AACZ,QAAM,SAAyB,CAAA;AAC/B,aAAW,cAAc,SAAS;AAChC,QAAI;AACF,iBAAW,iBAAA;AAAA,IACb,SAAS,OAAO;AACd,aAAO,KAAK,KAAK;AAAA,IACnB;AAAA,EACF;AACA,MAAI,OAAO,OAAQ,OAAM,OAAO,CAAC;AACnC;;;;;;"}