Rindle

API index and search · Build metadata

Source snapshot

packages/client/src/key.ts

Source revision 05d0bf2c2e56 · build details
Source revision: 05d0bf2c2e56.
TypeScript input SHA-256: aabe6cfcc4172b870d5e272142958e9ea8d8784c2aa23133156e5a7ee633318e
Generated 2026-09-04T23:58:25.590Z with TypeScript 6.0.3. Public TypeScript checks and declaration emit passed. Package runtime tests are separate.
1// A stable, canonical JSON string for a query AST — the `viewKey` shared by the React cache2// (one cached view per AST) and the SSR dehydrate/hydrate map (seed lookup by AST). Both sides3// MUST agree byte-for-byte, so the one canonical serializer lives here. Object keys are sorted;4// `undefined` is encoded distinctly (so `{a:undefined}` ≠ `{}`); cycles throw.56export function stableKey(value: unknown, seen = new WeakSet<object>()): string {7  if (value === undefined) return '{"$undefined":true}';8  if (value === null || typeof value !== "object") return JSON.stringify(value);9  if (seen.has(value)) throw new TypeError("Rindle query keys must be acyclic JSON values");10  seen.add(value);11  if (Array.isArray(value)) {12    const out = `[${value.map((v) => stableKey(v, seen)).join(",")}]`;13    seen.delete(value);14    return out;15  }16  const obj = value as Record<string, unknown>;17  const out = `{${Object.keys(obj)18    .sort()19    .map((k) => `${JSON.stringify(k)}:${stableKey(obj[k], seen)}`)20    .join(",")}}`;21  seen.delete(value);22  return out;23}24