@maximem/synap-js-sdk 0.3.0 → 1.0.0-beta.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/MIGRATING.md +146 -0
- package/README.md +96 -83
- package/bin/synap-js-sdk.js +45 -122
- package/dist/anticipation-cache-BgkqcTPJ.d.cts +180 -0
- package/dist/anticipation-cache-BgkqcTPJ.d.ts +180 -0
- package/dist/anticipation-cache-D5YHEPV3.js +10 -0
- package/dist/anticipation-cache-D5YHEPV3.js.map +1 -0
- package/dist/anticipation-cache-JBZHTJ3O.cjs +10 -0
- package/dist/anticipation-cache-JBZHTJ3O.cjs.map +1 -0
- package/dist/chunk-5SC3ELNK.js +856 -0
- package/dist/chunk-5SC3ELNK.js.map +1 -0
- package/dist/chunk-HR5Y3KXS.cjs +172 -0
- package/dist/chunk-HR5Y3KXS.cjs.map +1 -0
- package/dist/chunk-NIDPTBNC.cjs +800 -0
- package/dist/chunk-NIDPTBNC.cjs.map +1 -0
- package/dist/chunk-QBCVMPGK.js +28 -0
- package/dist/chunk-QBCVMPGK.js.map +1 -0
- package/dist/chunk-T3NZBIV2.js +172 -0
- package/dist/chunk-T3NZBIV2.js.map +1 -0
- package/dist/chunk-TCEP5OVR.js +800 -0
- package/dist/chunk-TCEP5OVR.js.map +1 -0
- package/dist/chunk-VXRCBMCY.cjs +856 -0
- package/dist/chunk-VXRCBMCY.cjs.map +1 -0
- package/dist/chunk-ZKOJDUN4.cjs +28 -0
- package/dist/chunk-ZKOJDUN4.cjs.map +1 -0
- package/dist/env-55ULHNJZ.cjs +11 -0
- package/dist/env-55ULHNJZ.cjs.map +1 -0
- package/dist/env-QCUKKW36.js +11 -0
- package/dist/env-QCUKKW36.js.map +1 -0
- package/dist/grpc/index.cjs +87 -0
- package/dist/grpc/index.cjs.map +1 -0
- package/dist/grpc/index.d.cts +162 -0
- package/dist/grpc/index.d.ts +162 -0
- package/dist/grpc/index.js +87 -0
- package/dist/grpc/index.js.map +1 -0
- package/dist/index.cjs +2111 -0
- package/dist/index.cjs.map +1 -0
- package/dist/index.d.cts +1477 -0
- package/dist/index.d.ts +1477 -0
- package/dist/index.js +2111 -0
- package/dist/index.js.map +1 -0
- package/dist/stream-client-ME5N5NK4.js +7 -0
- package/dist/stream-client-ME5N5NK4.js.map +1 -0
- package/dist/stream-client-ZN6ADZBR.cjs +7 -0
- package/dist/stream-client-ZN6ADZBR.cjs.map +1 -0
- package/package.json +68 -23
- package/.env.example +0 -39
- package/bridge/synap_bridge.py +0 -768
- package/src/bridge-manager.js +0 -262
- package/src/errors.js +0 -168
- package/src/index.js +0 -13
- package/src/runtime.js +0 -161
- package/src/setup-typescript.js +0 -161
- package/src/synap-client.js +0 -464
- package/types/index.d.ts +0 -475
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["/Users/anish/maximemai/maximem_synap/synap/sdk/js/dist/chunk-NIDPTBNC.cjs","../src/behavior/anticipation.json","../src/behavior/contract.ts","../src/cache/bm25.ts","../src/context/anticipation-cache.ts"],"names":[],"mappings":"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","file":"/Users/anish/maximemai/maximem_synap/synap/sdk/js/dist/chunk-NIDPTBNC.cjs","sourcesContent":[null,"{\n \"$comment\": \"SOURCE OF TRUTH for anticipation-cache behavior, shared by the Python and JS/TS SDKs. Do not duplicate these values into either SDK's source. See ../README.md. Regexes are restricted to the intersection of Python 're' and ECMAScript; both SDKs have a parity test.\",\n \"version\": 1,\n \"recall_bypass\": {\n \"note\": \"WS4 of the playground query-hygiene plan. A recall-shaped question never serves from the anticipation cache. Asymmetric cost is why: a stale false-hit makes the agent answer 'I don't see that' while the store holds the fact (the BZQR6J cross-session failure), whereas bypassing costs only cold-fetch latency on a turn where the user already expects a lookup. Stem coverage cannot gate this \\u2014 false hits were measured at coverage=1.00. Ties break toward INCLUDING a pattern.\",\n \"env_flag\": \"SYNAP_SDK_CACHE_RECALL_BYPASS\",\n \"default\": false,\n \"patterns\": [\n {\n \"pattern\": \"\\\\bremind me\\\\b\",\n \"flags\": \"i\",\n \"note\": \"Original set (WS4, playground query-hygiene plan).\"\n },\n {\n \"pattern\": \"\\\\bon file\\\\b\",\n \"flags\": \"i\",\n \"note\": \"Original set (WS4).\"\n },\n {\n \"pattern\": \"\\\\b(your|my|the) records\\\\b\",\n \"flags\": \"i\",\n \"note\": \"Original set (WS4).\"\n },\n {\n \"pattern\": \"\\\\bdo you (have|know|remember|recall|see)\\\\b\",\n \"flags\": \"i\",\n \"note\": \"Original set (WS4).\"\n },\n {\n \"pattern\": \"\\\\bwhat (do|did) (i|you) (say|tell|mention|have)\\\\b\",\n \"flags\": \"i\",\n \"note\": \"Original set (WS4).\"\n },\n {\n \"pattern\": \"\\\\bwhat('s| is) my\\\\b\",\n \"flags\": \"i\",\n \"note\": \"Original set (WS4).\"\n },\n {\n \"pattern\": \"\\\\bwhere (am i|do i live)\\\\b\",\n \"flags\": \"i\",\n \"note\": \"Original set (WS4).\"\n },\n {\n \"pattern\": \"\\\\bhow long have i\\\\b\",\n \"flags\": \"i\",\n \"note\": \"Original set (WS4).\"\n },\n {\n \"pattern\": \"\\\\bwhich of my\\\\b\",\n \"flags\": \"i\",\n \"note\": \"Original set (WS4).\"\n },\n {\n \"pattern\": \"\\\\bwhat .{0,40}\\\\b(again|earlier|last time|previously|yesterday)\\\\b\",\n \"flags\": \"i\",\n \"note\": \"Original set (WS4). 'again' alone is deliberately NOT a marker: 'book me a ride again' is a task query, not a recall query.\"\n },\n {\n \"pattern\": \"\\\\bwill you use to (contact|reach|notify)\\\\b\",\n \"flags\": \"i\",\n \"note\": \"Original set (WS4).\"\n },\n {\n \"pattern\": \"\\\\b(confirm|verify|double.?check)\\\\b.{0,40}\\\\bmy\\\\b\",\n \"flags\": \"i\",\n \"note\": \"2026-07-16 eval register issue #11: 'can you confirm my email address?' served a stale bundle. Also catches 'confirm my booking' \\u2014 an intentional over-match, costing one cloud fetch.\"\n },\n {\n \"pattern\": \"\\\\b(linked to|associated with|registered (to|on|with)) my\\\\b\",\n \"flags\": \"i\",\n \"note\": \"2026-07-16 eval register issue #11: 'what name is linked to my Uber account?' served a stale bundle.\"\n },\n {\n \"pattern\": \"\\\\b(best|preferred) way to (reach|contact|update|notify) me\\\\b\",\n \"flags\": \"i\",\n \"note\": \"2026-07-16 eval register issue #11: 'best way to contact me with updates' served a stale bundle.\"\n },\n {\n \"pattern\": \"\\\\bhow (do|will|can|should) you (reach|contact|notify) me\\\\b\",\n \"flags\": \"i\",\n \"note\": \"2026-07-16 eval register issue #11, sibling phrasing of the above.\"\n },\n {\n \"pattern\": \"\\\\bwhich .{0,40}\\\\b(are|will) you (going to )?(use|using)\\\\b\",\n \"flags\": \"i\",\n \"note\": \"2026-07-16 eval register issue #11: 'which email are you going to use?' served a stale bundle.\"\n },\n {\n \"pattern\": \"\\\\bon (my|the) account\\\\b\",\n \"flags\": \"i\",\n \"note\": \"2026-07-16 eval register issue #11.\"\n }\n ]\n },\n \"thresholds\": {\n \"bm25\": {\n \"value\": 1.5,\n \"note\": \"Nominal threshold. The value actually applied is derived per query: max(effective_floor, min(bm25, query_token_scale * len(query_tokens))). Short queries cannot reach the nominal score, so holding them to it would miss every time.\"\n },\n \"novel_term\": {\n \"value\": 0.45,\n \"note\": \"Fraction of query stems absent from the cached corpus that forces a miss.\"\n },\n \"min_corpus_for_novel_gate\": {\n \"value\": 200,\n \"note\": \"The novel-term gate is meaningless on a small corpus, where the ratio is dominated by ordinary English word forms. Measured: a fresh playground conversation reaches ~60 stems after the first push and would trip the 0.45 gate on essentially every second-turn query. 200 means the gate engages once a customer has ~3-4 typical bundles cached.\"\n },\n \"effective_floor\": {\n \"value\": 0.6,\n \"note\": \"Lower bound on the derived per-query threshold. Below this, BM25 stops discriminating.\"\n },\n \"query_token_scale\": {\n \"value\": 0.3,\n \"note\": \"Scales the threshold down for short queries: 0.3 points of score per query token.\"\n }\n },\n \"bm25\": {\n \"k1\": 1.5,\n \"b\": 0.75,\n \"idf_floor\": 0.5,\n \"min_token_len\": 2,\n \"min_stem_len\": 4,\n \"suffixes\": [\n \"ences\",\n \"ances\",\n \"ation\",\n \"tion\",\n \"sion\",\n \"ence\",\n \"ance\",\n \"ness\",\n \"ment\",\n \"able\",\n \"ible\",\n \"ical\",\n \"ally\",\n \"ies\",\n \"ive\",\n \"ful\",\n \"ous\",\n \"ing\",\n \"ary\",\n \"ly\",\n \"ed\",\n \"es\",\n \"s\"\n ],\n \"stop_words\": [\n \"a\",\n \"about\",\n \"after\",\n \"an\",\n \"and\",\n \"are\",\n \"at\",\n \"be\",\n \"been\",\n \"before\",\n \"being\",\n \"but\",\n \"by\",\n \"can\",\n \"could\",\n \"did\",\n \"do\",\n \"does\",\n \"for\",\n \"from\",\n \"had\",\n \"has\",\n \"have\",\n \"how\",\n \"if\",\n \"in\",\n \"into\",\n \"is\",\n \"it\",\n \"its\",\n \"may\",\n \"might\",\n \"no\",\n \"nor\",\n \"not\",\n \"of\",\n \"on\",\n \"or\",\n \"over\",\n \"should\",\n \"so\",\n \"than\",\n \"that\",\n \"the\",\n \"then\",\n \"these\",\n \"this\",\n \"those\",\n \"to\",\n \"was\",\n \"were\",\n \"what\",\n \"when\",\n \"where\",\n \"which\",\n \"who\",\n \"whom\",\n \"why\",\n \"will\",\n \"with\",\n \"would\"\n ],\n \"alias_token\": {\n \"pattern\": \"\\\\[\\\\[([A-Za-z][A-Za-z0-9_]*_[a-z0-9]{12})\\\\]\\\\]\",\n \"note\": \"An alias label as it appears in text: [[PERSON_PHONE_h2n7v5cx8m0d]]. Kept whole rather than split, because 'person' and 'phone' are boilerplate shared by every label of that field type and would make two different people's memories score alike. Mirrors synap/cloud/shared/tokenizer.py \\u2014 keep the two in step.\"\n },\n \"suffix_note\": \"Order matters: longest-first, because _stem returns on first match. Reordering this list silently changes every stem and therefore every BM25 score.\"\n },\n \"env_flags\": {\n \"$comment\": \"Read at CALL time, never at module load. Python does os.environ.get inside the function bodies; JS must do the same or late process.env mutation stops working and the flag looks broken. See gotcha G-S.\",\n \"SYNAP_SDK_CACHE_RECALL_BYPASS\": {\n \"default\": false,\n \"truthy\": [\n \"true\",\n \"1\",\n \"yes\"\n ]\n },\n \"SYNAP_SDK_CACHE_HONOR_TTL_HINT\": {\n \"default\": false,\n \"truthy\": [\n \"true\",\n \"1\",\n \"yes\"\n ],\n \"note\": \"A bundle's server ttl_hint_seconds may only SHORTEN the global TTL, never extend it.\"\n },\n \"SYNAP_SDK_CACHE_INVALIDATE_ON_WRITE\": {\n \"default\": false,\n \"truthy\": [\n \"true\",\n \"1\",\n \"yes\"\n ],\n \"note\": \"2026-07-16 eval register issue #8: the cloud invalidates its own Redis caches on ingest, but that stops at the process boundary.\"\n },\n \"SYNAP_SDK_CACHE_MAX_ENTRY_AGE\": {\n \"default\": null,\n \"note\": \"2026-07-16 eval register issue #6: stored_at is a sliding lease renewed on hit, so under steady traffic a pre-update snapshot never expired. Defaults to 2x the sliding TTL; 0 disables.\"\n },\n \"SYNAP_SDK_CACHE_COVERAGE_MIN\": {\n \"default\": null\n }\n },\n \"coverage_gate\": {\n \"note\": \"Fraction of the query's stems present in the picked items. A bundle can clear the BM25 threshold on one shared token ('account') while lacking the asked-for fact entirely: the false HIT behind the eval's 'forgot the name' failure. ALWAYS computed and reported; ENFORCED only when SYNAP_SDK_CACHE_COVERAGE_MIN is explicitly set, so default behavior is unchanged. When it does fire it must gate BEFORE any side effect, so a rejected lookup leaves cache state untouched.\",\n \"env_flag\": \"SYNAP_SDK_CACHE_COVERAGE_MIN\",\n \"default\": null,\n \"empty_query_coverage\": 1.0\n },\n \"telemetry\": {\n \"rejected_items_cap\": {\n \"value\": 20,\n \"note\": \"Rejected items reported per lookup, highest score first, so a large cache cannot bloat the payload.\"\n },\n \"content_preview_chars\": 120\n }\n}\n","/**\n * Loader for the shared SDK behavior contract.\n *\n * The values here are tuned against measured eval failures and are shared,\n * byte-identical, with the Python SDK. They live in data rather than code\n * specifically so the two SDKs cannot drift. See\n * `synap/sdk/CONTRACT/README.md`.\n *\n * `anticipation.json` is vendored into `src/` by\n * `synap/sdk/scripts/sync-behavior.sh` and imported (not read from disk) so\n * that the bundler inlines it. Reading it with `node:fs` at runtime would work\n * in Node and break in every bundled target: Edge, Workers, and anything under\n * webpack/turbopack, where `dist/` is rewritten and relative paths do not\n * survive. It is the same failure mode as `@grpc/proto-loader` reading a\n * `.proto` off disk (gotcha G-P).\n */\n\nimport contractJson from './anticipation.json' with { type: 'json' };\n\nexport interface RecallPattern {\n pattern: string;\n flags: string;\n note: string;\n}\n\nexport interface BehaviorContract {\n version: number;\n recall_bypass: {\n note: string;\n env_flag: string;\n default: boolean;\n patterns: RecallPattern[];\n };\n thresholds: {\n bm25: { value: number; note: string };\n novel_term: { value: number; note: string };\n min_corpus_for_novel_gate: { value: number; note: string };\n effective_floor: { value: number; note: string };\n query_token_scale: { value: number; note: string };\n };\n coverage_gate: {\n note: string;\n env_flag: string;\n default: number | null;\n empty_query_coverage: number;\n };\n telemetry: {\n rejected_items_cap: { value: number; note: string };\n content_preview_chars: number;\n };\n bm25: {\n k1: number;\n b: number;\n idf_floor: number;\n min_token_len: number;\n min_stem_len: number;\n suffixes: string[];\n stop_words: string[];\n alias_token: { pattern: string; note: string };\n };\n}\n\nexport const CONTRACT = contractJson as unknown as BehaviorContract;\n\n/** ECMAScript flags we accept. Anything else is invalid in Python too. */\nconst ALLOWED_FLAGS = new Set(['i', 'm', 's']);\n\nfunction compile(pattern: string, flags: string): RegExp {\n for (const ch of flags) {\n if (!ALLOWED_FLAGS.has(ch)) {\n throw new Error(\n `Unsupported regex flag '${ch}' in behavior contract. Flags must be ` +\n `valid in both Python and ECMAScript.`,\n );\n }\n }\n return new RegExp(pattern, flags);\n}\n\n/**\n * Compiled recall-bypass patterns, in contract order.\n *\n * Deliberately NOT using the `g` flag: a global RegExp carries `lastIndex`\n * between calls, so a shared instance would match on one query and then miss\n * on the next. That failure is intermittent and traffic-dependent, which is\n * the worst kind to debug.\n */\nexport const RECALL_PATTERNS: readonly RegExp[] = CONTRACT.recall_bypass.patterns.map((p) =>\n compile(p.pattern, p.flags ?? ''),\n);\n\nexport const THRESHOLDS = {\n bm25: CONTRACT.thresholds.bm25.value,\n novelTerm: CONTRACT.thresholds.novel_term.value,\n minCorpusForNovelGate: CONTRACT.thresholds.min_corpus_for_novel_gate.value,\n /** Lower bound on the derived per-query threshold. */\n effectiveFloor: CONTRACT.thresholds.effective_floor.value,\n /** Points of score allowed per query token when deriving the threshold. */\n queryTokenScale: CONTRACT.thresholds.query_token_scale.value,\n} as const;\n\nexport const BM25_PARAMS = CONTRACT.bm25;\nexport const STOP_WORDS: ReadonlySet<string> = new Set(CONTRACT.bm25.stop_words);\n// Order is load-bearing: stem() returns on first match, so this must stay\n// longest-first exactly as the contract lists it.\nexport const SUFFIXES: readonly string[] = CONTRACT.bm25.suffixes;\nexport const ALIAS_TOKEN_SOURCE = CONTRACT.bm25.alias_token.pattern;\n\n/** True when any query string looks like an explicit memory-recall ask. */\nexport function isRecallQuery(searchQuery: readonly (string | null | undefined)[] | null | undefined): boolean {\n for (const q of searchQuery ?? []) {\n if (!q) continue;\n for (const pattern of RECALL_PATTERNS) {\n if (pattern.test(q)) return true;\n }\n }\n return false;\n}\n","/**\n * BM25 scorer for the anticipation cache.\n *\n * A faithful port of `maximem_synap/cache/bm25.py`. Every tuned value comes\n * from the shared behavior contract, so the two implementations cannot drift\n * on parameters. What they *can* still drift on is arithmetic, which is what\n * the shared conformance corpus is for.\n */\n\nimport { BM25_PARAMS, STOP_WORDS, SUFFIXES, ALIAS_TOKEN_SOURCE } from '../behavior/contract.js';\n\nconst MIN_STEM_LEN = BM25_PARAMS.min_stem_len;\nconst MIN_TOKEN_LEN = BM25_PARAMS.min_token_len;\n\nexport function stem(word: string): string {\n // Order is load-bearing: longest suffix first, return on first match.\n for (const suffix of SUFFIXES) {\n if (word.endsWith(suffix) && word.length - suffix.length >= MIN_STEM_LEN) {\n return word.slice(0, word.length - suffix.length);\n }\n }\n return word;\n}\n\n/**\n * An alias label, as it appears in text: `[[PERSON_PHONE_h2n7v5cx8m0d]]`.\n *\n * Kept whole rather than split into `person`, `phone` and the suffix, because\n * the first two are boilerplate shared by every label of that field type and\n * would make two different people's memories score alike.\n *\n * Mirrors `synap/cloud/shared/tokenizer.py`. Keep the two in step.\n */\nfunction aliasTokenRe(): RegExp {\n // Constructed per call because `g` regexes carry `lastIndex`, and this one\n // is used with replace(). A module-level shared instance would produce\n // different results on alternating calls.\n return new RegExp(ALIAS_TOKEN_SOURCE, 'g');\n}\n\nconst WORD_RE = /[a-z0-9]+/g;\n\n/** Tokenize, lowercase, remove stop words, and stem. Alias labels survive whole. */\nexport function tokenize(text: string | null | undefined): string[] {\n if (!text) return [];\n\n const labels: string[] = [];\n const remainder = text.replace(aliasTokenRe(), (_match, captured: string) => {\n labels.push(captured.toLowerCase());\n return ' ';\n });\n\n const words = remainder.toLowerCase().match(WORD_RE) ?? [];\n const out = labels.slice();\n for (const w of words) {\n if (w.length >= MIN_TOKEN_LEN && !STOP_WORDS.has(w)) out.push(stem(w));\n }\n return out;\n}\n\n/** Okapi BM25 scorer over a small in-memory corpus. */\nexport class BM25 {\n static readonly IDF_FLOOR = BM25_PARAMS.idf_floor;\n\n readonly k1: number;\n readonly b: number;\n readonly corpus: readonly (readonly string[])[];\n readonly docCount: number;\n readonly avgdl: number;\n readonly docLens: readonly number[];\n readonly idf: ReadonlyMap<string, number>;\n\n constructor(\n corpus: readonly (readonly string[])[],\n k1: number = BM25_PARAMS.k1,\n b: number = BM25_PARAMS.b,\n ) {\n this.k1 = k1;\n this.b = b;\n this.corpus = corpus;\n this.docCount = corpus.length;\n this.docLens = corpus.map((doc) => doc.length);\n // Python falls back to 1.0 rather than dividing by zero on an empty corpus.\n this.avgdl = this.docCount\n ? this.docLens.reduce((a, n) => a + n, 0) / this.docCount\n : 1.0;\n\n const idf = new Map<string, number>();\n const allTerms = new Set<string>();\n for (const doc of corpus) for (const t of doc) allTerms.add(t);\n for (const term of allTerms) {\n let df = 0;\n for (const doc of corpus) if (doc.includes(term)) df++;\n const raw = Math.log((this.docCount - df + 0.5) / (df + 0.5) + 1.0);\n idf.set(term, Math.max(raw, BM25.IDF_FLOOR));\n }\n this.idf = idf;\n }\n\n score(queryTokens: readonly string[], docIdx: number): number {\n const doc = this.corpus[docIdx];\n if (doc === undefined) return 0;\n const dl = this.docLens[docIdx] ?? 0;\n\n const tfMap = new Map<string, number>();\n for (const t of doc) tfMap.set(t, (tfMap.get(t) ?? 0) + 1);\n\n let s = 0;\n for (const term of queryTokens) {\n const tf = tfMap.get(term);\n if (tf === undefined) continue;\n const idf = this.idf.get(term) ?? BM25.IDF_FLOOR;\n const numerator = tf * (this.k1 + 1);\n const denominator = tf + this.k1 * (1 - this.b + (this.b * dl) / this.avgdl);\n s += (idf * numerator) / denominator;\n }\n return s;\n }\n\n scores(queryTokens: readonly string[]): number[] {\n return this.corpus.map((_, i) => this.score(queryTokens, i));\n }\n}\n","/**\n * In-memory TTL cache for context bundles pushed over gRPC.\n *\n * Port of `maximem_synap/cache/anticipation_cache.py`.\n *\n * ## Why this is a faithful port and not a simplification\n *\n * `@maximem/synap-vercel-adk` already contains a native TS anticipation cache,\n * and it is a simplification: a hardcoded 30-minute TTL, a plain BM25 threshold\n * with no per-query derivation, and none of the gates below. Shipping that as\n * the SDK's cache would mean two retrieval behaviors under one brand, which is\n * gotcha G-C. Every gate here exists because a specific eval failed without it:\n *\n * - **Recall bypass** runs BEFORE scoring. The measured false hit scored 2.86\n * at coverage 1.00, so no score-side gate could ever have caught it.\n * - **The novel-term gate** is suppressed below a 200-stem corpus, because at\n * cold start ordinary English trips it on nearly every query.\n * - **The per-query threshold** scales down for short queries, which otherwise\n * cannot reach the nominal score at all.\n * - **The coverage gate** catches a bundle that clears BM25 on one shared\n * token (\"account\") while lacking the asked-for fact.\n *\n * All thresholds come from the shared behavior contract.\n */\n\nimport { BM25, tokenize } from '../cache/bm25.js';\nimport { CONTRACT, THRESHOLDS, isRecallQuery } from '../behavior/contract.js';\nimport { getEnvFlag, getEnvFloat } from '../util/env.js';\n\nconst EFFECTIVE_FLOOR = CONTRACT.thresholds.effective_floor.value;\nconst QUERY_TOKEN_SCALE = CONTRACT.thresholds.query_token_scale.value;\nconst REJECTED_CAP = CONTRACT.telemetry.rejected_items_cap.value;\nconst PREVIEW_CHARS = CONTRACT.telemetry.content_preview_chars;\n\n/** Sentinel scope that matches any requester. */\nexport const ANY_SCOPE = '_any';\n\nexport interface BundleItem {\n item_id?: string;\n content?: string;\n [key: string]: unknown;\n}\n\nexport interface ContextBundle {\n bundleId: string;\n entityId?: string | null;\n conversationId?: string | null;\n itemsByType: Record<string, BundleItem[]>;\n /** Server hint; may only SHORTEN the global TTL, never extend it. */\n ttlHintSeconds?: number | null;\n /** Which anticipation pattern produced this bundle. Diagnostics only. */\n bundleType?: string | null;\n /** The queries the server anticipated. Diagnostics only. */\n searchQueries?: readonly string[] | null;\n}\n\ninterface ItemRecord {\n bundleId: string;\n itemType: string;\n content: string;\n tokens: string[];\n itemDict: BundleItem;\n}\n\ninterface EntryRecord {\n bundleId: string;\n entityId: string;\n conversationId: string | null;\n bundleType: string | null;\n searchQueries: string[];\n /** Sliding lease, refreshed on hit unless TTL hints are honoured. */\n storedAt: number;\n /** Absolute creation time; the max-entry-age cap uses this, not the lease. */\n createdAt: number;\n ttlHintSeconds: number | null;\n}\n\nexport interface LookupResult {\n itemsByType: Record<string, BundleItem[]>;\n bundleIds: string[];\n score: number;\n coverage: number;\n}\n\nexport interface LookupParams {\n searchQuery?: readonly string[] | null;\n entityId?: string | null;\n customerId?: string | null;\n clientId?: string | null;\n conversationId?: string | null;\n maxItems?: number;\n}\n\nexport type ExitReason =\n | 'empty'\n | 'recall_bypass'\n | 'no_query_tokens'\n | 'novel_term_gate'\n | 'empty_corpus'\n | 'no_items_above_threshold'\n | 'coverage_gate'\n | 'hit';\n\nexport interface LookupTelemetry {\n searchQuery: string[];\n entityId: string | null;\n customerId: string | null;\n clientId: string | null;\n conversationId: string | null;\n scopeFilterAccepted: string[];\n novelTermRatio: number | null;\n bm25Threshold: number | null;\n bm25QueryTokens: string[];\n itemsPicked: unknown[];\n itemsRejected: unknown[];\n coverage: number | null;\n hit: boolean;\n exitReason: ExitReason;\n}\n\nexport interface SnapshotItemPreview {\n type: string;\n scope: string | null;\n content: string;\n}\n\nexport interface SnapshotItemRecord {\n bundle_id: string;\n item_type: string;\n tokens: string[];\n content: string;\n}\n\nexport interface SnapshotBundle {\n bundle_id: string;\n entity_id: string;\n conversation_id: string | null;\n bundle_type: string | null;\n search_queries: string[];\n scope_counts: Record<string, number>;\n total_items: number;\n items: SnapshotItemPreview[];\n}\n\nexport interface AnticipationCacheSnapshot {\n total_entries: number;\n total_item_records: number;\n scope_breakdown_overall: Record<string, number>;\n corpus_vocab_size: number;\n corpus_vocab_sample: string[];\n item_records: SnapshotItemRecord[];\n bundles: SnapshotBundle[];\n}\n\nexport interface AnticipationCacheOptions {\n ttlSeconds?: number;\n maxBundles?: number;\n /** Injected in tests. Defaults to a monotonic clock. */\n now?: () => number;\n onLookup?: (telemetry: LookupTelemetry) => void;\n}\n\nconst DEFAULT_TTL_SECONDS = 1800;\nconst DEFAULT_MAX_BUNDLES = 50;\n\nexport class AnticipationCache {\n private readonly ttlSeconds: number;\n private readonly maxBundles: number;\n private readonly now: () => number;\n private readonly onLookup: ((t: LookupTelemetry) => void) | undefined;\n\n private entries = new Map<string, EntryRecord>();\n private items: ItemRecord[] = [];\n private corpusVocab = new Set<string>();\n private bm25: BM25 | null = null;\n private bm25Dirty = true;\n\n constructor(options: AnticipationCacheOptions = {}) {\n this.ttlSeconds = options.ttlSeconds ?? DEFAULT_TTL_SECONDS;\n this.maxBundles = options.maxBundles ?? DEFAULT_MAX_BUNDLES;\n this.now = options.now ?? monotonicNow;\n this.onLookup = options.onLookup;\n }\n\n get size(): number {\n return this.entries.size;\n }\n\n get itemCount(): number {\n return this.items.length;\n }\n\n store(bundle: ContextBundle): void {\n if (!bundle.bundleId) return;\n this.evictExpired();\n\n // Client-scope knowledge (FAQs, policies) arrives with no entity, and the\n // sentinel makes it visible to every requester.\n const entityId = bundle.entityId || ANY_SCOPE;\n\n if (this.entries.has(bundle.bundleId)) this.dropBundle(bundle.bundleId);\n\n const now = this.now();\n this.entries.set(bundle.bundleId, {\n bundleId: bundle.bundleId,\n entityId,\n conversationId: bundle.conversationId ?? null,\n bundleType: bundle.bundleType ?? null,\n searchQueries: [...(bundle.searchQueries ?? [])],\n storedAt: now,\n createdAt: now,\n ttlHintSeconds: bundle.ttlHintSeconds ?? null,\n });\n\n for (const [itemType, list] of Object.entries(bundle.itemsByType ?? {})) {\n for (const item of list ?? []) {\n const content = String(item.content ?? '');\n const tokens = tokenize(content);\n this.items.push({ bundleId: bundle.bundleId, itemType, content, tokens, itemDict: item });\n for (const t of tokens) this.corpusVocab.add(t);\n }\n }\n this.bm25Dirty = true;\n\n // LRU by lease age.\n while (this.entries.size > this.maxBundles) {\n let oldest: EntryRecord | null = null;\n for (const e of this.entries.values()) {\n if (oldest === null || e.storedAt < oldest.storedAt) oldest = e;\n }\n if (oldest === null) break;\n this.dropBundle(oldest.bundleId);\n }\n }\n\n lookup(params: LookupParams): LookupResult | null {\n const {\n searchQuery = null, entityId = null, customerId = null,\n clientId = null, conversationId = null, maxItems = 10,\n } = params;\n\n this.evictExpired();\n\n const accepted = this.buildAcceptedScope(entityId, customerId, clientId);\n const telemetry: LookupTelemetry = {\n searchQuery: (searchQuery ?? []).filter((q): q is string => Boolean(q)),\n entityId, customerId, clientId, conversationId,\n scopeFilterAccepted: [...accepted].sort(),\n novelTermRatio: null, bm25Threshold: null, bm25QueryTokens: [],\n itemsPicked: [], itemsRejected: [], coverage: null,\n hit: false, exitReason: 'empty',\n };\n\n if (this.entries.size === 0 || this.items.length === 0) {\n return this.miss(telemetry, 'empty');\n }\n\n const hasQuery = (searchQuery ?? []).some((q) => q && q.trim() !== '');\n if (!hasQuery) {\n return this.freshnessLookup(entityId, maxItems, telemetry);\n }\n\n // Recall bypass fires BEFORE scoring: a stale false-hit on a recall-shaped\n // question makes the agent deny a fact the store holds, and the measured\n // failure cleared every score-side gate.\n if (getEnvFlag(CONTRACT.recall_bypass.env_flag) && isRecallQuery(searchQuery)) {\n return this.miss(telemetry, 'recall_bypass');\n }\n\n const queryTokens = (searchQuery ?? []).flatMap((q) => tokenize(q));\n telemetry.bm25QueryTokens = queryTokens;\n if (queryTokens.length === 0) {\n return this.miss(telemetry, 'no_query_tokens');\n }\n\n const uniqueStems = new Set(queryTokens);\n let novel = 0;\n for (const s of uniqueStems) if (!this.corpusVocab.has(s)) novel++;\n const novelRatio = uniqueStems.size ? novel / uniqueStems.size : 0;\n telemetry.novelTermRatio = round4(novelRatio);\n\n // Only meaningful once the corpus has real vocabulary. Below the floor the\n // ratio is dominated by ordinary English and would miss on nearly anything.\n if (\n this.corpusVocab.size >= THRESHOLDS.minCorpusForNovelGate &&\n novelRatio >= THRESHOLDS.novelTerm\n ) {\n return this.miss(telemetry, 'novel_term_gate');\n }\n\n if (this.bm25Dirty || this.bm25 === null) {\n if (this.items.length === 0) return this.miss(telemetry, 'empty_corpus');\n this.bm25 = new BM25(this.items.map((i) => i.tokens));\n this.bm25Dirty = false;\n }\n\n const scores = this.bm25.scores(queryTokens);\n const validBundles = this.getValidBundleIds(accepted, conversationId);\n\n const effectiveThreshold = Math.max(\n EFFECTIVE_FLOOR,\n Math.min(THRESHOLDS.bm25, QUERY_TOKEN_SCALE * queryTokens.length),\n );\n telemetry.bm25Threshold = round4(effectiveThreshold);\n\n const picked: { score: number; item: ItemRecord }[] = [];\n const rejected: { score: number; payload: Record<string, unknown> }[] = [];\n\n for (let idx = 0; idx < scores.length; idx++) {\n const item = this.items[idx]!;\n const score = scores[idx]!;\n const reject = (reason: string) =>\n rejected.push({\n score,\n payload: {\n item_index: idx, bundle_id: item.bundleId, item_type: item.itemType,\n content_first_120: item.content.slice(0, PREVIEW_CHARS),\n bm25_score: round4(score), reason,\n },\n });\n if (score < effectiveThreshold) { reject('below_threshold'); continue; }\n if (!validBundles.has(item.bundleId)) { reject('scope_filter_excluded'); continue; }\n picked.push({ score, item });\n }\n\n rejected.sort((a, b) => b.score - a.score);\n telemetry.itemsRejected = rejected.slice(0, REJECTED_CAP).map((r) => r.payload);\n\n if (picked.length === 0) {\n return this.miss(telemetry, 'no_items_above_threshold');\n }\n\n picked.sort((a, b) => b.score - a.score);\n const top = picked.slice(0, maxItems);\n\n const pickedStems = new Set<string>();\n for (const { item } of top) for (const t of item.tokens) pickedStems.add(t);\n let overlap = 0;\n for (const s of uniqueStems) if (pickedStems.has(s)) overlap++;\n const coverage = uniqueStems.size ? overlap / uniqueStems.size : 1.0;\n telemetry.coverage = round4(coverage);\n\n // Observe-only unless explicitly configured. A malformed setting stays\n // observe-only rather than failing closed on every lookup.\n const coverageMin = getEnvFloat('SYNAP_SDK_CACHE_COVERAGE_MIN');\n if (coverageMin !== null && coverage < coverageMin) {\n // Gate BEFORE any side effect, so a rejected lookup leaves cache state\n // untouched and does not refresh a lease.\n return this.miss(telemetry, 'coverage_gate');\n }\n\n const itemsByType: Record<string, BundleItem[]> = {};\n const bundleIds = new Set<string>();\n for (const { item } of top) {\n (itemsByType[item.itemType] ??= []).push(item.itemDict);\n bundleIds.add(item.bundleId);\n }\n\n // Honouring a TTL hint also means a hit stops renewing the lease, otherwise\n // a hinted bundle under steady traffic would outlive its hint.\n const refreshOnHit = !getEnvFlag('SYNAP_SDK_CACHE_HONOR_TTL_HINT');\n if (refreshOnHit) {\n const now = this.now();\n for (const id of bundleIds) {\n const entry = this.entries.get(id);\n if (entry) entry.storedAt = now;\n }\n }\n\n telemetry.hit = true;\n telemetry.exitReason = 'hit';\n telemetry.itemsPicked = top.map(({ score, item }) => ({\n bundle_id: item.bundleId, item_type: item.itemType,\n content_first_120: item.content.slice(0, PREVIEW_CHARS), bm25_score: round4(score),\n }));\n this.fire(telemetry);\n\n return {\n itemsByType,\n bundleIds: [...bundleIds],\n score: top[0]!.score,\n coverage,\n };\n }\n\n /**\n * Drop this entity's bundles after a write, so the cache stops serving a\n * pre-write view. Gated on the flag: this is the write-path hook.\n */\n invalidateEntity(entityId: string): number {\n if (!getEnvFlag('SYNAP_SDK_CACHE_INVALIDATE_ON_WRITE')) return 0;\n return this.dropEntity(entityId);\n }\n\n /**\n * Unconditionally drop this entity's bundles. Backs `cache.clear_user` and\n * `cache.clear_customer`, which are explicit user requests and so are not\n * gated on the invalidate-on-write flag.\n */\n dropEntity(entityId: string): number {\n let dropped = 0;\n for (const entry of [...this.entries.values()]) {\n // Never drop shared client-scope knowledge on one entity's behalf.\n if (entry.entityId === ANY_SCOPE) continue;\n if (entry.entityId === entityId) { this.dropBundle(entry.bundleId); dropped++; }\n }\n return dropped;\n }\n\n /**\n * A read-only diagnostic projection of the cache.\n *\n * Backs `client.anticipation_cache_snapshot()` and mirrors Python's shape\n * key for key, including snake_case keys: this output gets logged, diffed\n * and pasted into issues across both SDKs, so it is a wire format.\n *\n * Note the 140-character content previews. That is Python's literal, and it\n * is deliberately NOT the 120 of `telemetry.content_preview_chars` from the\n * contract, which caps lookup telemetry rather than this snapshot.\n */\n snapshot(): AnticipationCacheSnapshot {\n const SNAPSHOT_PREVIEW_CHARS = 140;\n const overallScope = new Map<string, number>();\n const itemsByBundle = new Map<string, ItemRecord[]>();\n for (const record of this.items) {\n const list = itemsByBundle.get(record.bundleId);\n if (list === undefined) itemsByBundle.set(record.bundleId, [record]);\n else list.push(record);\n }\n\n const bundles: SnapshotBundle[] = [];\n for (const [bundleId, entry] of this.entries) {\n const perBundle = new Map<string, number>();\n const itemPreviews: SnapshotItemPreview[] = [];\n for (const record of itemsByBundle.get(bundleId) ?? []) {\n // `scope` is absent on plenty of items; Python's Counter happily keys\n // on None, which JSON-serialises to null, so preserve the distinction\n // rather than coercing to a string.\n const scope = (record.itemDict['scope'] ?? null) as string | null;\n const key = scope === null ? '' : scope;\n overallScope.set(key, (overallScope.get(key) ?? 0) + 1);\n perBundle.set(key, (perBundle.get(key) ?? 0) + 1);\n itemPreviews.push({\n type: record.itemType,\n scope,\n content: record.content.slice(0, SNAPSHOT_PREVIEW_CHARS),\n });\n }\n let totalItems = 0;\n for (const n of perBundle.values()) totalItems += n;\n bundles.push({\n bundle_id: bundleId,\n entity_id: entry.entityId,\n conversation_id: entry.conversationId,\n bundle_type: entry.bundleType,\n search_queries: [...entry.searchQueries],\n scope_counts: Object.fromEntries(perBundle),\n total_items: totalItems,\n items: itemPreviews,\n });\n }\n\n return {\n total_entries: this.entries.size,\n total_item_records: this.items.length,\n scope_breakdown_overall: Object.fromEntries(overallScope),\n corpus_vocab_size: this.corpusVocab.size,\n corpus_vocab_sample: [...this.corpusVocab].sort().slice(0, 80),\n item_records: this.items.slice(0, 20).map((rec) => ({\n bundle_id: rec.bundleId,\n item_type: rec.itemType,\n tokens: rec.tokens.slice(0, 25),\n content: rec.content.slice(0, SNAPSHOT_PREVIEW_CHARS),\n })),\n bundles,\n };\n }\n\n /**\n * Drop every bundle belonging to one conversation.\n *\n * Backs the `compaction_update` signal on the Listen stream: a compaction\n * rewrites the conversation's summary, so any bundle built from the previous\n * state is stale and must not keep serving for the rest of its TTL.\n *\n * Unlike `dropEntity`, client-scope bundles are NOT spared: a bundle is only\n * dropped here if it is bound to this specific conversation, and a shared\n * client-scope bundle has no conversation id to match.\n */\n dropConversation(conversationId: string): number {\n if (!conversationId) return 0;\n let dropped = 0;\n for (const entry of [...this.entries.values()]) {\n if (entry.conversationId === conversationId) { this.dropBundle(entry.bundleId); dropped++; }\n }\n return dropped;\n }\n\n clear(): void {\n this.entries.clear();\n this.items = [];\n this.corpusVocab.clear();\n this.bm25 = null;\n this.bm25Dirty = true;\n }\n\n // ── internals ───────────────────────────────────────────────────────────────\n\n private miss(telemetry: LookupTelemetry, reason: ExitReason): null {\n telemetry.exitReason = reason;\n telemetry.hit = false;\n this.fire(telemetry);\n return null;\n }\n\n private fire(telemetry: LookupTelemetry): void {\n // Exception-safe by contract: a buggy hook must never break the SDK.\n try {\n this.onLookup?.(telemetry);\n } catch {\n /* ignored on purpose */\n }\n }\n\n private freshnessLookup(\n entityId: string | null,\n maxItems: number,\n telemetry: LookupTelemetry,\n ): LookupResult | null {\n const candidates = [...this.entries.values()]\n .filter((e) => entityId === null || e.entityId === entityId || e.entityId === ANY_SCOPE)\n .sort((a, b) => b.storedAt - a.storedAt);\n if (candidates.length === 0) return this.miss(telemetry, 'empty');\n\n const newest = candidates[0]!;\n const itemsByType: Record<string, BundleItem[]> = {};\n let n = 0;\n for (const item of this.items) {\n if (item.bundleId !== newest.bundleId) continue;\n if (n >= maxItems) break;\n (itemsByType[item.itemType] ??= []).push(item.itemDict);\n n++;\n }\n if (n === 0) return this.miss(telemetry, 'empty');\n\n telemetry.hit = true;\n telemetry.exitReason = 'hit';\n this.fire(telemetry);\n return { itemsByType, bundleIds: [newest.bundleId], score: 0, coverage: 1.0 };\n }\n\n /**\n * The widened scope-match set for a request.\n *\n * A narrower-scope request also matches broader-scope bundles for the same\n * customer or client. Falsy ids are dropped so an empty customer_id cannot\n * accidentally match bundles keyed at \"\".\n */\n private buildAcceptedScope(\n entityId: string | null, customerId: string | null, clientId: string | null,\n ): Set<string> {\n const accepted = new Set<string>([ANY_SCOPE]);\n if (entityId) accepted.add(entityId);\n if (customerId) accepted.add(customerId);\n if (clientId) accepted.add(clientId);\n return accepted;\n }\n\n private getValidBundleIds(accepted: Set<string>, conversationId: string | null): Set<string> {\n const valid = new Set<string>();\n for (const entry of this.entries.values()) {\n if (!accepted.has(entry.entityId)) continue;\n // A conversation-scoped bundle is only valid inside its conversation.\n if (entry.conversationId && conversationId && entry.conversationId !== conversationId) continue;\n valid.add(entry.bundleId);\n }\n return valid;\n }\n\n private effectiveTtl(entry: EntryRecord): number {\n if (!getEnvFlag('SYNAP_SDK_CACHE_HONOR_TTL_HINT')) return this.ttlSeconds;\n if (entry.ttlHintSeconds == null || entry.ttlHintSeconds <= 0) return this.ttlSeconds;\n // A hint may only shorten.\n return Math.min(this.ttlSeconds, entry.ttlHintSeconds);\n }\n\n private evictExpired(): void {\n const now = this.now();\n // Default cap is twice the sliding TTL; 0 disables. Without it a bundle\n // under steady traffic renews forever and can serve a retired value\n // indefinitely.\n const configuredMaxAge = getEnvFloat('SYNAP_SDK_CACHE_MAX_ENTRY_AGE');\n const maxAge = configuredMaxAge ?? this.ttlSeconds * 2;\n\n for (const entry of [...this.entries.values()]) {\n const idleExpired = now - entry.storedAt > this.effectiveTtl(entry);\n const ageExpired = maxAge > 0 && now - entry.createdAt > maxAge;\n if (idleExpired || ageExpired) this.dropBundle(entry.bundleId);\n }\n }\n\n private dropBundle(bundleId: string): void {\n if (!this.entries.delete(bundleId)) return;\n this.items = this.items.filter((i) => i.bundleId !== bundleId);\n // Vocabulary is rebuilt rather than decremented: a stem can be shared by\n // several bundles, so per-bundle subtraction would drop stems still in use.\n this.corpusVocab = new Set(this.items.flatMap((i) => i.tokens));\n this.bm25Dirty = true;\n }\n}\n\nfunction monotonicNow(): number {\n // performance.now() is monotonic and unaffected by wall-clock adjustments,\n // matching Python's time.monotonic(). Date.now() would let an NTP step\n // expire or resurrect every entry at once.\n return typeof performance !== 'undefined' && typeof performance.now === 'function'\n ? performance.now() / 1000\n : Date.now() / 1000;\n}\n\nfunction round4(n: number): number {\n return Number(n.toFixed(4));\n}\n"]}
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
// src/util/env.ts
|
|
2
|
+
var TRUTHY = /* @__PURE__ */ new Set(["true", "1", "yes"]);
|
|
3
|
+
function readEnv(name) {
|
|
4
|
+
if (typeof process === "undefined" || process.env === void 0) return void 0;
|
|
5
|
+
return process.env[name];
|
|
6
|
+
}
|
|
7
|
+
function getEnvFlag(name, fallback = false) {
|
|
8
|
+
const raw = readEnv(name);
|
|
9
|
+
if (raw === void 0 || raw.trim() === "") return fallback;
|
|
10
|
+
return TRUTHY.has(raw.trim().toLowerCase());
|
|
11
|
+
}
|
|
12
|
+
function getEnvFloat(name) {
|
|
13
|
+
const raw = readEnv(name)?.trim();
|
|
14
|
+
if (!raw) return null;
|
|
15
|
+
const n = Number(raw);
|
|
16
|
+
return Number.isFinite(n) ? n : null;
|
|
17
|
+
}
|
|
18
|
+
function getEnv(name) {
|
|
19
|
+
const v = readEnv(name);
|
|
20
|
+
return v === void 0 || v === "" ? void 0 : v;
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
export {
|
|
24
|
+
getEnvFlag,
|
|
25
|
+
getEnvFloat,
|
|
26
|
+
getEnv
|
|
27
|
+
};
|
|
28
|
+
//# sourceMappingURL=chunk-QBCVMPGK.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../src/util/env.ts"],"sourcesContent":["/**\n * Environment access.\n *\n * Every read happens at CALL time, never at module load. Python does\n * `os.environ.get(...)` inside the function bodies, and tests plus runtime\n * toggles depend on that: a value captured at import time makes a later\n * `process.env` mutation look like the flag simply does not work. That is\n * gotcha G-S.\n *\n * `process` is absent on Workers and in the browser, so every accessor\n * tolerates it being missing.\n */\n\nconst TRUTHY = new Set(['true', '1', 'yes']);\n\nfunction readEnv(name: string): string | undefined {\n if (typeof process === 'undefined' || process.env === undefined) return undefined;\n return process.env[name];\n}\n\n/** Boolean flag. Defaults to false, matching the Python SDK's flags. */\nexport function getEnvFlag(name: string, fallback = false): boolean {\n const raw = readEnv(name);\n if (raw === undefined || raw.trim() === '') return fallback;\n return TRUTHY.has(raw.trim().toLowerCase());\n}\n\n/** Numeric setting. Returns null when unset OR malformed: a bad value must not fail closed. */\nexport function getEnvFloat(name: string): number | null {\n const raw = readEnv(name)?.trim();\n if (!raw) return null;\n const n = Number(raw);\n return Number.isFinite(n) ? n : null;\n}\n\nexport function getEnv(name: string): string | undefined {\n const v = readEnv(name);\n return v === undefined || v === '' ? undefined : v;\n}\n"],"mappings":";AAaA,IAAM,SAAS,oBAAI,IAAI,CAAC,QAAQ,KAAK,KAAK,CAAC;AAE3C,SAAS,QAAQ,MAAkC;AACjD,MAAI,OAAO,YAAY,eAAe,QAAQ,QAAQ,OAAW,QAAO;AACxE,SAAO,QAAQ,IAAI,IAAI;AACzB;AAGO,SAAS,WAAW,MAAc,WAAW,OAAgB;AAClE,QAAM,MAAM,QAAQ,IAAI;AACxB,MAAI,QAAQ,UAAa,IAAI,KAAK,MAAM,GAAI,QAAO;AACnD,SAAO,OAAO,IAAI,IAAI,KAAK,EAAE,YAAY,CAAC;AAC5C;AAGO,SAAS,YAAY,MAA6B;AACvD,QAAM,MAAM,QAAQ,IAAI,GAAG,KAAK;AAChC,MAAI,CAAC,IAAK,QAAO;AACjB,QAAM,IAAI,OAAO,GAAG;AACpB,SAAO,OAAO,SAAS,CAAC,IAAI,IAAI;AAClC;AAEO,SAAS,OAAO,MAAkC;AACvD,QAAM,IAAI,QAAQ,IAAI;AACtB,SAAO,MAAM,UAAa,MAAM,KAAK,SAAY;AACnD;","names":[]}
|
|
@@ -0,0 +1,172 @@
|
|
|
1
|
+
// src/errors.ts
|
|
2
|
+
var BRAND = /* @__PURE__ */ Symbol.for("@maximem/synap-js-sdk.SynapError");
|
|
3
|
+
var SynapError = class extends Error {
|
|
4
|
+
/**
|
|
5
|
+
* The single declaration site for each subclass's code.
|
|
6
|
+
*
|
|
7
|
+
* It is `static` rather than a class field on purpose. Under
|
|
8
|
+
* `useDefineForClassFields` (the default at our ES2022 target) a class field
|
|
9
|
+
* is an *instance* property, so it is invisible from the constructor object.
|
|
10
|
+
* `Symbol.hasInstance` below only has the constructor to work with, so a
|
|
11
|
+
* field would leave it unable to tell `AuthenticationError` from
|
|
12
|
+
* `RateLimitError` -- it would report every Synap error as an instance of
|
|
13
|
+
* every other one.
|
|
14
|
+
*/
|
|
15
|
+
static errorCode = "synap_error";
|
|
16
|
+
/** True for errors where a retry may succeed. Static for the same reason. */
|
|
17
|
+
static isTransient = false;
|
|
18
|
+
/** Own, enumerable, so logs and JSON.stringify include it. */
|
|
19
|
+
code;
|
|
20
|
+
correlationId;
|
|
21
|
+
transient;
|
|
22
|
+
constructor(message, options = {}) {
|
|
23
|
+
super(message, options.cause !== void 0 ? { cause: options.cause } : void 0);
|
|
24
|
+
const ctor = new.target;
|
|
25
|
+
this.name = new.target.name;
|
|
26
|
+
this.code = ctor.errorCode;
|
|
27
|
+
this.transient = ctor.isTransient;
|
|
28
|
+
this.correlationId = options.correlationId ?? null;
|
|
29
|
+
Object.defineProperty(this, BRAND, { value: true, enumerable: false });
|
|
30
|
+
Object.setPrototypeOf(this, new.target.prototype);
|
|
31
|
+
}
|
|
32
|
+
static [Symbol.hasInstance](instance) {
|
|
33
|
+
if (instance === null || typeof instance !== "object") return false;
|
|
34
|
+
if (!(BRAND in instance)) return false;
|
|
35
|
+
const expected = this.errorCode;
|
|
36
|
+
if (expected === void 0) return true;
|
|
37
|
+
if (expected === "synap_error") return true;
|
|
38
|
+
const actual = instance.code;
|
|
39
|
+
return actual === expected || descendsFrom(actual, expected);
|
|
40
|
+
}
|
|
41
|
+
};
|
|
42
|
+
function isSynapError(e) {
|
|
43
|
+
return typeof e === "object" && e !== null && BRAND in e;
|
|
44
|
+
}
|
|
45
|
+
var SynapTransientError = class extends SynapError {
|
|
46
|
+
static errorCode = "transient";
|
|
47
|
+
static isTransient = true;
|
|
48
|
+
};
|
|
49
|
+
var SynapPermanentError = class extends SynapError {
|
|
50
|
+
static errorCode = "permanent";
|
|
51
|
+
static isTransient = false;
|
|
52
|
+
};
|
|
53
|
+
var NetworkTimeoutError = class extends SynapTransientError {
|
|
54
|
+
static errorCode = "network_timeout";
|
|
55
|
+
};
|
|
56
|
+
var RateLimitError = class extends SynapTransientError {
|
|
57
|
+
static errorCode = "rate_limit";
|
|
58
|
+
retryAfterSeconds;
|
|
59
|
+
constructor(message, options = {}) {
|
|
60
|
+
super(message, options);
|
|
61
|
+
this.retryAfterSeconds = options.retryAfterSeconds ?? null;
|
|
62
|
+
}
|
|
63
|
+
};
|
|
64
|
+
var ServiceUnavailableError = class extends SynapTransientError {
|
|
65
|
+
static errorCode = "service_unavailable";
|
|
66
|
+
};
|
|
67
|
+
var AgentUnavailableError = class extends SynapTransientError {
|
|
68
|
+
static errorCode = "agent_unavailable";
|
|
69
|
+
constructor(message = "Agent unavailable", options = {}) {
|
|
70
|
+
super(message, options);
|
|
71
|
+
}
|
|
72
|
+
};
|
|
73
|
+
var InsufficientCreditsError = class extends SynapPermanentError {
|
|
74
|
+
static errorCode = "insufficient_credits";
|
|
75
|
+
balanceCredits;
|
|
76
|
+
requiredCredits;
|
|
77
|
+
constructor(message, options = {}) {
|
|
78
|
+
super(message, options);
|
|
79
|
+
this.balanceCredits = options.balanceCredits ?? null;
|
|
80
|
+
this.requiredCredits = options.requiredCredits ?? null;
|
|
81
|
+
}
|
|
82
|
+
};
|
|
83
|
+
var InvalidInputError = class extends SynapPermanentError {
|
|
84
|
+
static errorCode = "invalid_input";
|
|
85
|
+
};
|
|
86
|
+
var InvalidInstanceIdError = class extends InvalidInputError {
|
|
87
|
+
static errorCode = "invalid_instance_id";
|
|
88
|
+
};
|
|
89
|
+
var InvalidConversationIdError = class extends InvalidInputError {
|
|
90
|
+
static errorCode = "invalid_conversation_id";
|
|
91
|
+
};
|
|
92
|
+
var AuthenticationError = class extends SynapPermanentError {
|
|
93
|
+
static errorCode = "authentication";
|
|
94
|
+
};
|
|
95
|
+
var ContextNotFoundError = class extends SynapPermanentError {
|
|
96
|
+
static errorCode = "context_not_found";
|
|
97
|
+
};
|
|
98
|
+
var ConflictError = class extends SynapPermanentError {
|
|
99
|
+
static errorCode = "conflict";
|
|
100
|
+
};
|
|
101
|
+
var TranscriptConflictError = class extends ConflictError {
|
|
102
|
+
static errorCode = "transcript_conflict";
|
|
103
|
+
};
|
|
104
|
+
var SessionExpiredError = class extends SynapPermanentError {
|
|
105
|
+
static errorCode = "session_expired";
|
|
106
|
+
};
|
|
107
|
+
var ListeningAlreadyActiveError = class extends SynapPermanentError {
|
|
108
|
+
static errorCode = "listening_already_active";
|
|
109
|
+
};
|
|
110
|
+
var ListeningNotActiveError = class extends SynapPermanentError {
|
|
111
|
+
static errorCode = "listening_not_active";
|
|
112
|
+
};
|
|
113
|
+
var PARENT = {
|
|
114
|
+
transient: "synap_error",
|
|
115
|
+
permanent: "synap_error",
|
|
116
|
+
network_timeout: "transient",
|
|
117
|
+
rate_limit: "transient",
|
|
118
|
+
service_unavailable: "transient",
|
|
119
|
+
agent_unavailable: "transient",
|
|
120
|
+
insufficient_credits: "permanent",
|
|
121
|
+
invalid_input: "permanent",
|
|
122
|
+
invalid_instance_id: "invalid_input",
|
|
123
|
+
invalid_conversation_id: "invalid_input",
|
|
124
|
+
authentication: "permanent",
|
|
125
|
+
context_not_found: "permanent",
|
|
126
|
+
conflict: "permanent",
|
|
127
|
+
transcript_conflict: "conflict",
|
|
128
|
+
session_expired: "permanent",
|
|
129
|
+
listening_already_active: "permanent",
|
|
130
|
+
listening_not_active: "permanent"
|
|
131
|
+
};
|
|
132
|
+
function descendsFrom(actual, expected) {
|
|
133
|
+
let cur = actual;
|
|
134
|
+
const seen = /* @__PURE__ */ new Set();
|
|
135
|
+
while (cur && !seen.has(cur)) {
|
|
136
|
+
seen.add(cur);
|
|
137
|
+
if (cur === expected) return true;
|
|
138
|
+
cur = PARENT[cur];
|
|
139
|
+
}
|
|
140
|
+
return false;
|
|
141
|
+
}
|
|
142
|
+
var SDKError = SynapError;
|
|
143
|
+
var TransientError = SynapTransientError;
|
|
144
|
+
var PermanentError = SynapPermanentError;
|
|
145
|
+
var ConnectionError = NetworkTimeoutError;
|
|
146
|
+
|
|
147
|
+
export {
|
|
148
|
+
SynapError,
|
|
149
|
+
isSynapError,
|
|
150
|
+
SynapTransientError,
|
|
151
|
+
SynapPermanentError,
|
|
152
|
+
NetworkTimeoutError,
|
|
153
|
+
RateLimitError,
|
|
154
|
+
ServiceUnavailableError,
|
|
155
|
+
AgentUnavailableError,
|
|
156
|
+
InsufficientCreditsError,
|
|
157
|
+
InvalidInputError,
|
|
158
|
+
InvalidInstanceIdError,
|
|
159
|
+
InvalidConversationIdError,
|
|
160
|
+
AuthenticationError,
|
|
161
|
+
ContextNotFoundError,
|
|
162
|
+
ConflictError,
|
|
163
|
+
TranscriptConflictError,
|
|
164
|
+
SessionExpiredError,
|
|
165
|
+
ListeningAlreadyActiveError,
|
|
166
|
+
ListeningNotActiveError,
|
|
167
|
+
SDKError,
|
|
168
|
+
TransientError,
|
|
169
|
+
PermanentError,
|
|
170
|
+
ConnectionError
|
|
171
|
+
};
|
|
172
|
+
//# sourceMappingURL=chunk-T3NZBIV2.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../src/errors.ts"],"sourcesContent":["/**\n * Synap SDK error taxonomy.\n *\n * Mirrors `maximem_synap/models/errors.py` 1:1, including the four\n * backward-compatibility aliases at the bottom. If you add an error to one\n * SDK, add it to the other in the same change.\n *\n * ## Why every error carries a `.code`\n *\n * This package ships dual ESM + CJS. A consumer whose dependency graph pulls\n * in both formats gets *two* copies of every class in this file, and then:\n *\n * try { ... } catch (e) { if (e instanceof SynapError) { ... } }\n *\n * silently evaluates to `false` against the copy from the other format. Error\n * handling stops working and nothing throws to tell you. `.code` is a plain\n * string, so it is immune. Prefer it at package boundaries:\n *\n * if (isSynapError(e) && e.code === 'rate_limit') { ... }\n *\n * `Symbol.hasInstance` is also wired up on the base class, so `instanceof`\n * works across realms too -- but `.code` is the documented contract.\n */\n\n/** Stable, format-independent discriminators. Never renumber or reuse. */\nexport type SynapErrorCode =\n | 'synap_error'\n | 'transient'\n | 'permanent'\n | 'network_timeout'\n | 'rate_limit'\n | 'insufficient_credits'\n | 'service_unavailable'\n | 'invalid_input'\n | 'invalid_instance_id'\n | 'invalid_conversation_id'\n | 'authentication'\n | 'context_not_found'\n | 'conflict'\n | 'transcript_conflict'\n | 'session_expired'\n | 'listening_already_active'\n | 'listening_not_active'\n | 'agent_unavailable';\n\nconst BRAND = Symbol.for('@maximem/synap-js-sdk.SynapError');\n\nexport interface SynapErrorOptions {\n correlationId?: string | null;\n cause?: unknown;\n}\n\nexport class SynapError extends Error {\n /**\n * The single declaration site for each subclass's code.\n *\n * It is `static` rather than a class field on purpose. Under\n * `useDefineForClassFields` (the default at our ES2022 target) a class field\n * is an *instance* property, so it is invisible from the constructor object.\n * `Symbol.hasInstance` below only has the constructor to work with, so a\n * field would leave it unable to tell `AuthenticationError` from\n * `RateLimitError` -- it would report every Synap error as an instance of\n * every other one.\n */\n static readonly errorCode: SynapErrorCode = 'synap_error';\n /** True for errors where a retry may succeed. Static for the same reason. */\n static readonly isTransient: boolean = false;\n\n /** Own, enumerable, so logs and JSON.stringify include it. */\n readonly code: SynapErrorCode;\n readonly correlationId: string | null;\n readonly transient: boolean;\n\n constructor(message: string, options: SynapErrorOptions = {}) {\n super(message, options.cause !== undefined ? { cause: options.cause } : undefined);\n const ctor = new.target as typeof SynapError;\n this.name = new.target.name;\n this.code = ctor.errorCode;\n this.transient = ctor.isTransient;\n this.correlationId = options.correlationId ?? null;\n Object.defineProperty(this, BRAND, { value: true, enumerable: false });\n // Without this, subclassing a built-in under a downlevel target breaks the\n // prototype chain and `instanceof` fails even within a single copy.\n Object.setPrototypeOf(this, new.target.prototype);\n }\n\n static override [Symbol.hasInstance](instance: unknown): boolean {\n if (instance === null || typeof instance !== 'object') return false;\n // Cross-realm / dual-format tolerant: identify by brand, then narrow by the\n // subclass's own code so `e instanceof RateLimitError` stays meaningful.\n if (!(BRAND in instance)) return false;\n const expected = (this as unknown as { errorCode?: SynapErrorCode }).errorCode;\n // Called on something that is not one of our classes: fall back to the brand.\n if (expected === undefined) return true;\n // Everything branded descends from the root.\n if (expected === 'synap_error') return true;\n const actual = (instance as { code?: string }).code;\n return actual === expected || descendsFrom(actual, expected);\n }\n}\n\n/** Type guard that works across ESM/CJS copies and realms. */\nexport function isSynapError(e: unknown): e is SynapError {\n return typeof e === 'object' && e !== null && BRAND in e;\n}\n\nexport class SynapTransientError extends SynapError {\n static override readonly errorCode: SynapErrorCode = 'transient';\n static override readonly isTransient: boolean = true;\n}\n\nexport class SynapPermanentError extends SynapError {\n static override readonly errorCode: SynapErrorCode = 'permanent';\n static override readonly isTransient: boolean = false;\n}\n\n// ─── Transient ────────────────────────────────────────────────────────────────\n\nexport class NetworkTimeoutError extends SynapTransientError {\n static override readonly errorCode: SynapErrorCode = 'network_timeout';\n}\n\nexport class RateLimitError extends SynapTransientError {\n static override readonly errorCode: SynapErrorCode = 'rate_limit';\n readonly retryAfterSeconds: number | null;\n\n constructor(\n message: string,\n options: SynapErrorOptions & { retryAfterSeconds?: number | null } = {},\n ) {\n super(message, options);\n this.retryAfterSeconds = options.retryAfterSeconds ?? null;\n }\n}\n\nexport class ServiceUnavailableError extends SynapTransientError {\n static override readonly errorCode: SynapErrorCode = 'service_unavailable';\n}\n\nexport class AgentUnavailableError extends SynapTransientError {\n static override readonly errorCode: SynapErrorCode = 'agent_unavailable';\n constructor(message = 'Agent unavailable', options: SynapErrorOptions = {}) {\n super(message, options);\n }\n}\n\n// ─── Permanent ────────────────────────────────────────────────────────────────\n\n/**\n * The caller's credit wallet cannot cover this request.\n *\n * HTTP 402, and gRPC RESOURCE_EXHAUSTED with credit-related trailing metadata.\n * Permanent by design: retrying without topping up burns quota and never\n * succeeds. This is the error behind \"the agent forgot\" reports where retrieval\n * silently returns nothing.\n */\nexport class InsufficientCreditsError extends SynapPermanentError {\n static override readonly errorCode: SynapErrorCode = 'insufficient_credits';\n readonly balanceCredits: number | null;\n readonly requiredCredits: number | null;\n\n constructor(\n message: string,\n options: SynapErrorOptions & {\n balanceCredits?: number | null;\n requiredCredits?: number | null;\n } = {},\n ) {\n super(message, options);\n this.balanceCredits = options.balanceCredits ?? null;\n this.requiredCredits = options.requiredCredits ?? null;\n }\n}\n\nexport class InvalidInputError extends SynapPermanentError {\n static override readonly errorCode: SynapErrorCode = 'invalid_input';\n}\n\n/**\n * Raised by `validateInstanceId` before any network call, matching Python's\n * `utils/validators.py`. The message text is identical in both SDKs.\n */\nexport class InvalidInstanceIdError extends InvalidInputError {\n static override readonly errorCode: SynapErrorCode = 'invalid_instance_id';\n}\n\n/** See the note on InvalidInstanceIdError. Raised by `validateConversationId`. */\nexport class InvalidConversationIdError extends InvalidInputError {\n static override readonly errorCode: SynapErrorCode = 'invalid_conversation_id';\n}\n\nexport class AuthenticationError extends SynapPermanentError {\n static override readonly errorCode: SynapErrorCode = 'authentication';\n}\n\nexport class ContextNotFoundError extends SynapPermanentError {\n static override readonly errorCode: SynapErrorCode = 'context_not_found';\n}\n\nexport class ConflictError extends SynapPermanentError {\n static override readonly errorCode: SynapErrorCode = 'conflict';\n}\n\nexport class TranscriptConflictError extends ConflictError {\n static override readonly errorCode: SynapErrorCode = 'transcript_conflict';\n}\n\nexport class SessionExpiredError extends SynapPermanentError {\n static override readonly errorCode: SynapErrorCode = 'session_expired';\n}\n\nexport class ListeningAlreadyActiveError extends SynapPermanentError {\n static override readonly errorCode: SynapErrorCode = 'listening_already_active';\n}\n\nexport class ListeningNotActiveError extends SynapPermanentError {\n static override readonly errorCode: SynapErrorCode = 'listening_not_active';\n}\n\n// ─── Hierarchy metadata (drives the cross-copy instanceof above) ──────────────\n\nconst PARENT: Partial<Record<SynapErrorCode, SynapErrorCode>> = {\n transient: 'synap_error',\n permanent: 'synap_error',\n network_timeout: 'transient',\n rate_limit: 'transient',\n service_unavailable: 'transient',\n agent_unavailable: 'transient',\n insufficient_credits: 'permanent',\n invalid_input: 'permanent',\n invalid_instance_id: 'invalid_input',\n invalid_conversation_id: 'invalid_input',\n authentication: 'permanent',\n context_not_found: 'permanent',\n conflict: 'permanent',\n transcript_conflict: 'conflict',\n session_expired: 'permanent',\n listening_already_active: 'permanent',\n listening_not_active: 'permanent',\n};\n\nfunction descendsFrom(actual: string | undefined, expected: string): boolean {\n let cur = actual as SynapErrorCode | undefined;\n const seen = new Set<string>();\n while (cur && !seen.has(cur)) {\n seen.add(cur);\n if (cur === expected) return true;\n cur = PARENT[cur];\n }\n return false;\n}\n\n// ─── Backward-compatibility aliases (mirrors the tail of errors.py) ──────────\n// `ConnectionError` deliberately shadows the global in a module scope. Python\n// does the same thing; keeping the name means ported code reads identically.\n\nexport const SDKError = SynapError;\nexport const TransientError = SynapTransientError;\nexport const PermanentError = SynapPermanentError;\nexport const ConnectionError = NetworkTimeoutError;\n"],"mappings":"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","names":[]}
|