@jungjaehoon/mama-core 1.9.0 → 2.1.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.
Files changed (139) hide show
  1. package/db/migrations/043-add-tool-trace-failure-code.sql +11 -0
  2. package/dist/agent-graph/alias-write.js +3 -0
  3. package/dist/agent-graph/entity-resolve.js +3 -7
  4. package/dist/agent-graph/graph-query.js +5 -4
  5. package/dist/agent-graph/types.d.ts +30 -0
  6. package/dist/cases/store.d.ts +0 -4
  7. package/dist/cases/store.js +0 -66
  8. package/dist/cases/wiki-page-index.d.ts +0 -13
  9. package/dist/cases/wiki-page-index.js +0 -153
  10. package/dist/connectors/event-index.d.ts +1 -22
  11. package/dist/connectors/event-index.js +0 -157
  12. package/dist/context-compile/channel-grant.d.ts +46 -0
  13. package/dist/context-compile/channel-grant.js +66 -0
  14. package/dist/context-compile/compiler.js +5 -2
  15. package/dist/context-compile/index.d.ts +1 -0
  16. package/dist/context-compile/index.js +1 -0
  17. package/dist/context-compile/packet-store.d.ts +0 -1
  18. package/dist/context-compile/packet-store.js +0 -16
  19. package/dist/context-compile/source-readers.d.ts +1 -0
  20. package/dist/context-compile/source-readers.js +156 -23
  21. package/dist/context-compile/types.d.ts +17 -0
  22. package/dist/context-compile/visibility.js +28 -4
  23. package/dist/db-adapter/node-sqlite-adapter.js +4 -0
  24. package/dist/db-manager.d.ts +0 -13
  25. package/dist/db-manager.js +0 -66
  26. package/dist/decision-formatter.d.ts +0 -11
  27. package/dist/decision-formatter.js +0 -122
  28. package/dist/decision-tracker.d.ts +0 -12
  29. package/dist/decision-tracker.js +0 -50
  30. package/dist/edges/ref-validation.d.ts +1 -2
  31. package/dist/edges/ref-validation.js +33 -13
  32. package/dist/edges/store.d.ts +1 -3
  33. package/dist/edges/store.js +0 -214
  34. package/dist/edges/types.d.ts +10 -0
  35. package/dist/embedding-client.d.ts +0 -17
  36. package/dist/embedding-client.js +0 -80
  37. package/dist/embedding-server/mobile/auth.d.ts +1 -10
  38. package/dist/embedding-server/mobile/auth.js +0 -15
  39. package/dist/embeddings.d.ts +0 -12
  40. package/dist/embeddings.js +0 -68
  41. package/dist/entities/audit-metrics.d.ts +0 -5
  42. package/dist/entities/audit-metrics.js +0 -4
  43. package/dist/entities/candidate-generator.d.ts +1 -2
  44. package/dist/entities/candidate-generator.js +0 -412
  45. package/dist/entities/entity-list.d.ts +0 -1
  46. package/dist/entities/entity-list.js +0 -96
  47. package/dist/entities/entity-orphan-list.d.ts +0 -9
  48. package/dist/entities/entity-orphan-list.js +0 -88
  49. package/dist/entities/entity-search.d.ts +0 -1
  50. package/dist/entities/entity-search.js +0 -147
  51. package/dist/entities/errors.d.ts +0 -10
  52. package/dist/entities/errors.js +1 -25
  53. package/dist/entities/lineage-store.d.ts +0 -23
  54. package/dist/entities/lineage-store.js +0 -104
  55. package/dist/entities/policy-store.d.ts +0 -9
  56. package/dist/entities/policy-store.js +0 -188
  57. package/dist/entities/provenance-query.d.ts +0 -1
  58. package/dist/entities/provenance-query.js +0 -164
  59. package/dist/entities/resolution-engine.d.ts +1 -8
  60. package/dist/entities/resolution-engine.js +0 -66
  61. package/dist/entities/rollback-preview.d.ts +0 -4
  62. package/dist/entities/rollback-preview.js +0 -232
  63. package/dist/entities/store.d.ts +1 -10
  64. package/dist/entities/store.js +0 -49
  65. package/dist/index.d.ts +15 -31
  66. package/dist/index.js +4 -46
  67. package/dist/mama-api.d.ts +19 -1
  68. package/dist/mama-api.js +97 -2
  69. package/dist/memory/api.d.ts +8 -0
  70. package/dist/memory/api.js +55 -2
  71. package/dist/memory/event-store.d.ts +0 -1
  72. package/dist/memory/event-store.js +0 -15
  73. package/dist/memory/finding-store.d.ts +0 -1
  74. package/dist/memory/finding-store.js +0 -12
  75. package/dist/memory/scope-backfill.d.ts +0 -3
  76. package/dist/memory/scope-backfill.js +0 -74
  77. package/dist/memory/scope-store.d.ts +0 -1
  78. package/dist/memory/scope-store.js +0 -4
  79. package/dist/memory/truth-store.d.ts +0 -3
  80. package/dist/memory/truth-store.js +0 -22
  81. package/dist/memory/types.d.ts +0 -1
  82. package/dist/memory/types.js +0 -13
  83. package/dist/memory-store.d.ts +0 -16
  84. package/dist/memory-store.js +0 -51
  85. package/dist/model-runs/tool-trace-store.js +9 -5
  86. package/dist/model-runs/types.d.ts +3 -0
  87. package/dist/ollama-client.d.ts +0 -9
  88. package/dist/ollama-client.js +0 -125
  89. package/dist/outcome-tracker.d.ts +0 -14
  90. package/dist/outcome-tracker.js +0 -44
  91. package/dist/progress-indicator.d.ts +0 -4
  92. package/dist/progress-indicator.js +0 -7
  93. package/dist/provenance/source-ref.d.ts +0 -9
  94. package/dist/provenance/source-ref.js +0 -145
  95. package/dist/query-intent.d.ts +0 -4
  96. package/dist/query-intent.js +0 -30
  97. package/dist/relevance-scorer.d.ts +0 -9
  98. package/dist/relevance-scorer.js +0 -81
  99. package/dist/search/feedback-store.d.ts +0 -1
  100. package/dist/search/feedback-store.js +0 -4
  101. package/dist/search/ranker-rescore.d.ts +0 -3
  102. package/dist/search/ranker-rescore.js +0 -27
  103. package/dist/search/ranker-trainer.d.ts +0 -8
  104. package/dist/search/ranker-trainer.js +0 -376
  105. package/dist/tier-validator.d.ts +0 -12
  106. package/dist/tier-validator.js +0 -56
  107. package/package.json +1 -10
  108. package/dist/cases/case-links.d.ts +0 -116
  109. package/dist/cases/case-links.js +0 -794
  110. package/dist/cases/composition-overrides.d.ts +0 -90
  111. package/dist/cases/composition-overrides.js +0 -724
  112. package/dist/cases/corrections.d.ts +0 -156
  113. package/dist/cases/corrections.js +0 -1045
  114. package/dist/cases/freshness.d.ts +0 -57
  115. package/dist/cases/freshness.js +0 -283
  116. package/dist/cases/live-state.d.ts +0 -48
  117. package/dist/cases/live-state.js +0 -256
  118. package/dist/cases/membership-explain.d.ts +0 -56
  119. package/dist/cases/membership-explain.js +0 -140
  120. package/dist/cases/membership-matcher.d.ts +0 -23
  121. package/dist/cases/membership-matcher.js +0 -193
  122. package/dist/cases/merge-split.d.ts +0 -61
  123. package/dist/cases/merge-split.js +0 -368
  124. package/dist/cases/role-inference.d.ts +0 -10
  125. package/dist/cases/role-inference.js +0 -85
  126. package/dist/cases/sqlite-transaction.d.ts +0 -10
  127. package/dist/cases/sqlite-transaction.js +0 -62
  128. package/dist/cases/target-ref.d.ts +0 -25
  129. package/dist/cases/target-ref.js +0 -22
  130. package/dist/cases/tombstone-sweeper.d.ts +0 -13
  131. package/dist/cases/tombstone-sweeper.js +0 -128
  132. package/dist/entities/entity-impact.d.ts +0 -41
  133. package/dist/entities/entity-impact.js +0 -140
  134. package/dist/entities/exact-merge-backfill.d.ts +0 -11
  135. package/dist/entities/exact-merge-backfill.js +0 -161
  136. package/dist/entities/lineage-backfill.d.ts +0 -12
  137. package/dist/entities/lineage-backfill.js +0 -101
  138. package/dist/memory-inject.d.ts +0 -24
  139. package/dist/memory-inject.js +0 -116
