@tangle-network/agent-knowledge 20.0.0 → 20.0.2

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.
@@ -4,9 +4,10 @@ import { contentHash } from "@tangle-network/agent-eval";
4
4
  import { z } from "zod";
5
5
  import { createHash, randomUUID } from "node:crypto";
6
6
  import { constants, lstatSync } from "node:fs";
7
- import { lstat, mkdir, mkdtemp, open, readFile, readdir, realpath, rename, rm } from "node:fs/promises";
7
+ import { lstat, mkdir, mkdtemp, open, readFile, readdir, realpath, rename, rm, writeFile } from "node:fs/promises";
8
8
  import { basename, dirname, isAbsolute, join, relative, resolve } from "node:path";
9
9
  import { AsyncLocalStorage } from "node:async_hooks";
10
+ import { hostname } from "node:os";
10
11
  //#region src/adapters.ts
11
12
  const textSourceAdapter = {
12
13
  id: "text",
@@ -862,8 +863,45 @@ function fileMatches(file, hash, mode) {
862
863
  //#endregion
863
864
  //#region src/mutation-lock.ts
864
865
  const DEFAULT_STALE_MS = 9e5;
865
- const DEFAULT_READ_RETRIES = 100;
866
866
  const DEFAULT_READ_WAIT_MS = 25;
867
+ const MAX_POLL_MS = 250;
868
+ function sleep(ms) {
869
+ return new Promise((resolve) => setTimeout(resolve, ms));
870
+ }
871
+ /**
872
+ * How long a writer waits for the store lock, behind this process's writers and then another
873
+ * process's hold, before it fails naming the holder. It is the default stale window: by then the
874
+ * holder released, or stopped heartbeating and its lock was taken over, or it held the store
875
+ * longer than a crashed holder could wedge it.
876
+ *
877
+ * Holds measured on Discovery's archive USB disk had a median of 30.4 s and reached 92.6 s, and
878
+ * the 60 s same-process admission this replaces failed a queued `knowledge_record` terminally
879
+ * there, losing the write (agent-knowledge#251). On flash the same holds take 58-86 ms.
880
+ */
881
+ const WRITER_WAIT_MS = DEFAULT_STALE_MS;
882
+ /**
883
+ * How long a reader waits out writes before failing, when the caller sets no `retries`. It covers
884
+ * the slowest hold measured (92.6 s); the 2.5 s it replaces failed 18.3% of reads on that disk.
885
+ * A read changes nothing, so failing one loses no work, which is why it waits less than a writer.
886
+ */
887
+ const READER_WAIT_MS = 12e4;
888
+ /** Diagnostic record of the current cross-process holder, read only to name it in a timeout. */
889
+ const LOCK_OWNER_FILE = "mutation.lock.owner.json";
890
+ const holderLabels = new AsyncLocalStorage();
891
+ /**
892
+ * Name the store mutations `body` performs, so a writer or reader that times out behind them can
893
+ * say who held the store. Internal: tools label their writes with the tool and actor.
894
+ */
895
+ function withKnowledgeMutationLabel(label, body) {
896
+ return holderLabels.run(label, body);
897
+ }
898
+ function describeHolder(holder, now = Date.now()) {
899
+ const heldS = Math.max(0, Math.round((now - holder.since) / 1e3));
900
+ return `${holder.label} (pid ${holder.pid} on ${holder.host}, holding since ${new Date(holder.since).toISOString()}, ${heldS} s)`;
901
+ }
902
+ function seconds(ms) {
903
+ return `${Math.round(ms / 100) / 10} s`;
904
+ }
867
905
  let lockfileModule;
868
906
  function loadLockfile() {
869
907
  lockfileModule ??= import("proper-lockfile");
@@ -872,14 +910,13 @@ function loadLockfile() {
872
910
  const activeRoots = new AsyncLocalStorage();
873
911
  const activeReadRoots = new AsyncLocalStorage();
874
912
  const gates = /* @__PURE__ */ new Map();
875
- /** How long a same-process writer waits for admission before failing like a contended lock. */
876
- const WRITER_ADMISSION_MS = 6e4;
877
913
  function gateOf(root) {
878
914
  let gate = gates.get(root);
879
915
  if (!gate) {
880
916
  gate = {
881
917
  readers: 0,
882
918
  writing: false,
919
+ holder: void 0,
883
920
  readersWaiting: [],
884
921
  writersWaiting: []
885
922
  };
@@ -899,34 +936,51 @@ function admitNext(root, gate, afterWrite) {
899
936
  gate.writersWaiting.shift()();
900
937
  } else if (gate.readers === 0) gates.delete(root);
901
938
  }
902
- async function enterGate(root, mode, timeoutMs) {
939
+ /** Who a same-process waiter is waiting behind, for its timeout error. */
940
+ function describeGate(gate) {
941
+ const queued = gate.writersWaiting.length;
942
+ const behind = gate.holder ? describeHolder(gate.holder) : gate.readers > 0 ? `${gate.readers} reader(s) of this process` : "no admitted writer";
943
+ return queued > 0 ? `${behind}; ${queued} writer(s) still queued` : behind;
944
+ }
945
+ async function enterGate(root, mode, timeoutMs, label = "a knowledge mutation") {
903
946
  const gate = gateOf(root);
904
947
  const release = mode === "read" ? () => {
905
948
  gate.readers -= 1;
906
949
  if (gate.readers === 0) admitNext(root, gate, false);
907
950
  } : () => {
908
951
  gate.writing = false;
952
+ gate.holder = void 0;
909
953
  admitNext(root, gate, true);
910
954
  };
955
+ const hold = () => {
956
+ if (mode === "write") gate.holder = {
957
+ label,
958
+ pid: process.pid,
959
+ host: hostname(),
960
+ since: Date.now()
961
+ };
962
+ return once(release);
963
+ };
911
964
  if (mode === "read" ? !gate.writing && gate.writersWaiting.length === 0 : !gate.writing && gate.readers === 0 && gate.writersWaiting.length === 0) {
912
965
  if (mode === "read") gate.readers += 1;
913
966
  else gate.writing = true;
914
- return once(release);
967
+ return hold();
915
968
  }
916
969
  const waiting = mode === "read" ? gate.readersWaiting : gate.writersWaiting;
917
970
  return new Promise((resolve, reject) => {
918
971
  let timer;
919
972
  const admit = () => {
920
973
  if (timer) clearTimeout(timer);
921
- resolve(once(release));
974
+ resolve(hold());
922
975
  };
923
976
  waiting.push(admit);
924
977
  timer = setTimeout(() => {
925
978
  const position = waiting.indexOf(admit);
926
979
  if (position < 0) return;
927
980
  waiting.splice(position, 1);
981
+ const behind = describeGate(gate);
928
982
  admitNext(root, gate, mode === "write");
929
- reject(mode === "read" ? /* @__PURE__ */ new Error("knowledge read could not observe a stable mutation epoch") : Object.assign(/* @__PURE__ */ new Error(`knowledge store is locked by this process: ${root}`), { code: "ELOCKED" }));
983
+ reject(mode === "read" ? /* @__PURE__ */ new Error(`knowledge read could not observe a stable mutation epoch: ${root}; waited ${seconds(timeoutMs)} behind ${behind}`) : Object.assign(/* @__PURE__ */ new Error(`knowledge store is locked by this process: ${root}; waited ${seconds(timeoutMs)} behind ${behind}`), { code: "ELOCKED" }));
930
984
  }, timeoutMs);
931
985
  timer.unref?.();
932
986
  });
@@ -971,21 +1025,17 @@ async function withKnowledgeMutation(root, mutate, options = {}) {
971
1025
  const existing = activeRoots.getStore()?.get(resolvedRoot);
972
1026
  if (existing?.active) return await runInlineMutation(existing.lock, mutate);
973
1027
  if (activeReadRoots.getStore()?.has(resolvedRoot)) throw new Error("a knowledge mutation cannot start inside a read of the same store");
1028
+ const label = holderLabels.getStore() ?? options.resumeTransaction?.purpose ?? "a knowledge mutation";
974
1029
  const started = performance.now();
975
- const leave = await enterGate(resolvedRoot, "write", noRetries(options.retries) ? 0 : WRITER_ADMISSION_MS);
1030
+ const leave = await enterGate(resolvedRoot, "write", noRetries(options.retries) ? 0 : WRITER_WAIT_MS, label);
976
1031
  try {
977
1032
  return await withSafeDirectory(resolvedRoot, ".agent-knowledge", true, async (cacheDir) => {
978
- const acquired = await acquireDurableFileLock(resolvedRoot, {
979
- lockfilePath: join(cacheDir, "mutation.lock.durable"),
1033
+ const acquired = await acquireStoreLock(resolvedRoot, cacheDir, {
980
1034
  staleMs: options.staleMs,
981
- retries: options.retries ?? {
982
- retries: 100,
983
- factor: 1.1,
984
- minTimeout: 10,
985
- maxTimeout: 200,
986
- randomize: true
987
- }
1035
+ retries: options.retries,
1036
+ started
988
1037
  });
1038
+ await recordLockOwner(cacheDir, label);
989
1039
  const held = performance.now();
990
1040
  try {
991
1041
  return await runOwnedMutation(resolvedRoot, cacheDir, acquired, options, mutate);
@@ -1004,6 +1054,54 @@ async function withKnowledgeMutation(root, mutate, options = {}) {
1004
1054
  leave();
1005
1055
  }
1006
1056
  }
1057
+ /**
1058
+ * Take the cross-process file lock. A caller that sets `retries` keeps that attempt budget; every
1059
+ * other writer polls until one deadline shared with its in-process wait, so a hold longer than a
1060
+ * fixed number of attempts delays a write instead of failing it.
1061
+ */
1062
+ async function acquireStoreLock(root, cacheDir, options) {
1063
+ const lockfilePath = join(cacheDir, "mutation.lock.durable");
1064
+ const deadline = options.started + WRITER_WAIT_MS;
1065
+ let pause = 10;
1066
+ for (;;) try {
1067
+ return await acquireDurableFileLock(root, {
1068
+ lockfilePath,
1069
+ staleMs: options.staleMs,
1070
+ retries: options.retries ?? 0
1071
+ });
1072
+ } catch (error) {
1073
+ const remaining = deadline - performance.now();
1074
+ if (options.retries !== void 0 || error.code !== "ELOCKED" || remaining <= 0) throw await namedLockError(error, root, cacheDir, performance.now() - options.started);
1075
+ await sleep(Math.min(remaining, pause * (.5 + Math.random())));
1076
+ pause = Math.min(MAX_POLL_MS, pause * 1.5);
1077
+ }
1078
+ }
1079
+ /** A contended file lock, restated with the holder its owner record names. */
1080
+ async function namedLockError(error, root, cacheDir, waitedMs) {
1081
+ if (error?.code !== "ELOCKED") return error;
1082
+ const owner = await readLockOwner(cacheDir);
1083
+ return Object.assign(new Error(`knowledge store is locked by another process: ${root}; waited ${seconds(waitedMs)} for ${owner ? describeHolder(owner) : "a holder that recorded no owner"}`, { cause: error }), { code: "ELOCKED" });
1084
+ }
1085
+ /** Record who holds the file lock, for a waiter's timeout. Diagnostic only, so not fsynced. */
1086
+ async function recordLockOwner(cacheDir, label) {
1087
+ const owner = {
1088
+ label,
1089
+ pid: process.pid,
1090
+ host: hostname(),
1091
+ since: Date.now()
1092
+ };
1093
+ try {
1094
+ await writeFile(join(cacheDir, LOCK_OWNER_FILE), `${JSON.stringify(owner)}\n`);
1095
+ } catch {}
1096
+ }
1097
+ async function readLockOwner(cacheDir) {
1098
+ try {
1099
+ const value = JSON.parse(await readFile(join(cacheDir, LOCK_OWNER_FILE), "utf8"));
1100
+ return typeof value.label === "string" && Number.isSafeInteger(value.pid) && typeof value.host === "string" && Number.isFinite(value.since) ? value : void 0;
1101
+ } catch {
1102
+ return;
1103
+ }
1104
+ }
1007
1105
  function noRetries(retries) {
1008
1106
  return retries === 0 || typeof retries === "object" && !Array.isArray(retries) && retries.retries === 0;
1009
1107
  }
@@ -1150,27 +1248,46 @@ async function withKnowledgeRead(root, read, options = {}) {
1150
1248
  if (activeReadRoots.getStore()?.has(resolvedRoot)) return await read();
1151
1249
  const readRoots = new Set(activeReadRoots.getStore());
1152
1250
  readRoots.add(resolvedRoot);
1153
- const retries = options.retries ?? DEFAULT_READ_RETRIES;
1154
- const leave = await enterGate(resolvedRoot, "read", (retries + 1) * (options.waitMs ?? DEFAULT_READ_WAIT_MS));
1251
+ const started = performance.now();
1252
+ const retries = options.retries;
1253
+ const budgetMs = retries === void 0 ? READER_WAIT_MS : (retries + 1) * (options.waitMs ?? DEFAULT_READ_WAIT_MS);
1254
+ const deadline = started + budgetMs;
1255
+ const leave = await enterGate(resolvedRoot, "read", budgetMs);
1155
1256
  try {
1156
1257
  return await activeReadRoots.run(readRoots, async () => {
1157
- for (let attempt = 0; attempt <= retries; attempt += 1) {
1258
+ let pause = options.waitMs ?? DEFAULT_READ_WAIT_MS;
1259
+ for (let attempt = 0; retries === void 0 || attempt <= retries; attempt += 1) {
1260
+ if (attempt > 0 && retries === void 0 && performance.now() >= deadline) break;
1158
1261
  const before = await readMutationEpoch(resolvedRoot);
1159
- if (isOdd(before)) {
1160
- await waitForActiveMutationEpoch(resolvedRoot, before, options);
1161
- continue;
1262
+ let active = before;
1263
+ if (!isOdd(before)) {
1264
+ const result = await read();
1265
+ const after = await readMutationEpoch(resolvedRoot);
1266
+ if (before === after) return result;
1267
+ if (!isOdd(after)) continue;
1268
+ active = after;
1162
1269
  }
1163
- const result = await read();
1164
- const after = await readMutationEpoch(resolvedRoot);
1165
- if (before === after && !isOdd(after)) return result;
1166
- if (isOdd(after)) await waitForActiveMutationEpoch(resolvedRoot, after, options);
1270
+ await waitForActiveMutationEpoch(resolvedRoot, active, options, pause);
1271
+ if (retries === void 0) pause = Math.min(MAX_POLL_MS, pause * 1.5);
1167
1272
  }
1168
- throw new Error("knowledge read could not observe a stable mutation epoch");
1273
+ throw new Error(`knowledge read could not observe a stable mutation epoch: ${resolvedRoot}; waited ${seconds(performance.now() - started)} for ${await describeWriter(resolvedRoot)}`);
1169
1274
  });
1170
1275
  } finally {
1171
1276
  leave();
1172
1277
  }
1173
1278
  }
1279
+ /** The writer a reader gave up on: this process's admitted writer, else the recorded owner. */
1280
+ async function describeWriter(root) {
1281
+ const local = gates.get(root)?.holder;
1282
+ if (local) return describeHolder(local);
1283
+ let owner;
1284
+ try {
1285
+ owner = await withSafeDirectory(root, ".agent-knowledge", false, readLockOwner);
1286
+ } catch {
1287
+ owner = void 0;
1288
+ }
1289
+ return owner ? describeHolder(owner) : "a writer that recorded no owner";
1290
+ }
1174
1291
  async function acquireDurableFileLock(target, options) {
1175
1292
  const stale = Math.max(5e3, options.staleMs ?? DEFAULT_STALE_MS);
1176
1293
  const update = Math.max(1e3, Math.floor(stale / 3));
@@ -1242,9 +1359,9 @@ async function writeMutationEpoch(cacheDir, epoch) {
1242
1359
  updatedAt: (/* @__PURE__ */ new Date()).toISOString()
1243
1360
  });
1244
1361
  }
1245
- async function waitForActiveMutationEpoch(root, epoch, options) {
1362
+ async function waitForActiveMutationEpoch(root, epoch, options, pauseMs) {
1246
1363
  if (!await hasActiveMutationLock(root, options)) await healAbandonedMutationEpoch(root, epoch, options);
1247
- await new Promise((resolve) => setTimeout(resolve, options.waitMs ?? DEFAULT_READ_WAIT_MS));
1364
+ await sleep(pauseMs);
1248
1365
  }
1249
1366
  async function healAbandonedMutationEpoch(root, expectedEpoch, options) {
1250
1367
  await withSafeDirectory(root, ".agent-knowledge", false, async (cacheDir) => {
@@ -4581,29 +4698,25 @@ function lexicalPageTerms(page, tokenize, fieldBoosts) {
4581
4698
  length
4582
4699
  };
4583
4700
  }
4584
- /** Inverted index from per-page terms already computed with `tokenize` and `fieldBoosts`. */
4701
+ /**
4702
+ * Inverted index from per-page terms already computed with `tokenize` and `fieldBoosts`.
4703
+ *
4704
+ * Posting lists are built when a term is first looked up, not up front. A query reads a handful of
4705
+ * terms, while assembling every list walks every distinct term of every page: on a 910-page run
4706
+ * store that was about 440 ms of each search that followed a write, because every write starts a
4707
+ * new page view and so a new index (agent-knowledge#203). Enumerating the postings builds them all
4708
+ * once, so the map behaves exactly as an eagerly built one.
4709
+ */
4585
4710
  function assembleLexicalIndex(pages, terms, tokenize, fieldBoosts) {
4586
- const postings = /* @__PURE__ */ new Map();
4587
4711
  const documentLengths = [];
4588
4712
  let totalLength = 0;
4589
- terms.forEach(({ frequencies, length }, ordinal) => {
4713
+ for (const { length } of terms) {
4590
4714
  documentLengths.push(length);
4591
4715
  totalLength += length;
4592
- for (const [term, tf] of frequencies) {
4593
- let list = postings.get(term);
4594
- if (!list) {
4595
- list = [];
4596
- postings.set(term, list);
4597
- }
4598
- list.push({
4599
- ordinal,
4600
- tf
4601
- });
4602
- }
4603
- });
4716
+ }
4604
4717
  return {
4605
4718
  pages,
4606
- postings,
4719
+ postings: new LazyPostings(terms),
4607
4720
  documentLengths,
4608
4721
  averageDocumentLength: pages.length > 0 ? totalLength / pages.length : 0,
4609
4722
  documentCount: pages.length,
@@ -4611,6 +4724,74 @@ function assembleLexicalIndex(pages, terms, tokenize, fieldBoosts) {
4611
4724
  fieldBoosts
4612
4725
  };
4613
4726
  }
4727
+ const NO_POSTINGS = Object.freeze([]);
4728
+ /** A read-only postings map that builds one term's list on first lookup, in ordinal order. */
4729
+ var LazyPostings = class {
4730
+ #terms;
4731
+ #lists = /* @__PURE__ */ new Map();
4732
+ #all;
4733
+ constructor(terms) {
4734
+ this.#terms = terms;
4735
+ }
4736
+ get(term) {
4737
+ if (this.#all) return this.#all.get(term);
4738
+ let list = this.#lists.get(term);
4739
+ if (list === void 0) {
4740
+ const found = [];
4741
+ this.#terms.forEach(({ frequencies }, ordinal) => {
4742
+ const tf = frequencies.get(term);
4743
+ if (tf !== void 0) found.push({
4744
+ ordinal,
4745
+ tf
4746
+ });
4747
+ });
4748
+ list = found.length === 0 ? NO_POSTINGS : found;
4749
+ this.#lists.set(term, list);
4750
+ }
4751
+ return list.length === 0 ? void 0 : list;
4752
+ }
4753
+ has(term) {
4754
+ return this.get(term) !== void 0;
4755
+ }
4756
+ get size() {
4757
+ return this.#every().size;
4758
+ }
4759
+ forEach(callback, thisArg) {
4760
+ for (const [term, list] of this.#every()) callback.call(thisArg, list, term, this);
4761
+ }
4762
+ entries() {
4763
+ return this.#every().entries();
4764
+ }
4765
+ keys() {
4766
+ return this.#every().keys();
4767
+ }
4768
+ values() {
4769
+ return this.#every().values();
4770
+ }
4771
+ [Symbol.iterator]() {
4772
+ return this.entries();
4773
+ }
4774
+ #every() {
4775
+ if (this.#all) return this.#all;
4776
+ const all = /* @__PURE__ */ new Map();
4777
+ this.#terms.forEach(({ frequencies }, ordinal) => {
4778
+ for (const [term, tf] of frequencies) {
4779
+ let list = all.get(term);
4780
+ if (!list) {
4781
+ list = [];
4782
+ all.set(term, list);
4783
+ }
4784
+ list.push({
4785
+ ordinal,
4786
+ tf
4787
+ });
4788
+ }
4789
+ });
4790
+ this.#lists.clear();
4791
+ this.#all = all;
4792
+ return all;
4793
+ }
4794
+ };
4614
4795
  //#endregion
4615
4796
  //#region src/lexical-index.ts
4616
4797
  const STOP_WORDS = /* @__PURE__ */ new Set([
@@ -4891,6 +5072,6 @@ function explainKnowledgeTarget(index, target) {
4891
5072
  };
4892
5073
  }
4893
5074
  //#endregion
4894
- export { assertGradeableEvidence as $, removeDurable as $n, KnowledgeIndexSchema as $t, createKnowledgeVisibilitySnapshot as A, isKnowledgeMutationHeld as An, auditKnowledgeCitations as At, snapshotImmutableVisibility as B, knowledgeFileTransactionPlanHash as Bn, isScaffoldPath as Bt, createRunScopedStores as C, mergeTrackedClaims as Cn, KnowledgeCitationAuditError as Ct, KNOWLEDGE_RECEIPT_DIGEST_ALGORITHM as D, parseFrontmatter as Dn, assertKnowledgeCitationsResolved as Dt, originatedPages as E, formatFrontmatter as En, assertKnowledgeCitationAudit as Et, knowledgePageDigest as F, withKnowledgeRead as Fn, resolveRunScopedCitation as Ft, visibilityIndexOf as G, canonicalPathsEqual as Gn, WIKILINK_REGEX as Gt, validateOrigin as H, rollbackKnowledgeFileTransaction as Hn, layoutFor as Ht, knowledgeVisibilityArtifactRef as I, applyKnowledgeFileTransaction as In, resolveRunScopedCitations as It, validateKnowledgeIndex as J, isMissingFile as Jn, DeepQuestionSchema as Jt, detectNearDuplicatePages as K, canonicalRelativeWithinRoot as Kn, extractWikilinks as Kt, nonEmpty as L, assertKnowledgeMutationPath as Ln, SCAFFOLD_PAGE_BASENAMES as Lt, digest as M, recoverPendingKnowledgeMutation as Mn, parseKnowledgeCitationReference as Mt, encodeKnowledgeVisibilitySnapshot as N, runInKnowledgeMutationScope as Nn, resolveKnowledgeCitation as Nt, KNOWLEDGE_USE_RECEIPT_SCHEMA_VERSION as O, acquireDurableFileLock as On, assertRunScopedCitationsResolved as Ot, immutablePageDigest as P, withKnowledgeMutation as Pn, resolveKnowledgeCitations as Pt, UncheckableClaimError as Q, relativeWithinRoot as Qn, KnowledgeGraphNodeSchema as Qt, normalizeVisibilityArtifact as R, commitKnowledgeFileMutations as Rn, initKnowledgeBase as Rt, createFileRunLineageAuthority as S, mergeClaimLedgers as Sn, knowledgePageRelations as St, loadKnowledgeToolChain as T, researchSourceVersionKey as Tn, assertCurrentRunCitationsResolved as Tt, verifyKnowledgeVisibilitySnapshot as U, DEFAULT_PAGES_DIRECTORY as Un, loadKnowledgePages as Ut, validateKnowledgePage as V, prepareKnowledgeFileTransaction as Vn, knowledgePageFromMarkdown as Vt, visibilityIdentity as W, normalizePagesDirectory as Wn, writeJson as Wt, CHECKABLE_RUNG_THRESHOLD as X, readRegularFileNoFollow as Xn, KnowledgeEventSchema as Xt, lintKnowledgeIndex as Y, listRegularFilesWithinRoot as Yn, KnowledgeBaseCandidateSchema as Yt, DEADLINE_EXIT_CODE as Z, readRegularFileWithinRoot as Zn, KnowledgeGraphEdgeSchema as Zt, isSafeKnowledgePath as _, claimSourceHost as _n, KB_INDEX_PATH as _t, searchKnowledge as a, ResearchClaimRecordSchema as an, writeFileDurableWithinRoot as ar, buildKnowledgeIndex as at, assertKnowledgeWriteIntake as b, linkClaimContradictions as bn, assertClaimLedgerId as bt, scoreBm25 as c, SourceRecordSchema as cn, mediaTypeFor$1 as cr, addSourceText as ct, DEFAULT_FIELD_BOOSTS as d, assertDeepQuestionIntegrity as dn, sourceRegistryPath as dt, KnowledgePageInvalidationSchema as en, renameDurable as er, claimCheckKey as et, assembleLexicalIndex as f, assertResearchClaimEvidenceIntegrity as fn, writeSourceRegistry as ft, applyKnowledgeWriteBlocksFile as g, claimId as gn, KB_EVENTS_PATH as gt, applyKnowledgeWriteBlocks as h, claimEvidenceId as hn, KB_CLAIM_LEDGER_DIR as ht, reciprocalRankFusion as i, ResearchClaimLedgerSchema as in, writeFileDurable as ir, verifyGradeableEvidence as it, decodeKnowledgeVisibilitySnapshot as j, measureKnowledgeMutation as jn, formatKnowledgeCitationReference as jt, assertSchemaVersion as k, inspectPendingKnowledgeMutation as kn, auditCurrentRunCitations as kt, tokenizeQuery as l, KNOWLEDGE_EVENT_TYPES as ln, textSourceAdapter as lr, loadSourceRegistry as lt, stringMetadata as m, assertTrackedClaimIntegrity as mn, FileSystemKbStore as mt, inspectKnowledgeIndex as n, KnowledgeRelationSchema as nn, withSafeDescendant as nr, gradeFor as nt, searchKnowledgePages as o, ResearchSourceVersionSchema as on, writeJsonDurable as or, writeKnowledgeIndex as ot, lexicalPageTerms as p, assertResearchClaimLedgerIntegrity as pn, ClaimLedgerMigrationRequiredError as pt, normalizePageText as q, isKernelAnchoredPath as qn, normalizeLinkTarget as qt, KNOWLEDGE_SEARCH_RETRIEVER_ID as r, ResearchClaimEvidenceSchema as rn, withSafeDirectory as rr, verdictFor as rt, buildKnowledgeLexicalIndex as s, SourceAnchorSchema as sn, writeJsonDurableWithinRoot as sr, addSourcePath as st, explainKnowledgeTarget as t, KnowledgePageSchema as tn, syncDirectory as tr, gradeClaims as tt, tokenizeText as u, ClaimLedgerGoalConflictError as un, snapshotSourceTextInput as ut, parseKnowledgeWriteBlocks as v, deepQuestionId as vn, KB_STORE_DIR as vt, isKnowledgeToolChain as w, normalizeClaimText as wn, KnowledgeCitationResolutionError as wt, RUN_LINEAGE_BASENAME as x, materializeRegisteredClaimEvidence as xn, buildKnowledgeGraph as xt, KnowledgeDuplicateIntakeError as y, emptyClaimLedger as yn, MemoryKbStore as yt, normalizeVisibilityRef as z, finishKnowledgeFileTransaction as zn, isKnowledgePagePath as zt };
5075
+ export { assertGradeableEvidence as $, relativeWithinRoot as $n, KnowledgeIndexSchema as $t, createKnowledgeVisibilitySnapshot as A, isKnowledgeMutationHeld as An, auditKnowledgeCitations as At, snapshotImmutableVisibility as B, finishKnowledgeFileTransaction as Bn, isScaffoldPath as Bt, createRunScopedStores as C, mergeTrackedClaims as Cn, KnowledgeCitationAuditError as Ct, KNOWLEDGE_RECEIPT_DIGEST_ALGORITHM as D, parseFrontmatter as Dn, assertKnowledgeCitationsResolved as Dt, originatedPages as E, formatFrontmatter as En, assertKnowledgeCitationAudit as Et, knowledgePageDigest as F, withKnowledgeMutationLabel as Fn, resolveRunScopedCitation as Ft, visibilityIndexOf as G, normalizePagesDirectory as Gn, WIKILINK_REGEX as Gt, validateOrigin as H, prepareKnowledgeFileTransaction as Hn, layoutFor as Ht, knowledgeVisibilityArtifactRef as I, withKnowledgeRead as In, resolveRunScopedCitations as It, validateKnowledgeIndex as J, isKernelAnchoredPath as Jn, DeepQuestionSchema as Jt, detectNearDuplicatePages as K, canonicalPathsEqual as Kn, extractWikilinks as Kt, nonEmpty as L, applyKnowledgeFileTransaction as Ln, SCAFFOLD_PAGE_BASENAMES as Lt, digest as M, recoverPendingKnowledgeMutation as Mn, parseKnowledgeCitationReference as Mt, encodeKnowledgeVisibilitySnapshot as N, runInKnowledgeMutationScope as Nn, resolveKnowledgeCitation as Nt, KNOWLEDGE_USE_RECEIPT_SCHEMA_VERSION as O, acquireDurableFileLock as On, assertRunScopedCitationsResolved as Ot, immutablePageDigest as P, withKnowledgeMutation as Pn, resolveKnowledgeCitations as Pt, UncheckableClaimError as Q, readRegularFileWithinRoot as Qn, KnowledgeGraphNodeSchema as Qt, normalizeVisibilityArtifact as R, assertKnowledgeMutationPath as Rn, initKnowledgeBase as Rt, createFileRunLineageAuthority as S, mergeClaimLedgers as Sn, knowledgePageRelations as St, loadKnowledgeToolChain as T, researchSourceVersionKey as Tn, assertCurrentRunCitationsResolved as Tt, verifyKnowledgeVisibilitySnapshot as U, rollbackKnowledgeFileTransaction as Un, loadKnowledgePages as Ut, validateKnowledgePage as V, knowledgeFileTransactionPlanHash as Vn, knowledgePageFromMarkdown as Vt, visibilityIdentity as W, DEFAULT_PAGES_DIRECTORY as Wn, writeJson as Wt, CHECKABLE_RUNG_THRESHOLD as X, listRegularFilesWithinRoot as Xn, KnowledgeEventSchema as Xt, lintKnowledgeIndex as Y, isMissingFile as Yn, KnowledgeBaseCandidateSchema as Yt, DEADLINE_EXIT_CODE as Z, readRegularFileNoFollow as Zn, KnowledgeGraphEdgeSchema as Zt, isSafeKnowledgePath as _, claimSourceHost as _n, KB_INDEX_PATH as _t, searchKnowledge as a, ResearchClaimRecordSchema as an, writeFileDurable as ar, buildKnowledgeIndex as at, assertKnowledgeWriteIntake as b, linkClaimContradictions as bn, assertClaimLedgerId as bt, scoreBm25 as c, SourceRecordSchema as cn, writeJsonDurableWithinRoot as cr, addSourceText as ct, DEFAULT_FIELD_BOOSTS as d, assertDeepQuestionIntegrity as dn, sourceRegistryPath as dt, KnowledgePageInvalidationSchema as en, removeDurable as er, claimCheckKey as et, assembleLexicalIndex as f, assertResearchClaimEvidenceIntegrity as fn, writeSourceRegistry as ft, applyKnowledgeWriteBlocksFile as g, claimId as gn, KB_EVENTS_PATH as gt, applyKnowledgeWriteBlocks as h, claimEvidenceId as hn, KB_CLAIM_LEDGER_DIR as ht, reciprocalRankFusion as i, ResearchClaimLedgerSchema as in, withSafeDirectory as ir, verifyGradeableEvidence as it, decodeKnowledgeVisibilitySnapshot as j, measureKnowledgeMutation as jn, formatKnowledgeCitationReference as jt, assertSchemaVersion as k, inspectPendingKnowledgeMutation as kn, auditCurrentRunCitations as kt, tokenizeQuery as l, KNOWLEDGE_EVENT_TYPES as ln, mediaTypeFor$1 as lr, loadSourceRegistry as lt, stringMetadata as m, assertTrackedClaimIntegrity as mn, FileSystemKbStore as mt, inspectKnowledgeIndex as n, KnowledgeRelationSchema as nn, syncDirectory as nr, gradeFor as nt, searchKnowledgePages as o, ResearchSourceVersionSchema as on, writeFileDurableWithinRoot as or, writeKnowledgeIndex as ot, lexicalPageTerms as p, assertResearchClaimLedgerIntegrity as pn, ClaimLedgerMigrationRequiredError as pt, normalizePageText as q, canonicalRelativeWithinRoot as qn, normalizeLinkTarget as qt, KNOWLEDGE_SEARCH_RETRIEVER_ID as r, ResearchClaimEvidenceSchema as rn, withSafeDescendant as rr, verdictFor as rt, buildKnowledgeLexicalIndex as s, SourceAnchorSchema as sn, writeJsonDurable as sr, addSourcePath as st, explainKnowledgeTarget as t, KnowledgePageSchema as tn, renameDurable as tr, gradeClaims as tt, tokenizeText as u, ClaimLedgerGoalConflictError as un, textSourceAdapter as ur, snapshotSourceTextInput as ut, parseKnowledgeWriteBlocks as v, deepQuestionId as vn, KB_STORE_DIR as vt, isKnowledgeToolChain as w, normalizeClaimText as wn, KnowledgeCitationResolutionError as wt, RUN_LINEAGE_BASENAME as x, materializeRegisteredClaimEvidence as xn, buildKnowledgeGraph as xt, KnowledgeDuplicateIntakeError as y, emptyClaimLedger as yn, MemoryKbStore as yt, normalizeVisibilityRef as z, commitKnowledgeFileMutations as zn, isKnowledgePagePath as zt };
4895
5076
 
4896
- //# sourceMappingURL=inspect-CMigdsD5.js.map
5077
+ //# sourceMappingURL=inspect-B24gqPC4.js.map