@inerrata-corporation/errata 2.0.17-dev.3369 → 2.0.17-dev.3407

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.
@@ -16216,12 +16216,13 @@ function installHistoryCacheFloor(db) {
16216
16216
  }
16217
16217
 
16218
16218
  // ../../packages/local-graph/src/session-evidence.ts
16219
+ var arrays = /* @__PURE__ */ new Set(["sources", "recurrenceSources", "contributors", "inferredContributors", "citeSessions"]);
16220
+ var scalars = /* @__PURE__ */ new Set(["discriminatorSource", "originSession", "sessionId", "sourceSession"]);
16221
+ var SESSION_EVIDENCE_FIELDS = [...arrays, ...scalars, "citeAnchorHints"];
16219
16222
  function repairSessionEvidence(input, aliases = /* @__PURE__ */ new Map()) {
16220
16223
  const mapping = new Map(aliases);
16221
16224
  const uuid3 = "[a-f0-9]{8}(?:-[a-f0-9]{4}){3}-[a-f0-9]{12}";
16222
16225
  const codex = new RegExp(`^codex:(?:rollout-.*?)?(${uuid3})$`, "i");
16223
- const arrays = /* @__PURE__ */ new Set(["sources", "recurrenceSources", "contributors", "inferredContributors", "citeSessions"]);
16224
- const scalars = /* @__PURE__ */ new Set(["discriminatorSource", "originSession", "sessionId", "sourceSession"]);
16225
16226
  const discover = (value, key = "") => {
16226
16227
  if (typeof value === "string" && (arrays.has(key) || scalars.has(key) || key === "citeAnchorHints")) {
16227
16228
  const match = value.match(codex);
@@ -16319,6 +16320,7 @@ function localEdgeViolation(fromLabel, type, toLabel) {
16319
16320
  return verdict.ok ? null : verdict.reason ?? "edge rule violation";
16320
16321
  }
16321
16322
  var SCHEMA_VERSION = 6;
16323
+ var SESSION_EVIDENCE_PREDICATE = SESSION_EVIDENCE_FIELDS.map((field) => `instr(attrs_json, '${JSON.stringify(field)}') > 0`).join(" OR ");
16322
16324
  var SCHEMA_SQL = `
16323
16325
  CREATE TABLE IF NOT EXISTS schema_version (
16324
16326
  version INTEGER PRIMARY KEY
@@ -16411,6 +16413,10 @@ CREATE UNIQUE INDEX IF NOT EXISTS edges_triple ON edges(from_id, type, to_id);
16411
16413
  `;
16412
16414
  var TEMPORAL_INDEX_SQL = `
16413
16415
  CREATE INDEX IF NOT EXISTS nodes_live ON nodes(label, valid_to);
16416
+ CREATE INDEX IF NOT EXISTS nodes_live_count ON nodes(valid_to);
16417
+ CREATE INDEX IF NOT EXISTS nodes_live_recent ON nodes(label, last_updated_at DESC) WHERE valid_to IS NULL;
16418
+ CREATE INDEX IF NOT EXISTS nodes_session_evidence ON nodes(id) WHERE ${SESSION_EVIDENCE_PREDICATE};
16419
+ CREATE INDEX IF NOT EXISTS edges_session_evidence ON edges(id) WHERE ${SESSION_EVIDENCE_PREDICATE};
16414
16420
  -- Covering + partial index for labelFingerprint over the instance labels: the
16415
16421
  -- live-push probe runs it per workspace on a timer, and each hit used to read
16416
16422
  -- its table row. Partial, so it maintains a few thousand rows instead of adding
@@ -16780,12 +16786,13 @@ var SqliteGraphStore = class {
16780
16786
  });
16781
16787
  }
16782
16788
  repairSessionAliases(canonical, aliases = []) {
16789
+ if (canonical && aliases.length === 0) return 0;
16783
16790
  const mapping = new Map(aliases.map((alias) => [alias, canonical]));
16784
16791
  let changed = 0;
16785
16792
  for (const table of ["nodes", "edges"]) {
16786
16793
  const predicates = canonical ? aliases.map(() => "instr(attrs_json, ?) > 0") : ["instr(attrs_json, 'codex:') > 0", "instr(attrs_json, 'discriminatorSource') > 0"];
16787
16794
  if (!predicates.length) continue;
16788
- const rows = this.db.prepare(`SELECT id, attrs_json FROM ${table} WHERE ${predicates.join(" OR ")}`).all(...canonical ? aliases : []);
16795
+ const rows = this.db.prepare(`SELECT id, attrs_json FROM ${table} WHERE (${SESSION_EVIDENCE_PREDICATE}) AND (${predicates.join(" OR ")})`).all(...canonical ? aliases.map((alias) => JSON.stringify(alias)) : []);
16789
16796
  const update = this.db.prepare(`UPDATE ${table} SET attrs_json = ?${table === "edges" ? ", type = CASE WHEN type = 'CONFIRMS' AND json_extract(?, '$.provisional') = 1 THEN 'INDICATES' ELSE type END" : ""} WHERE id = ?`);
16790
16797
  for (const row of rows) {
16791
16798
  const attrs = JSON.stringify(repairSessionEvidence(JSON.parse(row.attrs_json), mapping));
@@ -17011,6 +17018,25 @@ var SqliteGraphStore = class {
17011
17018
  const rows = this.db.prepare("SELECT id FROM nodes WHERE label = ? AND valid_to IS NULL ORDER BY last_updated_at DESC LIMIT ?").all(label, Math.max(0, limit));
17012
17019
  return rows.map((r) => r.id);
17013
17020
  }
17021
+ recentOpenProblemCandidates(opts) {
17022
+ if (!Number.isSafeInteger(opts.limit) || opts.limit < 0) {
17023
+ throw new RangeError("candidate limit must be a non-negative safe integer");
17024
+ }
17025
+ return this.db.prepare(`SELECT id, description FROM nodes
17026
+ WHERE label = 'Problem' AND valid_to IS NULL
17027
+ AND json_extract(attrs_json, '$.resolvedAt') IS NULL
17028
+ AND json_type(attrs_json, '$.mergedInto') IS NULL
17029
+ AND (? IS NULL OR id != ?)
17030
+ AND (json_type(attrs_json, '$.workspaceId') IS NULL OR json_extract(attrs_json, '$.workspaceId') = ?)
17031
+ AND COALESCE(json_extract(attrs_json, '$.kind') = 'constraint', 0) = ?
17032
+ ORDER BY last_updated_at DESC, rowid ASC LIMIT ?`).all(
17033
+ opts.excludeId ?? null,
17034
+ opts.excludeId ?? null,
17035
+ opts.workspaceId,
17036
+ opts.constraint ? 1 : 0,
17037
+ opts.limit
17038
+ );
17039
+ }
17014
17040
  hasLiveNodes() {
17015
17041
  const r = this.db.prepare("SELECT EXISTS(SELECT 1 FROM nodes WHERE valid_to IS NULL) AS e").get();
17016
17042
  return r.e === 1;
package/errata.mjs CHANGED
@@ -18012,8 +18012,6 @@ function repairSessionEvidence(input, aliases = /* @__PURE__ */ new Map()) {
18012
18012
  const mapping = new Map(aliases);
18013
18013
  const uuid3 = "[a-f0-9]{8}(?:-[a-f0-9]{4}){3}-[a-f0-9]{12}";
18014
18014
  const codex = new RegExp(`^codex:(?:rollout-.*?)?(${uuid3})$`, "i");
18015
- const arrays = /* @__PURE__ */ new Set(["sources", "recurrenceSources", "contributors", "inferredContributors", "citeSessions"]);
18016
- const scalars = /* @__PURE__ */ new Set(["discriminatorSource", "originSession", "sessionId", "sourceSession"]);
18017
18015
  const discover = (value, key = "") => {
18018
18016
  if (typeof value === "string" && (arrays.has(key) || scalars.has(key) || key === "citeAnchorHints")) {
18019
18017
  const match2 = value.match(codex);
@@ -18071,9 +18069,13 @@ function repairSessionEvidence(input, aliases = /* @__PURE__ */ new Map()) {
18071
18069
  }
18072
18070
  return repaired;
18073
18071
  }
18072
+ var arrays, scalars, SESSION_EVIDENCE_FIELDS;
18074
18073
  var init_session_evidence = __esm({
18075
18074
  "../../packages/local-graph/src/session-evidence.ts"() {
18076
18075
  "use strict";
18076
+ arrays = /* @__PURE__ */ new Set(["sources", "recurrenceSources", "contributors", "inferredContributors", "citeSessions"]);
18077
+ scalars = /* @__PURE__ */ new Set(["discriminatorSource", "originSession", "sessionId", "sourceSession"]);
18078
+ SESSION_EVIDENCE_FIELDS = [...arrays, ...scalars, "citeAnchorHints"];
18077
18079
  }
18078
18080
  });
18079
18081
 
@@ -18153,7 +18155,7 @@ function rowToEdge(r) {
18153
18155
  function openGraphStore(opts) {
18154
18156
  return new SqliteGraphStore(opts);
18155
18157
  }
18156
- var LOCAL_RULE_OVERRIDES, SCHEMA_VERSION, SCHEMA_SQL, TEMPORAL_INDEX_SQL, FINGERPRINT_INDEXED_LABELS, SqliteGraphStore;
18158
+ var LOCAL_RULE_OVERRIDES, SCHEMA_VERSION, SESSION_EVIDENCE_PREDICATE, SCHEMA_SQL, TEMPORAL_INDEX_SQL, FINGERPRINT_INDEXED_LABELS, SqliteGraphStore;
18157
18159
  var init_store = __esm({
18158
18160
  "../../packages/local-graph/src/store.ts"() {
18159
18161
  "use strict";
@@ -18184,6 +18186,7 @@ var init_store = __esm({
18184
18186
  REGRESSION_OF: { from: ["Problem"], to: ["Problem"] }
18185
18187
  };
18186
18188
  SCHEMA_VERSION = 6;
18189
+ SESSION_EVIDENCE_PREDICATE = SESSION_EVIDENCE_FIELDS.map((field) => `instr(attrs_json, '${JSON.stringify(field)}') > 0`).join(" OR ");
18187
18190
  SCHEMA_SQL = `
18188
18191
  CREATE TABLE IF NOT EXISTS schema_version (
18189
18192
  version INTEGER PRIMARY KEY
@@ -18276,6 +18279,10 @@ CREATE UNIQUE INDEX IF NOT EXISTS edges_triple ON edges(from_id, type, to_id);
18276
18279
  `;
18277
18280
  TEMPORAL_INDEX_SQL = `
18278
18281
  CREATE INDEX IF NOT EXISTS nodes_live ON nodes(label, valid_to);
18282
+ CREATE INDEX IF NOT EXISTS nodes_live_count ON nodes(valid_to);
18283
+ CREATE INDEX IF NOT EXISTS nodes_live_recent ON nodes(label, last_updated_at DESC) WHERE valid_to IS NULL;
18284
+ CREATE INDEX IF NOT EXISTS nodes_session_evidence ON nodes(id) WHERE ${SESSION_EVIDENCE_PREDICATE};
18285
+ CREATE INDEX IF NOT EXISTS edges_session_evidence ON edges(id) WHERE ${SESSION_EVIDENCE_PREDICATE};
18279
18286
  -- Covering + partial index for labelFingerprint over the instance labels: the
18280
18287
  -- live-push probe runs it per workspace on a timer, and each hit used to read
18281
18288
  -- its table row. Partial, so it maintains a few thousand rows instead of adding
@@ -18588,12 +18595,13 @@ CREATE INDEX IF NOT EXISTS nodes_anchor_hint_path ON nodes(json_extract(attrs_js
18588
18595
  });
18589
18596
  }
18590
18597
  repairSessionAliases(canonical, aliases = []) {
18598
+ if (canonical && aliases.length === 0) return 0;
18591
18599
  const mapping = new Map(aliases.map((alias) => [alias, canonical]));
18592
18600
  let changed = 0;
18593
18601
  for (const table of ["nodes", "edges"]) {
18594
18602
  const predicates = canonical ? aliases.map(() => "instr(attrs_json, ?) > 0") : ["instr(attrs_json, 'codex:') > 0", "instr(attrs_json, 'discriminatorSource') > 0"];
18595
18603
  if (!predicates.length) continue;
18596
- const rows = this.db.prepare(`SELECT id, attrs_json FROM ${table} WHERE ${predicates.join(" OR ")}`).all(...canonical ? aliases : []);
18604
+ const rows = this.db.prepare(`SELECT id, attrs_json FROM ${table} WHERE (${SESSION_EVIDENCE_PREDICATE}) AND (${predicates.join(" OR ")})`).all(...canonical ? aliases.map((alias) => JSON.stringify(alias)) : []);
18597
18605
  const update = this.db.prepare(`UPDATE ${table} SET attrs_json = ?${table === "edges" ? ", type = CASE WHEN type = 'CONFIRMS' AND json_extract(?, '$.provisional') = 1 THEN 'INDICATES' ELSE type END" : ""} WHERE id = ?`);
18598
18606
  for (const row of rows) {
18599
18607
  const attrs = JSON.stringify(repairSessionEvidence(JSON.parse(row.attrs_json), mapping));
@@ -18819,6 +18827,25 @@ CREATE INDEX IF NOT EXISTS nodes_anchor_hint_path ON nodes(json_extract(attrs_js
18819
18827
  const rows = this.db.prepare("SELECT id FROM nodes WHERE label = ? AND valid_to IS NULL ORDER BY last_updated_at DESC LIMIT ?").all(label, Math.max(0, limit));
18820
18828
  return rows.map((r) => r.id);
18821
18829
  }
18830
+ recentOpenProblemCandidates(opts) {
18831
+ if (!Number.isSafeInteger(opts.limit) || opts.limit < 0) {
18832
+ throw new RangeError("candidate limit must be a non-negative safe integer");
18833
+ }
18834
+ return this.db.prepare(`SELECT id, description FROM nodes
18835
+ WHERE label = 'Problem' AND valid_to IS NULL
18836
+ AND json_extract(attrs_json, '$.resolvedAt') IS NULL
18837
+ AND json_type(attrs_json, '$.mergedInto') IS NULL
18838
+ AND (? IS NULL OR id != ?)
18839
+ AND (json_type(attrs_json, '$.workspaceId') IS NULL OR json_extract(attrs_json, '$.workspaceId') = ?)
18840
+ AND COALESCE(json_extract(attrs_json, '$.kind') = 'constraint', 0) = ?
18841
+ ORDER BY last_updated_at DESC, rowid ASC LIMIT ?`).all(
18842
+ opts.excludeId ?? null,
18843
+ opts.excludeId ?? null,
18844
+ opts.workspaceId,
18845
+ opts.constraint ? 1 : 0,
18846
+ opts.limit
18847
+ );
18848
+ }
18822
18849
  hasLiveNodes() {
18823
18850
  const r = this.db.prepare("SELECT EXISTS(SELECT 1 FROM nodes WHERE valid_to IS NULL) AS e").get();
18824
18851
  return r.e === 1;
@@ -24132,10 +24159,12 @@ function markFoldCandidate(store, problemId, targetId, info2) {
24132
24159
  }
24133
24160
  function findWorkspaceFoldCandidate(store, workspaceId2, statement, kind, opts) {
24134
24161
  const stmtVec = embed(statement);
24135
- const wantConstraint = kind === "constraint";
24136
- const open2 = store.findNodesByLabel("Problem").filter(
24137
- (p) => p.attrs["resolvedAt"] == null && p.attrs["mergedInto"] === void 0 && p.id !== opts?.excludeId && (p.attrs["workspaceId"] === void 0 || p.attrs["workspaceId"] === workspaceId2) && isConstraintProblem(p) === wantConstraint
24138
- ).sort((a, b) => (b.lastUpdatedAt ?? b.createdAt) - (a.lastUpdatedAt ?? a.createdAt)).slice(0, opts?.scanCap ?? WORKSPACE_SCAN_CAP);
24162
+ const open2 = store.recentOpenProblemCandidates({
24163
+ workspaceId: workspaceId2,
24164
+ constraint: kind === "constraint",
24165
+ limit: opts?.scanCap ?? WORKSPACE_SCAN_CAP,
24166
+ ...opts?.excludeId !== void 0 ? { excludeId: opts.excludeId } : {}
24167
+ });
24139
24168
  let best = null;
24140
24169
  for (const p of open2) {
24141
24170
  const c = cosine(stmtVec, embed(p.description));
@@ -77859,6 +77888,15 @@ var PassWorker = class {
77859
77888
  nightly() {
77860
77889
  return this.call("nightly");
77861
77890
  }
77891
+ semanticMaintenance() {
77892
+ return this.call("semanticMaintenance");
77893
+ }
77894
+ liveness(invocations) {
77895
+ return this.call("liveness", [...invocations]);
77896
+ }
77897
+ retrievalInputs(repoLocator) {
77898
+ return this.call("retrievalInputs", repoLocator);
77899
+ }
77862
77900
  /** Reindex stale/drifted files on the worker; resolves to the count reindexed. */
77863
77901
  reconcile() {
77864
77902
  return this.call("reconcile");
@@ -78986,6 +79024,13 @@ function scanManifests(root) {
78986
79024
  function readManifestDependencies(root) {
78987
79025
  return scanManifests(root).deps;
78988
79026
  }
79027
+ function readRetrievalInputs(root, repoLocator) {
79028
+ return {
79029
+ direct: readDirectDependencies(root),
79030
+ manifestDeps: readManifestDependencies(root),
79031
+ registry: loadRegistryPolicy(root, process.env, repoLocator)
79032
+ };
79033
+ }
78989
79034
 
78990
79035
  // src/git-sensor.ts
78991
79036
  import { existsSync as existsSync23, readFileSync as readFileSync23, watch as fsWatch } from "node:fs";
@@ -81354,11 +81399,13 @@ function saveAlarmState(configDir, state) {
81354
81399
  }
81355
81400
  function createLivenessWatch(deps) {
81356
81401
  let lastRunAt = 0;
81402
+ let running = false;
81357
81403
  const lastAlarmedAt = loadAlarmState(deps.configDir);
81358
81404
  return {
81359
- maybeRun(nowMs = Date.now()) {
81360
- if (nowMs - lastRunAt < LIVENESS_WATCH_INTERVAL_MS) return null;
81405
+ async maybeRun(nowMs = Date.now()) {
81406
+ if (running || nowMs - lastRunAt < LIVENESS_WATCH_INTERVAL_MS) return null;
81361
81407
  lastRunAt = nowMs;
81408
+ running = true;
81362
81409
  try {
81363
81410
  const started2 = Date.now();
81364
81411
  const invocations = /* @__PURE__ */ new Map();
@@ -81372,7 +81419,7 @@ function createLivenessWatch(deps) {
81372
81419
  lastTotals: s.lastTotals
81373
81420
  });
81374
81421
  }
81375
- const rows = evaluateMechanisms(deps.store, invocations);
81422
+ const rows = deps.evaluate ? await deps.evaluate(invocations) : evaluateMechanisms(deps.store, invocations);
81376
81423
  const workspaceActive = invocations.has("capture") || invocations.has("render");
81377
81424
  const bad = workspaceActive ? rows.filter((r) => hasStarvedMechanism([r])) : [];
81378
81425
  const watch3 = watchCensus();
@@ -81409,13 +81456,42 @@ function createLivenessWatch(deps) {
81409
81456
  }
81410
81457
  }
81411
81458
  return rows;
81412
- } catch {
81459
+ } catch (err2) {
81460
+ console.warn("[errata] liveness watch failed:", err2 instanceof Error ? err2.message : String(err2));
81413
81461
  return null;
81462
+ } finally {
81463
+ running = false;
81414
81464
  }
81415
81465
  }
81416
81466
  };
81417
81467
  }
81418
81468
 
81469
+ // src/workspace-maintenance.ts
81470
+ init_src8();
81471
+ init_src5();
81472
+ function runWorkspaceMaintenance(store, workspaceId2) {
81473
+ const seqBefore = store.currentIngestSeq();
81474
+ const report = runSemanticMaintenance(store);
81475
+ let hintUpgrade = { upgraded: 0, standing: 0, unresolvable: 0, blocked: 0 };
81476
+ try {
81477
+ hintUpgrade = upgradeAnchorHints(store, workspaceId2, Date.now());
81478
+ } catch {
81479
+ }
81480
+ let calibration = null;
81481
+ const calibrationStarted = Date.now();
81482
+ try {
81483
+ calibration = wmCalibrationCells(store);
81484
+ } catch {
81485
+ }
81486
+ return {
81487
+ report,
81488
+ hintUpgrade,
81489
+ seqAdvanced: store.currentIngestSeq() - seqBefore,
81490
+ calibration,
81491
+ calibrationMs: Date.now() - calibrationStarted
81492
+ };
81493
+ }
81494
+
81419
81495
  // src/watch-breaker.ts
81420
81496
  function numEnv3(key, fallback) {
81421
81497
  const n = Number(process.env[key]);
@@ -81517,7 +81593,7 @@ function createWatchBreaker(deps) {
81517
81593
  }
81518
81594
 
81519
81595
  // src/engine.ts
81520
- var DAEMON_VERSION = true ? "2.0.17-dev.3369" : "2.0.0-alpha.0";
81596
+ var DAEMON_VERSION = true ? "2.0.17-dev.3407" : "2.0.0-alpha.0";
81521
81597
  var IGNORED_PATH = /[\\/](?:\.git|node_modules|\.errata|\.claude|\.codex|\.cursor|\.turbo|\.next|dist|coverage|test-results|playwright-report|__pycache__)(?:[\\/]|$)/;
81522
81598
  var IGNORED_NOISE = /castalia\.db|eventlog\.sqlite|turn-cursors/;
81523
81599
  var GIT_OP_MUTE_MS = 4e3;
@@ -81904,6 +81980,7 @@ function createWorkspaceEngine(opts) {
81904
81980
  const livenessWatch = createLivenessWatch({
81905
81981
  configDir: paths.configDir,
81906
81982
  store,
81983
+ ...passWorker ? { evaluate: (invocations) => passWorker.liveness(invocations) } : {},
81907
81984
  onAlarm: (id, line) => {
81908
81985
  console.warn(`[errata] mechanism not working: ${line}`);
81909
81986
  notifyEvent("mechanism-stalled", line, { key: id });
@@ -82069,21 +82146,22 @@ function createWorkspaceEngine(opts) {
82069
82146
  contextDirty = false;
82070
82147
  notifyDigest("recall");
82071
82148
  };
82072
- const outboundStack = () => retrievalStackTokens({
82073
- direct: readDirectDependencies(opts.workspaceRoot),
82074
- manifestDeps: readManifestDependencies(opts.workspaceRoot),
82075
- profileStack: profile?.stack ?? [],
82076
- // Languages ride the stack list: the cloud's context-affinity matcher
82077
- // resolves each token against both the Package and Language namespaces,
82078
- // and the profile keeps them in separate fields.
82079
- languages: profile?.languages ?? [],
82080
- contributePackages: consentNow().contributePackages,
82081
- // `repoLocator` feeds the Maven self-disclosure rule ONLY: a groupId
82082
- // carrying this project's own owner/repo token is the project naming
82083
- // itself, not a library it depends on.
82084
- registry: loadRegistryPolicy(opts.workspaceRoot, process.env, profile?.repoLocator),
82085
- ignorePatterns: loadClaimIgnorePatterns(opts.workspaceRoot)
82086
- }).tokens;
82149
+ const outboundStack = async () => {
82150
+ const inputs = passWorker ? await passWorker.retrievalInputs(profile?.repoLocator) : readRetrievalInputs(opts.workspaceRoot, profile?.repoLocator);
82151
+ return retrievalStackTokens({
82152
+ ...inputs,
82153
+ profileStack: profile?.stack ?? [],
82154
+ // Languages ride the stack list: the cloud's context-affinity matcher
82155
+ // resolves each token against both the Package and Language namespaces,
82156
+ // and the profile keeps them in separate fields.
82157
+ languages: profile?.languages ?? [],
82158
+ contributePackages: consentNow().contributePackages,
82159
+ // `repoLocator` feeds the Maven self-disclosure rule ONLY: a groupId
82160
+ // carrying this project's own owner/repo token is the project naming
82161
+ // itself, not a library it depends on.
82162
+ ignorePatterns: loadClaimIgnorePatterns(opts.workspaceRoot)
82163
+ }).tokens;
82164
+ };
82087
82165
  const maybeRefreshRemotePriors = () => {
82088
82166
  if (opts.skipContextWriter || remoteInFlight) return;
82089
82167
  const now = Date.now();
@@ -82093,11 +82171,12 @@ function createWorkspaceEngine(opts) {
82093
82171
  if (typeof cloud.search !== "function") return;
82094
82172
  remoteInFlight = true;
82095
82173
  lastRemoteAt = now;
82096
- try {
82174
+ void outboundStack().then((stack) => {
82175
+ if (!(opts.syncConsent ?? consentNow().sync)) return;
82097
82176
  const norm = normStackTokens;
82098
82177
  const seed = store.recentNodeIds("Problem", 6);
82099
82178
  const q = {
82100
- stack: outboundStack(),
82179
+ stack,
82101
82180
  domains: norm(profile.domains),
82102
82181
  kinds: ["Pattern", "Technique", "AntiPattern"],
82103
82182
  ...seed.length ? { seed } : {},
@@ -82107,7 +82186,7 @@ function createWorkspaceEngine(opts) {
82107
82186
  channel: "priming",
82108
82187
  limit: 8
82109
82188
  };
82110
- cloud.search(q).then((res) => {
82189
+ return cloud.search(q).then((res) => {
82111
82190
  remotePriors = res.nodes ?? [];
82112
82191
  const contributorLabels = [];
82113
82192
  for (const n of remotePriors) {
@@ -82117,13 +82196,11 @@ function createWorkspaceEngine(opts) {
82117
82196
  }
82118
82197
  if (contributorLabels.length > 0) registerRenderedContributorLabels(contributorLabels);
82119
82198
  contextDirty = true;
82120
- }).catch(() => {
82121
- }).finally(() => {
82122
- remoteInFlight = false;
82123
82199
  });
82124
- } catch {
82200
+ }).catch(() => {
82201
+ }).finally(() => {
82125
82202
  remoteInFlight = false;
82126
- }
82203
+ });
82127
82204
  };
82128
82205
  const maybeRefreshIntentPriors = (liveIntent) => {
82129
82206
  if (!liveIntent || opts.skipContextWriter || intentRemoteInFlight) return;
@@ -82132,22 +82209,26 @@ function createWorkspaceEngine(opts) {
82132
82209
  if (!syncOk) return;
82133
82210
  if (typeof cloud.search !== "function") return;
82134
82211
  intentRemoteInFlight = true;
82135
- cloud.search({
82136
- // VS-context-affinity: the intent lane used to send an empty context
82137
- // while the priming lane sent the profile — opposite postures on the
82138
- // same method. Under "union derived + stated, canonicalize once"
82139
- // (VS-intent-fence) the stated intent IS the query and the derived
82140
- // stack rides along as structured relevanceContext: the cloud no
82141
- // longer concatenates these tokens into the embedding string, it
82142
- // re-weights anchored hits with them (stated beats derived — the
82143
- // intent text drives entry search, the stack only re-ranks).
82144
- stack: outboundStack(),
82145
- domains: normStackTokens(profile?.domains ?? []),
82146
- kinds: ["Pattern", "Technique", "AntiPattern", "Problem", "Solution"],
82147
- q: liveIntent,
82148
- channel: "intent",
82149
- limit: 6
82212
+ void outboundStack().then((stack) => {
82213
+ if (!(opts.syncConsent ?? consentNow().sync)) return;
82214
+ return cloud.search({
82215
+ // VS-context-affinity: the intent lane used to send an empty context
82216
+ // while the priming lane sent the profile — opposite postures on the
82217
+ // same method. Under "union derived + stated, canonicalize once"
82218
+ // (VS-intent-fence) the stated intent IS the query and the derived
82219
+ // stack rides along as structured relevanceContext: the cloud no
82220
+ // longer concatenates these tokens into the embedding string, it
82221
+ // re-weights anchored hits with them (stated beats derived — the
82222
+ // intent text drives entry search, the stack only re-ranks).
82223
+ stack,
82224
+ domains: normStackTokens(profile?.domains ?? []),
82225
+ kinds: ["Pattern", "Technique", "AntiPattern", "Problem", "Solution"],
82226
+ q: liveIntent,
82227
+ channel: "intent",
82228
+ limit: 6
82229
+ });
82150
82230
  }).then((res) => {
82231
+ if (!res) return;
82151
82232
  intentRemote = {
82152
82233
  forIntent: liveIntent,
82153
82234
  hits: res.nodes ?? [],
@@ -82207,7 +82288,7 @@ function createWorkspaceEngine(opts) {
82207
82288
  if (isWorkerOom(err2)) {
82208
82289
  console.warn("[errata] nightly worker hit its heap ceiling \u2014 heavy pass skipped this fire");
82209
82290
  appendPassLedger(paths.configDir, "graph-rescore", 0, { oomSkipped: 1 });
82210
- const sem = runSemanticMaintenance(store);
82291
+ const { report: sem } = await passWorker.semanticMaintenance();
82211
82292
  return {
82212
82293
  report: {
82213
82294
  scoredNodes: 0,
@@ -83727,15 +83808,7 @@ B: ${b}`,
83727
83808
  return report;
83728
83809
  },
83729
83810
  async semanticMaintenance() {
83730
- const yieldLoop = () => new Promise((r) => setImmediate(r));
83731
- const seqBefore = store.currentIngestSeq();
83732
- const report = runSemanticMaintenance(store);
83733
- await yieldLoop();
83734
- let hintUpgrade = { upgraded: 0, standing: 0, unresolvable: 0, blocked: 0 };
83735
- try {
83736
- hintUpgrade = upgradeAnchorHints(store, profile.id, Date.now());
83737
- } catch {
83738
- }
83811
+ const { report, hintUpgrade, seqAdvanced, calibration, calibrationMs } = passWorker ? await passWorker.semanticMaintenance() : runWorkspaceMaintenance(store, profile.id);
83739
83812
  appendPassLedger(paths.configDir, "semantic-maintenance", report.durationMs, {
83740
83813
  revisitsCleared: report.revisitsCleared,
83741
83814
  revisitsStanding: report.revisitsStanding,
@@ -83746,7 +83819,7 @@ B: ${b}`,
83746
83819
  fixCandidatesStanding: report.fixCandidates.standing,
83747
83820
  designResolved: report.designResolved,
83748
83821
  claimsEvaluated: report.claimsEvaluated,
83749
- seqAdvanced: store.currentIngestSeq() - seqBefore,
83822
+ seqAdvanced,
83750
83823
  anchorHintsUpgraded: hintUpgrade.upgraded,
83751
83824
  anchorHintsStanding: hintUpgrade.standing,
83752
83825
  anchorHintsUnresolvable: hintUpgrade.unresolvable,
@@ -83755,19 +83828,15 @@ B: ${b}`,
83755
83828
  if (report.revisitsCleared > 0 || report.fixCandidatesSettled > 0 || report.designResolved > 0) {
83756
83829
  refreshContextNow();
83757
83830
  }
83758
- await yieldLoop();
83759
- try {
83760
- const t0 = Date.now();
83831
+ if (calibration) {
83761
83832
  appendPassLedger(
83762
83833
  paths.configDir,
83763
83834
  "wm-calibration",
83764
- Date.now() - t0,
83765
- wmCalibrationCells(store)
83835
+ calibrationMs,
83836
+ calibration
83766
83837
  );
83767
- } catch {
83768
83838
  }
83769
- await yieldLoop();
83770
- livenessWatch.maybeRun();
83839
+ await livenessWatch.maybeRun();
83771
83840
  return report;
83772
83841
  },
83773
83842
  async nightly() {
@@ -84677,7 +84746,7 @@ function stripCodebaseScope(scope) {
84677
84746
  return s;
84678
84747
  }
84679
84748
  function compositionCounters(c) {
84680
- const { sidecarDropReasons, ...scalars } = c;
84749
+ const { sidecarDropReasons, ...scalars2 } = c;
84681
84750
  const buckets = [
84682
84751
  "empty",
84683
84752
  "too_long",
@@ -84687,7 +84756,7 @@ function compositionCounters(c) {
84687
84756
  "other"
84688
84757
  ];
84689
84758
  return {
84690
- ...scalars,
84759
+ ...scalars2,
84691
84760
  ...Object.fromEntries(buckets.map((b) => [`sidecarDrop_${b}`, sidecarDropReasons[b] ?? 0]))
84692
84761
  };
84693
84762
  }
@@ -85722,38 +85791,41 @@ function classifyAnchorVersion(cloudAttrs, localSymbol) {
85722
85791
  if (typeof seen !== "string" || typeof have !== "string") return "unverified";
85723
85792
  return seen === have ? "current" : "pre-change";
85724
85793
  }
85725
- function buildReverseSymbolMap(opts) {
85726
- return collectFirstWins(reverseSymbolEntries(opts));
85794
+ async function buildReverseSymbolMap(opts) {
85795
+ return collectFirstWinsYielding(reverseSymbolEntries(opts));
85727
85796
  }
85728
85797
  function* reverseSymbolEntries(opts) {
85729
85798
  const { store, salt, projectId } = opts;
85730
85799
  for (const kind of ANCHOR_SYMBOL_KINDS2) {
85731
85800
  for (const n of store.iterateNodeIdentitiesByLabel(kind)) {
85732
85801
  const { relPath, qname } = n;
85733
- if (relPath === null || qname === null) continue;
85802
+ if (relPath === null || qname === null) {
85803
+ yield null;
85804
+ continue;
85805
+ }
85734
85806
  const sym = projectSymbolId(salt, projectId, relPath, qname, kind);
85735
85807
  yield [sym, n.id];
85736
85808
  yield [projectSaltedNodeId(sym, salt), n.id];
85737
85809
  }
85738
85810
  }
85739
85811
  for (const n of store.iterateNodeIdentitiesByLabel("File")) {
85740
- if (n.relPath === null) continue;
85812
+ if (n.relPath === null) {
85813
+ yield null;
85814
+ continue;
85815
+ }
85741
85816
  const sym = projectSymbolId(salt, projectId, n.relPath, FILE_ANCHOR_QNAME, "File");
85742
85817
  yield [sym, n.id];
85743
85818
  yield [projectSaltedNodeId(sym, salt), n.id];
85744
85819
  }
85745
85820
  }
85746
- function collectFirstWins(entries) {
85747
- const m = /* @__PURE__ */ new Map();
85748
- for (const [k, v] of entries) if (!m.has(k)) m.set(k, v);
85749
- return m;
85750
- }
85751
85821
  var MAP_BUILD_BATCH = 2e3;
85752
85822
  async function collectFirstWinsYielding(entries) {
85753
85823
  const m = /* @__PURE__ */ new Map();
85754
85824
  let i2 = 0;
85755
- for (const [k, v] of entries) {
85825
+ for (const entry of entries) {
85756
85826
  if (++i2 % MAP_BUILD_BATCH === 0) await new Promise((r) => setImmediate(r));
85827
+ if (entry === null) continue;
85828
+ const [k, v] = entry;
85757
85829
  if (!m.has(k)) m.set(k, v);
85758
85830
  }
85759
85831
  return m;
@@ -85845,7 +85917,7 @@ async function reanchorProject(opts) {
85845
85917
  if (!profile.projectId) return { reanchored: false, reason: "no-project" };
85846
85918
  if (profile.projectReanchoredAt) return { reanchored: false, reason: "already-reanchored" };
85847
85919
  if (!profile.projectHydratedAt) return { reanchored: false, reason: "not-hydrated" };
85848
- const reverse = buildReverseSymbolMap({ store, salt, projectId: profile.projectId });
85920
+ const reverse = await buildReverseSymbolMap({ store, salt, projectId: profile.projectId });
85849
85921
  if (reverse.size === 0) return { reanchored: false, reason: "no-local-symbols" };
85850
85922
  try {
85851
85923
  const res = await cloud.getProjectPriors(profile.projectId, opts.limit ?? DEFAULT_LIMIT);
@@ -85907,7 +85979,7 @@ async function syncProjectAnchors(opts) {
85907
85979
  reverseCache,
85908
85980
  store,
85909
85981
  key,
85910
- () => collectFirstWinsYielding(reverseSymbolEntries({ store, salt, projectId }))
85982
+ () => buildReverseSymbolMap({ store, salt, projectId })
85911
85983
  );
85912
85984
  const own = cachedMap(ownCache, store, salt, () => collectLastWinsYielding(ownKnowledgeEntries({ store, salt })));
85913
85985
  const limit = opts.limit ?? SYNC_PAGE;
@@ -86080,11 +86152,11 @@ async function syncHistoryRevisionPage(opts) {
86080
86152
  const sweepCommit = after ? oldCursor.atCommit : atCommit;
86081
86153
  const page = await cloud.getHistoryOccurrences(projectId, atCommit, after);
86082
86154
  if (!Array.isArray(page.occurrences) || page.occurrences.length > 50 || page.occurrences.some((o, i2) => o.occurrenceId <= (page.occurrences[i2 - 1]?.occurrenceId ?? after ?? "")) || page.cursor !== null && page.cursor !== page.occurrences.at(-1)?.occurrenceId) throw new Error("invalid history occurrence page");
86083
- const parents = (await git3(["rev-list", "--parents", "--max-count=8192", atCommit])).trim().split("\n").filter(Boolean).map((row) => {
86155
+ const parents = page.occurrences.length ? (await git3(["rev-list", "--parents", "--max-count=8192", atCommit])).trim().split("\n").filter(Boolean).map((row) => {
86084
86156
  const [commit, ...parents2] = row.trim().split(/\s+/);
86085
86157
  return { commit, parents: parents2 };
86086
- });
86087
- const reverse = buildReverseSymbolMap({ store, projectId, salt });
86158
+ }) : [];
86159
+ const reverse = page.occurrences.length ? await buildReverseSymbolMap({ store, projectId, salt }) : /* @__PURE__ */ new Map();
86088
86160
  const ignore2 = loadRepoIgnore(root, profile.ignoreExtra ?? []);
86089
86161
  const providers = defaultProviders();
86090
86162
  const parsedFiles = /* @__PURE__ */ new Map();
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@inerrata-corporation/errata",
3
- "version": "2.0.17-dev.3369",
3
+ "version": "2.0.17-dev.3407",
4
4
  "description": "errata - local-first observation engine for AI coding agents",
5
5
  "type": "module",
6
6
  "bin": {