@@ -0,0 +1,11 @@
1
+ -- Migration 043: tool_traces.failure_code — carry the thrower's closed cause.
2
+ --
3
+ -- The failure choke already emits a structured code (envelope_missing,
4
+ -- context_compile_scope_denied, ...) and the sanitizer explicitly preserves
5
+ -- it; the trace INSERT was the one place that dropped it, leaving only
6
+ -- `gateway_tool_failed;sha256=...` digests (measured 2026-07-30: the dominant
7
+ -- digest covered 52% of 2,460 context_compile failures with no name).
8
+ -- Nullable on purpose: a failure without a code stays NULL — labels are
9
+ -- carried, never invented.
10
+
11
+ ALTER TABLE tool_traces ADD COLUMN failure_code TEXT;
@@ -191,6 +191,9 @@ function attachEntityAliasWithEdge(adapter, input) {
191
191
  connectors: input.connectors,
192
192
  projectRefs: input.project_refs,
193
193
  tenantId: input.tenant_id,
194
+ // source_refs are caller-supplied, so this is the surface where naming a raw id from
195
+ // an ungranted channel would bind it to an entity the caller can read back.
196
+ ...(input.channels ? { channels: input.channels } : {}),
194
197
  };
195
198
  const sourceRefs = normalizeSourceRefs(input.source_refs);
