mason-context 0.21.0 → 0.22.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.
@@ -31,7 +31,7 @@ var init_types = __esm({
31
31
  });
32
32
 
33
33
  // src/drift/cli.ts
34
- import path11 from "path";
34
+ import path9 from "path";
35
35
 
36
36
  // src/utils/git-read.ts
37
37
  import { execFile } from "child_process";
@@ -84,10 +84,7 @@ function execGit(args, options) {
84
84
 
85
85
  // src/drift/drift.ts
86
86
  import fs4 from "fs/promises";
87
- import path6 from "path";
88
-
89
- // src/snapshot/snapshot.ts
90
- import path5 from "path";
87
+ import path4 from "path";
91
88
 
92
89
  // src/utils/validation.ts
93
90
  function isRecord(value) {
@@ -413,9 +410,6 @@ import fs3 from "fs/promises";
413
410
  import os from "os";
414
411
  var lockOwnerSchema = z.object({ host: z.string(), pid: z.number().int().positive() });
415
412
 
416
- // src/test-map.ts
417
- import path4 from "path";
418
-
419
413
  // src/snapshot/snapshot.ts
420
414
  var repoPath = z2.string().refine((value) => normalizeRepoPath(value) !== null, "Expected a relative repository path");
421
415
  var verificationFields = {
@@ -550,7 +544,7 @@ async function findGhostFiles(resolvedRoot, mappedFiles) {
550
544
  const ghosts = [];
551
545
  for (const file of mappedFiles) {
552
546
  try {
553
- await fs4.access(path6.join(resolvedRoot, file));
547
+ await fs4.access(path4.join(resolvedRoot, file));
554
548
  } catch {
555
549
  ghosts.push(file);
556
550
  }
@@ -558,7 +552,7 @@ async function findGhostFiles(resolvedRoot, mappedFiles) {
558
552
  return ghosts.sort();
559
553
  }
560
554
  async function computeDrift(rootDir) {
561
- const root = path6.resolve(rootDir);
555
+ const root = path4.resolve(rootDir);
562
556
  const snapshot = await loadSnapshot(root);
563
557
  if (!snapshot) return null;
564
558
  const [headHash, workingTree] = await Promise.all([
@@ -673,11 +667,11 @@ import fg3 from "fast-glob";
673
667
  // src/audit/inspection.ts
674
668
  import fg2 from "fast-glob";
675
669
  import { AsyncLocalStorage as AsyncLocalStorage2 } from "async_hooks";
676
- import path7 from "path";
670
+ import path5 from "path";
677
671
  var inspections = new AsyncLocalStorage2();
678
672
  function inspectionRead(root, key, read) {
679
673
  const inspection = inspections.getStore();
680
- if (!inspection || inspection.root !== path7.resolve(root)) return read();
674
+ if (!inspection || inspection.root !== path5.resolve(root)) return read();
681
675
  if (!inspection.reads.has(key)) {
682
676
  const pending = read();
683
677
  inspection.reads.set(key, pending);
@@ -817,16 +811,16 @@ function changedCaptureFiles(before, after) {
817
811
  }
818
812
 
819
813
  // src/decisions/drift.ts
820
- import path10 from "path";
814
+ import path8 from "path";
821
815
 
822
816
  // src/decisions/decisions.ts
823
817
  import fs6 from "fs/promises";
824
- import path9 from "path";
818
+ import path7 from "path";
825
819
  import { createHash as createHash3 } from "crypto";
826
820
  import { z as z5 } from "zod";
827
821
 
828
822
  // src/context/lexical.ts
829
- import path8 from "path";
823
+ import path6 from "path";
830
824
 
831
825
  // src/decisions/provenance.ts
832
826
  import { z as z4 } from "zod";
@@ -908,6 +902,7 @@ var currentSchema = legacySchema.extend({
908
902
  inspector: text(200),
909
903
  note: text(1500),
910
904
  outcome: z4.literal("no_contradiction_found"),
905
+ scope: z4.literal("operative").optional(),
911
906
  decisionDigest: z4.string().regex(/^[a-f0-9]{64}$/),
912
907
  headHash: z4.string(),
913
908
  capture: anchorCaptureSchema
@@ -991,8 +986,19 @@ function effectiveDecision(record) {
991
986
  history: record.history.slice(0, index + 1)
992
987
  };
993
988
  }
994
- function decisionInspectionDigest(record) {
989
+ function decisionInspectionDigest(record, scope = "all") {
995
990
  const effective = effectiveDecision(record);
991
+ if (scope === "operative")
992
+ return createHash2("sha256").update(
993
+ JSON.stringify([
994
+ "operative",
995
+ record.status,
996
+ decisionApproval(effective),
997
+ effective.version === 2 ? effective.revision : 0,
998
+ decisionContent(effective),
999
+ effective.refreshedHash
1000
+ ])
1001
+ ).digest("hex");
996
1002
  return createHash2("sha256").update(
997
1003
  JSON.stringify([
998
1004
  record.status,
@@ -1004,8 +1010,10 @@ function decisionInspectionDigest(record) {
1004
1010
  ])
1005
1011
  ).digest("hex");
1006
1012
  }
1007
- function latestDecisionInspection(record) {
1008
- return record.version === 2 ? record.inspections?.filter((i) => i.decisionDigest === decisionInspectionDigest(record)).at(-1) : void 0;
1013
+ function latestDecisionInspection(record, scope = "all") {
1014
+ return record.version === 2 ? record.inspections?.filter(
1015
+ (i) => (scope === "operative" || i.scope !== "operative") && i.decisionDigest === decisionInspectionDigest(record, i.scope ?? "all")
1016
+ ).at(-1) : void 0;
1009
1017
  }
1010
1018
 
1011
1019
  // src/decisions/decisions.ts
@@ -1086,7 +1094,7 @@ async function loadDecisionStore(rootDir) {
1086
1094
 
1087
1095
  // src/decisions/drift.ts
1088
1096
  async function computeDecisionDrift(rootDir, decisions) {
1089
- const resolvedRoot = path10.resolve(rootDir);
1097
+ const resolvedRoot = path8.resolve(rootDir);
1090
1098
  const store = decisions ? { records: decisions, diagnostics: [] } : await loadDecisionStore(resolvedRoot);
1091
1099
  const report = {
1092
1100
  historyAvailable: true,
@@ -1101,11 +1109,15 @@ async function computeDecisionDrift(rootDir, decisions) {
1101
1109
  ]);
1102
1110
  const changesByHash = /* @__PURE__ */ new Map();
1103
1111
  const baselines = store.records.filter((record) => record.status === "active").flatMap((record) => {
1104
- const inspection = latestDecisionInspection(record);
1105
- if (inspection) return [inspection.capture];
1106
- return [.../* @__PURE__ */ new Set([effectiveDecision(record), record])].flatMap(
1107
- (candidate) => candidate.version === 2 && candidate.capture ? [candidate.capture] : []
1108
- );
1112
+ const effective = effectiveDecision(record);
1113
+ return [.../* @__PURE__ */ new Set([effective, record])].flatMap((candidate) => {
1114
+ const inspection = latestDecisionInspection(
1115
+ record,
1116
+ candidate === effective && decisionApproval(effective) === "accepted" ? "operative" : "all"
1117
+ );
1118
+ const capture = inspection?.capture ?? (candidate.version === 2 ? candidate.capture : void 0);
1119
+ return capture ? [capture] : [];
1120
+ });
1109
1121
  });
1110
1122
  const captures = await captureAnchorScopes(
1111
1123
  resolvedRoot,
@@ -1144,12 +1156,18 @@ async function computeDecisionDrift(rootDir, decisions) {
1144
1156
  for (const record of store.records) {
1145
1157
  if (record.status !== "active") continue;
1146
1158
  const effective = effectiveDecision(record);
1147
- const inspection = latestDecisionInspection(record);
1159
+ const inspection = latestDecisionInspection(
1160
+ record,
1161
+ decisionApproval(effective) === "accepted" ? "operative" : "all"
1162
+ );
1148
1163
  const state = await inspect(effective, inspection?.capture);
1149
1164
  report.freshness[record.id] = state.freshness;
1150
1165
  if (state.changedFiles.length) report.staleDecisions[record.id] = state.changedFiles;
1151
1166
  if (effective !== record)
1152
- (report.pendingProposals ??= {})[record.id] = await inspect(record, inspection?.capture);
1167
+ (report.pendingProposals ??= {})[record.id] = await inspect(
1168
+ record,
1169
+ latestDecisionInspection(record)?.capture
1170
+ );
1153
1171
  }
1154
1172
  return report;
1155
1173
  }
@@ -1270,18 +1288,14 @@ function formatRefreshPrompt(report, decisionDrift) {
1270
1288
  )
1271
1289
  );
1272
1290
  lines.push("");
1273
- const scopedFiles = [...report.changedFiles, ...report.unmappedFiles];
1274
- if (!report.historyAvailable || report.recommendation === "full-rebuild") {
1275
- lines.push(
1276
- "PROCEDURE (full rebuild): run the complete Map-Reduce build. Call generate_snapshot_batch repeatedly (follow nextOffset until null), calling save_partial_snapshot after each batch, then reduce_snapshot, then save_snapshot once with the unified map. Derive features ONLY from files shown in each batch prompt \u2014 never invent paths."
1277
- );
1278
- } else {
1291
+ lines.push(
1292
+ "PROCEDURE (scoped refresh): inspect the changed and unmapped files with your own source tools. Use get_snapshot to read the existing map, then save_snapshot with only evidence-supported corrected features/flows. Remove deleted entries with removeFeatures/removeFlows. Managed batch creation and reduction have been removed."
1293
+ );
1294
+ if (!report.historyAvailable || report.recommendation === "full-rebuild")
1279
1295
  lines.push(
1280
- "PROCEDURE (scoped refresh): call generate_snapshot_batch with the files list below \u2014 the SAME list on every call \u2014 following nextOffset until null, calling save_partial_snapshot after each batch. Then call reduce_snapshot (it merges into the existing map, preserving untouched entries) and save_snapshot once. Use save_snapshot's removeFeatures/removeFlows for features that no longer exist (see ghostFiles/renames). Derive features ONLY from files shown in each batch prompt \u2014 never invent paths."
1296
+ "History or coverage is insufficient for a bounded refresh. Inspect all affected entries directly; do not claim freshness for entries you have not checked."
1281
1297
  );
1282
- lines.push("");
1283
- lines.push(`files: ${JSON.stringify(scopedFiles)}`);
1284
- }
1298
+ lines.push(`files: ${JSON.stringify([...report.changedFiles, ...report.unmappedFiles])}`);
1285
1299
  const staleDecisionIds = Object.keys(decisionDrift.staleDecisions);
1286
1300
  if (staleDecisionIds.length > 0) {
1287
1301
  lines.push("");
@@ -1319,7 +1333,7 @@ async function runDriftCli(argv, io = {
1319
1333
  io.out(USAGE);
1320
1334
  return 0;
1321
1335
  }
1322
- const rootDir = path11.resolve(args.dir);
1336
+ const rootDir = path9.resolve(args.dir);
1323
1337
  let report;
1324
1338
  try {
1325
1339
  report = await computeDrift(rootDir);
@@ -1329,7 +1343,7 @@ async function runDriftCli(argv, io = {
1329
1343
  }
1330
1344
  if (!report) {
1331
1345
  io.err(
1332
- `No Mason snapshot found at ${path11.join(rootDir, ".mason", "snapshot.json")}. Build one via the Mason MCP server first.`
1346
+ `No Mason snapshot found at ${path9.join(rootDir, ".mason", "snapshot.json")}. Managed map creation has been removed; decisions and context work without a map.`
1333
1347
  );
1334
1348
  return 2;
1335
1349
  }