196
199
  if (sourceRefs.length === 0) {
@@ -168,13 +168,8 @@ function contextBoost(adapter, entityId, contextRefs, visibility, asOfMs) {
168
168
  if (!contextRefs || contextRefs.length === 0) {
169
169
  return 0;
170
170
  }
171
- const edges = (0, ref_validation_js_1.listVisibleTwinEdgesForRefs)(adapter, contextRefs, {
172
- scopes: visibility.scopes,
173
- connectors: visibility.connectors,
174
- projectRefs: visibility.projectRefs,
175
- tenantId: visibility.tenantId,
176
- asOfMs,
177
- });
171
+ // Spread rather than re-list: see graph-query's listFilteredEdges.
172
+ const edges = (0, ref_validation_js_1.listVisibleTwinEdgesForRefs)(adapter, contextRefs, { ...visibility, asOfMs });
178
173
  return edges.some((edge) => (edge.subject_ref.kind === 'entity' && edge.subject_ref.id === entityId) ||
179
174
  (edge.object_ref.kind === 'entity' && edge.object_ref.id === entityId))
180
175
  ? 0.2
@@ -189,6 +184,7 @@ function resolveEntity(adapter, input) {
189
184
  projectRefs: input.project_refs,
190
185
  tenantId: input.tenant_id,
191
186
  asOfMs: input.as_of_ms,
187
+ ...(input.channels ? { channels: input.channels } : {}),
192
188
  };
193
189
  if (input.context_refs && input.context_refs.length > 0) {
194
190
  try {
@@ -80,11 +80,11 @@ function oppositeRef(edge, current) {
80
80
  return refs;
81
81
  }
82
82
  function listFilteredEdges(adapter, refs, input) {
83
+ // Spread, not a field-by-field re-listing. Re-listing is how the channel grant was
84
+ // silently dropped here while every other path enforced it: a new field on the
85
+ // visibility type simply never arrived, and nothing failed to say so.
83
86
  return (0, ref_validation_js_1.listVisibleTwinEdgesForRefs)(adapter, refs, {
84
- scopes: input.visibility.scopes,
85
- connectors: input.visibility.connectors,
86
- projectRefs: input.visibility.projectRefs,
87
- tenantId: input.visibility.tenantId,
87
+ ...input.visibility,
88
88
  edgeTypes: input.edge_filters?.edge_types,
89
89
  asOfMs: input.as_of_ms,
90
90
  limit: input.limit,
@@ -104,6 +104,7 @@ function graphVisibility(input) {
104
104
  connectors: input.connectors,
105
105
  projectRefs: input.project_refs,
106
106
  tenantId: input.tenant_id,
107
+ ...(input.channels ? { channels: input.channels } : {}),
107
108
  };
108
109
  }
109
110
  function numberMs(value, field, refId) {
@@ -10,6 +10,12 @@ export interface ResolveEntityInput {
10
10
  scopes?: TwinScopeRef[];
11
11
  connectors?: string[];
12
12
  project_refs?: TwinProjectRef[];
13
+ /**
14
+ * Which channels of each connector may be read. Carried on every graph input for the
15
+ * same reason it is carried on the reader's boundary: a raw ref reached through an edge
16
+ * must satisfy the same rule as a row the reader would have returned.
17
+ */
18
+ channels?: Record<string, readonly string[]>;
13
19
  tenant_id?: string | null;
14
20
  context_refs?: TwinRef[];
15
21
  limit?: number;
@@ -31,6 +37,12 @@ export interface GraphNeighborhoodInput {
31
37
  scopes?: TwinScopeRef[];
32
38
  connectors?: string[];
33
39
  project_refs?: TwinProjectRef[];
40
+ /**
41
+ * Which channels of each connector may be read. Carried on every graph input for the
42
+ * same reason it is carried on the reader's boundary: a raw ref reached through an edge
43
+ * must satisfy the same rule as a row the reader would have returned.
44
+ */
45
+ channels?: Record<string, readonly string[]>;
34
46
  tenant_id?: string | null;
35
47
  edge_filters?: AgentGraphEdgeFilters;
36
48
  as_of_ms?: number | null;
@@ -47,6 +59,12 @@ export interface GraphPathsInput {
47
59
  scopes?: TwinScopeRef[];
48
60
  connectors?: string[];
49
61
  project_refs?: TwinProjectRef[];
62
+ /**
63
+ * Which channels of each connector may be read. Carried on every graph input for the
64
+ * same reason it is carried on the reader's boundary: a raw ref reached through an edge
65
+ * must satisfy the same rule as a row the reader would have returned.
66
+ */
67
+ channels?: Record<string, readonly string[]>;
50
68
  tenant_id?: string | null;
51
69
  edge_filters?: AgentGraphEdgeFilters;
52
70
  as_of_ms?: number | null;
@@ -64,6 +82,12 @@ export interface GraphTimelineInput {
64
82
  scopes?: TwinScopeRef[];
65
83
  connectors?: string[];
66
84
  project_refs?: TwinProjectRef[];
85
+ /**
86
+ * Which channels of each connector may be read. Carried on every graph input for the
87
+ * same reason it is carried on the reader's boundary: a raw ref reached through an edge
88
+ * must satisfy the same rule as a row the reader would have returned.
89
+ */
90
+ channels?: Record<string, readonly string[]>;
67
91
  tenant_id?: string | null;
68
92
  edge_filters?: AgentGraphEdgeFilters;
69
93
  from_ms?: number;
@@ -153,6 +177,12 @@ export interface AttachEntityAliasWithEdgeInput {
153
177
  scopes?: TwinScopeRef[];
154
178
  connectors?: string[];
155
179
  project_refs?: TwinProjectRef[];
180
+ /**
181
+ * Which channels of each connector may be read. Carried on every graph input for the
182
+ * same reason it is carried on the reader's boundary: a raw ref reached through an edge
183
+ * must satisfy the same rule as a row the reader would have returned.
184
+ */
185
+ channels?: Record<string, readonly string[]>;
156
186
  tenant_id?: string | null;
157
187
  }
158
188
  export interface AttachEntityAliasWithEdgeResult {
@@ -63,10 +63,6 @@ export interface ListActiveCorrectionsForCaseResult {
63
63
  */
64
64
  export declare function listActiveCorrectionsForCase(adapter: CaseStoreAdapter, caseId: string): ListActiveCorrectionsForCaseResult;
65
65
  export declare function listActiveCorrectionsForCaseChain(adapter: CaseStoreAdapter, caseIds: string[]): CaseCorrectionRecord[];
66
- export declare function enqueueCaseProposal(adapter: CaseStoreAdapter, input: EnqueueCaseProposalInput): {
67
- proposal_id: string;
68
- inserted: boolean;
69
- };
70
66
  export declare function listUnresolvedCaseProposals(adapter: CaseStoreAdapter, project: string): CaseProposalQueueRecord[];
71
67
  export declare function assembleCase(caseId: string, options?: AssembleCaseOptions): CaseAssembly;
72
68
  export declare function assembleCase(adapter: CaseStoreAdapter, caseId: string, options?: AssembleCaseOptions): CaseAssembly;
@@ -7,11 +7,8 @@ exports.upsertExplicitCaseMemberships = upsertExplicitCaseMemberships;
7
7
  exports.listActiveMembershipsForCaseChain = listActiveMembershipsForCaseChain;
8
8
  exports.listActiveCorrectionsForCase = listActiveCorrectionsForCase;
9
9
  exports.listActiveCorrectionsForCaseChain = listActiveCorrectionsForCaseChain;
10
- exports.enqueueCaseProposal = enqueueCaseProposal;
11
10
  exports.listUnresolvedCaseProposals = listUnresolvedCaseProposals;
12
11
  exports.assembleCase = assembleCase;
13
- const node_crypto_1 = require("node:crypto");
14
- const canonicalize_js_1 = require("../canonicalize.js");
15
12
  const db_manager_js_1 = require("../db-manager.js");
16
13
  const errors_js_1 = require("../entities/errors.js");
17
14
  function isAdapter(value) {
@@ -447,69 +444,6 @@ function listActiveCorrectionsForCaseChain(adapter, caseIds) {
447
444
  .all(...caseIds);
448
445
  return rows.map(mapCaseCorrectionRow);
449
446
  }
450
- function isUniqueConstraintError(error) {
451
- if (!(error instanceof Error)) {
452
- return false;
453
- }
454
- return /UNIQUE constraint|SQLITE_CONSTRAINT_UNIQUE/i.test(error.message);
455
- }
456
- function findExistingProposalId(adapter, input, payloadFingerprint) {
457
- const row = adapter
458
- .prepare(`
459
- SELECT proposal_id
460
- FROM case_proposal_queue
461
- WHERE project = ?
462
- AND proposal_kind = ?
463
- AND COALESCE(conflicting_case_id, '') = ?
464
- AND payload_fingerprint = ?
465
- AND resolved_at IS NULL
466
- LIMIT 1
467
- `)
468
- .get(input.project, input.proposal_kind, input.conflicting_case_id ?? '', payloadFingerprint);
469
- return row?.proposal_id ?? null;
470
- }
471
- function enqueueCaseProposal(adapter, input) {
472
- const canonicalFingerprintInput = (0, canonicalize_js_1.canonicalizeJSON)(input.stable_fingerprint_input);
473
- const payloadFingerprint = (0, canonicalize_js_1.targetRefHashCanonicalJSON)(canonicalFingerprintInput);
474
- const proposalId = (0, node_crypto_1.randomUUID)();
475
- const detectedAt = nowIso();
476
- return adapter.transaction(() => {
477
- try {
478
- adapter
479
- .prepare(`
480
- INSERT INTO case_proposal_queue (
481
- proposal_id, project, proposal_kind, proposed_payload, payload_fingerprint,
482
- conflicting_case_id, detected_at, resolved_at, resolution, resolution_note
483
- )
484
- VALUES (?, ?, ?, ?, ?, ?, ?, NULL, NULL, NULL)
485
- `)
486
- .run(proposalId, input.project, input.proposal_kind, input.proposed_payload, payloadFingerprint, input.conflicting_case_id ?? null, detectedAt);
487
- return { proposal_id: proposalId, inserted: true };
488
- }
489
- catch (error) {
490
- if (!isUniqueConstraintError(error)) {
491
- throw error;
492
- }
493
- const existingId = findExistingProposalId(adapter, input, payloadFingerprint);
494
- if (!existingId) {
495
- throw error;
496
- }
497
- // Spec §5.7 L355: re-detection updates detected_at without duplicating.
498
- // Keeps listUnresolvedCaseProposals ordering (ASC detected_at) honest —
499
- // recently re-detected rows move to the tail instead of sitting at
500
- // stale timestamps.
501
- adapter
502
- .prepare(`
503
- UPDATE case_proposal_queue
504
- SET detected_at = ?
505
- WHERE proposal_id = ?
506
- AND resolved_at IS NULL
507
- `)
508
- .run(detectedAt, existingId);
509
- return { proposal_id: existingId, inserted: false };
510
- }
511
- });
512
- }
513
447
  function listUnresolvedCaseProposals(adapter, project) {
514
448
  const rows = adapter
515
449
  .prepare(`
@@ -32,19 +32,6 @@ export interface UpsertWikiPageIndexInput {
32
32
  embedding?: Float32Array | null;
33
33
  embedding_model?: string;
34
34
  }
35
- export declare function upsertWikiPageIndexEntry(adapter: AdapterLike, input: UpsertWikiPageIndexInput): {
36
- id: number;
37
- created: boolean;
38
- };
39
- export declare function deleteWikiPageIndexEntry(adapter: AdapterLike, source_locator: string): {
40
- deleted: boolean;
41
- };
42
35
  export declare function ftsSearchWikiPages(adapter: AdapterLike, query: string, limit: number): WikiPageSearchHit[];
43
36
  export declare function vectorSearchWikiPages(adapter: AdapterLike, queryEmbedding: Float32Array, limit: number): WikiPageSearchHit[];
44
- export declare function searchWikiPages(input: {
45
- adapter: AdapterLike;
46
- query: string;
47
- queryEmbedding?: Float32Array | null;
48
- limit: number;
49
- }): WikiPageSearchHit[];
50
37
  //# sourceMappingURL=wiki-page-index.d.ts.map
@@ -1,14 +1,7 @@
1
1
  "use strict";
2
- var __importDefault = (this && this.__importDefault) || function (mod) {
3
- return (mod && mod.__esModule) ? mod : { "default": mod };
4
- };
5
2
  Object.defineProperty(exports, "__esModule", { value: true });
6
- exports.upsertWikiPageIndexEntry = upsertWikiPageIndexEntry;
7
- exports.deleteWikiPageIndexEntry = deleteWikiPageIndexEntry;
8
3
  exports.ftsSearchWikiPages = ftsSearchWikiPages;
9
4
  exports.vectorSearchWikiPages = vectorSearchWikiPages;
10
- exports.searchWikiPages = searchWikiPages;
11
- const node_crypto_1 = __importDefault(require("node:crypto"));
12
5
  const embeddings_js_1 = require("../embeddings.js");
13
6
  function tableColumns(adapter, tableName) {
14
7
  const rows = adapter.prepare(`PRAGMA table_info(${tableName})`).all();
@@ -34,19 +27,12 @@ function readSchema(adapter) {
34
27
  embeddingHasCreatedAt: embeddingColumns.has('created_at'),
35
28
  };
36
29
  }
37
- function nowIso() {
38
- return new Date().toISOString();
39
- }
40
30
  function normalizeLimit(limit) {
41
31
  if (!Number.isFinite(limit)) {
42
32
  return 10;
43
33
  }
44
34
  return Math.max(0, Math.floor(limit));
45
35
  }
46
- function pageIdForSourceLocator(sourceLocator) {
47
- const digest = node_crypto_1.default.createHash('sha256').update(sourceLocator).digest('hex').slice(0, 24);
48
- return `wiki_page_${digest}`;
49
- }
50
36
  function parseJsonArray(value) {
51
37
  if (value === null || value === undefined || value === '') {
52
38
  return [];
@@ -89,13 +75,6 @@ function rowToRecord(row) {
89
75
  updated_at: String(row.updated_at ?? row.created_at ?? row.compiled_at ?? ''),
90
76
  };
91
77
  }
92
- function selectByLocator(adapter, schema, sourceLocator) {
93
- const sql = schema.hasIdColumn
94
- ? 'SELECT * FROM wiki_page_index WHERE source_locator = ?'
95
- : 'SELECT rowid AS id, * FROM wiki_page_index WHERE source_locator = ?';
96
- const row = adapter.prepare(sql).get(sourceLocator);
97
- return row ? rowToRecord(row) : null;
98
- }
99
78
  function selectByFtsPageId(adapter, schema, pageId) {
100
79
  const sql = schema.hasIdColumn
101
80
  ? 'SELECT * FROM wiki_page_index WHERE id = ?'
@@ -104,9 +83,6 @@ function selectByFtsPageId(adapter, schema, pageId) {
104
83
  const row = adapter.prepare(sql).get(lookup);
105
84
  return row ? rowToRecord(row) : null;
106
85
  }
107
- function vectorToBuffer(embedding) {
108
- return Buffer.from(embedding.buffer, embedding.byteOffset, embedding.byteLength);
109
- }
110
86
  function blobToVector(value) {
111
87
  if (!(value instanceof Uint8Array)) {
112
88
  return null;
@@ -118,35 +94,6 @@ function blobToVector(value) {
118
94
  const arrayBuffer = buffer.buffer.slice(buffer.byteOffset, buffer.byteOffset + buffer.byteLength);
119
95
  return new Float32Array(arrayBuffer);
120
96
  }
121
- function upsertEmbedding(adapter, schema, record, input) {
122
- if (!input.embedding) {
123
- return;
124
- }
125
- const vector = vectorToBuffer(input.embedding);
126
- const model = input.embedding_model ?? embeddings_js_1.MODEL_NAME;
127
- const dim = input.embedding.length;
128
- if (schema.embeddingUsesWikiPageId && schema.embeddingUsesVector) {
129
- adapter
130
- .prepare(`
131
- INSERT INTO wiki_page_embeddings(wiki_page_id, vector, model, dim, created_at)
132
- VALUES (?, ?, ?, ?, ?)
133
- ON CONFLICT(wiki_page_id) DO UPDATE SET
134
- vector = excluded.vector,
135
- model = excluded.model,
136
- dim = excluded.dim
137
- `)
138
- .run(record.id, vector, model, dim, nowIso());
139
- return;
140
- }
141
- adapter
142
- .prepare(`
143
- INSERT INTO wiki_page_embeddings(page_id, embedding)
144
- VALUES (?, ?)
145
- ON CONFLICT(page_id) DO UPDATE SET
146
- embedding = excluded.embedding
147
- `)
148
- .run(pageIdForSourceLocator(record.source_locator), vector);
149
- }
150
97
  function buildFtsQuery(query) {
151
98
  const tokens = query
152
99
  .toLowerCase()
@@ -173,89 +120,6 @@ function searchTableExists(adapter, tableName) {
173
120
  .get(tableName);
174
121
  return row !== undefined;
175
122
  }
176
- function upsertWikiPageIndexEntry(adapter, input) {
177
- const schema = readSchema(adapter);
178
- const existing = selectByLocator(adapter, schema, input.source_locator);
179
- const updatedAt = nowIso();
180
- return adapter.transaction(() => {
181
- if (schema.hasIdColumn) {
182
- adapter
183
- .prepare(`
184
- INSERT INTO wiki_page_index (
185
- source_locator, page_type, title, content, case_id, source_ids,
186
- confidence, entity_refs, compiled_at, created_at, updated_at
187
- )
188
- VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)
189
- ON CONFLICT(source_locator) DO UPDATE SET
190
- page_type = excluded.page_type,
191
- title = excluded.title,
192
- content = excluded.content,
193
- case_id = excluded.case_id,
194
- source_ids = excluded.source_ids,
195
- confidence = excluded.confidence,
196
- entity_refs = excluded.entity_refs,
197
- compiled_at = excluded.compiled_at,
198
- updated_at = excluded.updated_at
199
- `)
200
- .run(input.source_locator, input.page_type, input.title, input.content, input.case_id ?? null, JSON.stringify(input.source_ids), input.confidence, JSON.stringify(input.entity_refs), input.compiled_at, updatedAt, updatedAt);
201
- }
202
- else if (schema.hasSourceIdsColumn && schema.hasEntityRefsColumn) {
203
- adapter
204
- .prepare(`
205
- INSERT INTO wiki_page_index (
206
- page_id, source_type, source_locator, case_id, title, page_type,
207
- content, confidence, source_ids, entity_refs, compiled_at, updated_at
208
- )
209
- VALUES (?, 'wiki_page', ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)
210
- ON CONFLICT(source_type, source_locator) DO UPDATE SET
211
- case_id = excluded.case_id,
212
- title = excluded.title,
213
- page_type = excluded.page_type,
214
- content = excluded.content,
215
- confidence = excluded.confidence,
216
- source_ids = excluded.source_ids,
217
- entity_refs = excluded.entity_refs,
218
- compiled_at = excluded.compiled_at,
219
- updated_at = excluded.updated_at
220
- `)
221
- .run(pageIdForSourceLocator(input.source_locator), input.source_locator, input.case_id ?? null, input.title, input.page_type, input.content, input.confidence, JSON.stringify(input.source_ids), JSON.stringify(input.entity_refs), input.compiled_at, updatedAt);
222
- }
223
- else {
224
- adapter
225
- .prepare(`
226
- INSERT INTO wiki_page_index (
227
- page_id, source_type, source_locator, case_id, title, page_type,
228
- content, confidence, compiled_at, updated_at
229
- )
230
- VALUES (?, 'wiki_page', ?, ?, ?, ?, ?, ?, ?, ?)
231
- ON CONFLICT(source_type, source_locator) DO UPDATE SET
232
- case_id = excluded.case_id,
233
- title = excluded.title,
234
- page_type = excluded.page_type,
235
- content = excluded.content,
236
- confidence = excluded.confidence,
237
- compiled_at = excluded.compiled_at,
238
- updated_at = excluded.updated_at
239
- `)
240
- .run(pageIdForSourceLocator(input.source_locator), input.source_locator, input.case_id ?? null, input.title, input.page_type, input.content, input.confidence, input.compiled_at, updatedAt);
241
- }
242
- const saved = selectByLocator(adapter, schema, input.source_locator);
243
- if (!saved) {
244
- throw new Error(`Failed to load wiki_page_index row for ${input.source_locator}.`);
245
- }
246
- upsertEmbedding(adapter, schema, saved, input);
247
- return {
248
- id: saved.id,
249
- created: existing === null,
250
- };
251
- });
252
- }
253
- function deleteWikiPageIndexEntry(adapter, source_locator) {
254
- const result = adapter
255
- .prepare('DELETE FROM wiki_page_index WHERE source_locator = ?')
256
- .run(source_locator);
257
- return { deleted: result.changes > 0 };
258
- }
259
123
  function ftsSearchWikiPages(adapter, query, limit) {
260
124
  const boundedLimit = normalizeLimit(limit);
261
125
  if (boundedLimit === 0 || !query.trim()) {
@@ -334,21 +198,4 @@ function vectorSearchWikiPages(adapter, queryEmbedding, limit) {
334
198
  raw_score: entry.score,
335
199
  }));
336
200
  }
337
- function searchWikiPages(input) {
338
- const ftsHits = ftsSearchWikiPages(input.adapter, input.query, input.limit);
339
- const vectorHits = input.queryEmbedding
340
- ? vectorSearchWikiPages(input.adapter, input.queryEmbedding, input.limit)
341
- : [];
342
- const merged = new Map();
343
- for (const hit of [...ftsHits, ...vectorHits]) {
344
- const existing = merged.get(hit.record.id);
345
- if (!existing || hit.raw_score > existing.raw_score) {
346
- merged.set(hit.record.id, hit);
347
- }
348
- }
349
- return Array.from(merged.values())
350
- .sort((left, right) => right.raw_score - left.raw_score)
351
- .slice(0, normalizeLimit(input.limit))
352
- .map((hit, rank) => ({ ...hit, rank }));
353
- }
354
201
  //# sourceMappingURL=wiki-page-index.js.map
@@ -1,28 +1,11 @@
1
1
  import type { DatabaseAdapter } from '../db-manager.js';
2
- import type { ConnectorEventIndexCursorRecord, ConnectorEventIndexRecord, ConnectorEventSearchHit, ConnectorEventStalenessStatus, UpsertConnectorEventIndexCursorInput, UpsertConnectorEventIndexInput } from './types.js';
2
+ import type { ConnectorEventIndexCursorRecord, ConnectorEventIndexRecord, UpsertConnectorEventIndexInput } from './types.js';
3
3
  type ConnectorEventIndexAdapter = Pick<DatabaseAdapter, 'prepare' | 'transaction'>;
4
- interface ListConnectorEventsByDatetimeRangeInput {
5
- fromMs: number;
6
- toMs: number;
7
- limit?: number;
8
- connectors?: string[];
9
- order?: 'asc' | 'desc';
10
- }
11
- interface SearchConnectorEventsOptions {
12
- limit?: number;
13
- connectors?: string[];
14
- }
15
4
  interface DeleteExpiredConnectorEventsInput {
16
5
  nowMs: number;
17
6
  retentionMs: number;
18
7
  connectorName?: string;
19
8
  }
20
- interface StalenessOptions {
21
- nowMs: number;
22
- staleAfterMs?: number;
23
- stalenessWarnAfterMs?: number;
24
- unhealthyAfterMs?: number;
25
- }
26
9
  export declare function mapConnectorEventIndexRecord(row: Record<string, unknown>): ConnectorEventIndexRecord;
27
10
  export declare function connectorEventIndexId(sourceConnector: string, sourceId: string): string;
28
11
  export declare function connectorEventContentHash(input: {
@@ -33,13 +16,9 @@ export declare function connectorEventContentHash(input: {
33
16
  }): Buffer;
34
17
  export declare function upsertConnectorEventIndex(adapter: ConnectorEventIndexAdapter, input: UpsertConnectorEventIndexInput): ConnectorEventIndexRecord;
35
18
  export declare function getConnectorEventIndexRecord(adapter: ConnectorEventIndexAdapter, sourceConnector: string, sourceId: string): ConnectorEventIndexRecord | null;
36
- export declare function listConnectorEventsByDatetimeRange(adapter: ConnectorEventIndexAdapter, input: ListConnectorEventsByDatetimeRangeInput): ConnectorEventIndexRecord[];
37
- export declare function searchConnectorEventsByFTS(adapter: ConnectorEventIndexAdapter, query: string, options?: SearchConnectorEventsOptions): ConnectorEventSearchHit[];
38
19
  export declare function readConnectorCursor(adapter: ConnectorEventIndexAdapter, connectorName: string): ConnectorEventIndexCursorRecord | null;
39
- export declare function upsertConnectorCursor(adapter: ConnectorEventIndexAdapter, input: UpsertConnectorEventIndexCursorInput): ConnectorEventIndexCursorRecord;
40
20
  export declare function deleteExpiredConnectorEvents(adapter: ConnectorEventIndexAdapter, input: DeleteExpiredConnectorEventsInput): {
41
21
  rows_deleted: number;
42
22
  };
43
- export declare function computeStalenessStatus(cursor: ConnectorEventIndexCursorRecord | null, options: StalenessOptions): ConnectorEventStalenessStatus;
44
23
  export type { ConnectorEventIndexCursorRecord, ConnectorEventIndexRecord, ConnectorEventSearchHit, ConnectorEventStalenessStatus, UpsertConnectorEventIndexCursorInput, UpsertConnectorEventIndexInput, } from './types.js';
45
24
  //# sourceMappingURL=event-index.d.ts.map