@ecoma-io/archkeep 0.25.0 → 0.26.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 (120) hide show
  1. package/cli.mjs +166 -506
  2. package/commands.mjs +7 -1
  3. package/package.json +1 -1
  4. package/src/architecture-intent/judge.mjs +1 -1
  5. package/src/architecture-intent/model.mjs +34 -0
  6. package/src/canonical.mjs +2 -1
  7. package/src/commands/adr-for-workspace.mjs +63 -0
  8. package/src/commands/analyze-capability.mjs +13 -0
  9. package/src/commands/change-intent.mjs +11 -0
  10. package/src/commands/change.mjs +247 -34
  11. package/src/commands/check-capability.mjs +13 -0
  12. package/src/commands/check.mjs +13 -3
  13. package/src/commands/compare-capability.mjs +20 -0
  14. package/src/commands/completeness.mjs +12 -0
  15. package/src/commands/context-command.mjs +31 -0
  16. package/src/commands/coverage-verdict.mjs +15 -2
  17. package/src/commands/debt.mjs +30 -0
  18. package/src/commands/decisions.mjs +59 -10
  19. package/src/commands/delta.mjs +263 -49
  20. package/src/commands/diff.mjs +45 -0
  21. package/src/commands/discover.mjs +37 -0
  22. package/src/commands/drift.mjs +45 -0
  23. package/src/commands/evolution.mjs +22 -2
  24. package/src/commands/explain-capability.mjs +11 -0
  25. package/src/commands/explain.mjs +24 -0
  26. package/src/commands/fitness.mjs +119 -10
  27. package/src/commands/govern-capability.mjs +16 -0
  28. package/src/commands/graph.mjs +39 -0
  29. package/src/commands/health.mjs +34 -0
  30. package/src/commands/history.mjs +85 -2
  31. package/src/commands/impact.mjs +23 -0
  32. package/src/commands/inspect-capability.mjs +16 -0
  33. package/src/commands/plan-context-command.mjs +35 -0
  34. package/src/commands/policy.mjs +42 -4
  35. package/src/commands/provenance-command.mjs +15 -24
  36. package/src/commands/report.mjs +38 -0
  37. package/src/commands/rules-capability.mjs +16 -0
  38. package/src/commands/rules.mjs +3 -1
  39. package/src/commands/scenario.mjs +23 -0
  40. package/src/commands/trajectory.mjs +35 -0
  41. package/src/commands/waivers.mjs +30 -0
  42. package/src/corpus/goldens/.gitkeep +0 -0
  43. package/src/corpus/goldens/adr.json +62 -0
  44. package/src/corpus/goldens/adr.text +6 -0
  45. package/src/corpus/goldens/change.json +98 -0
  46. package/src/corpus/goldens/change.text +6 -0
  47. package/src/corpus/goldens/check.json +90 -0
  48. package/src/corpus/goldens/check.sarif +479 -0
  49. package/src/corpus/goldens/check.text +9 -0
  50. package/src/corpus/goldens/context.json +47 -0
  51. package/src/corpus/goldens/context.text +6 -0
  52. package/src/corpus/goldens/debt.json +59 -0
  53. package/src/corpus/goldens/debt.text +7 -0
  54. package/src/corpus/goldens/decisions.json +74 -0
  55. package/src/corpus/goldens/decisions.text +7 -0
  56. package/src/corpus/goldens/delta.json +94 -0
  57. package/src/corpus/goldens/delta.sarif +472 -0
  58. package/src/corpus/goldens/delta.text +5 -0
  59. package/src/corpus/goldens/diff.json +58 -0
  60. package/src/corpus/goldens/diff.text +4 -0
  61. package/src/corpus/goldens/discover.json +77 -0
  62. package/src/corpus/goldens/discover.text +10 -0
  63. package/src/corpus/goldens/drift.json +43 -0
  64. package/src/corpus/goldens/drift.text +3 -0
  65. package/src/corpus/goldens/evolution.json +328 -0
  66. package/src/corpus/goldens/evolution.text +32 -0
  67. package/src/corpus/goldens/explain.json +60 -0
  68. package/src/corpus/goldens/explain.text +7 -0
  69. package/src/corpus/goldens/fitness.json +45 -0
  70. package/src/corpus/goldens/fitness.text +3 -0
  71. package/src/corpus/goldens/graph.json +78 -0
  72. package/src/corpus/goldens/graph.text +10 -0
  73. package/src/corpus/goldens/health.json +72 -0
  74. package/src/corpus/goldens/health.text +10 -0
  75. package/src/corpus/goldens/help.text +104 -0
  76. package/src/corpus/goldens/history.json +43 -0
  77. package/src/corpus/goldens/history.text +4 -0
  78. package/src/corpus/goldens/impact.json +327 -0
  79. package/src/corpus/goldens/impact.text +10 -0
  80. package/src/corpus/goldens/provenance.json +453 -0
  81. package/src/corpus/goldens/provenance.text +14 -0
  82. package/src/corpus/goldens/reconcile.json +168 -0
  83. package/src/corpus/goldens/reconcile.text +3 -0
  84. package/src/corpus/goldens/report.json +168 -0
  85. package/src/corpus/goldens/report.text +42 -0
  86. package/src/corpus/goldens/rules verify.json +0 -0
  87. package/src/corpus/goldens/rules verify.text +0 -0
  88. package/src/corpus/goldens/scenario.json +441 -0
  89. package/src/corpus/goldens/scenario.text +28 -0
  90. package/src/corpus/goldens/trajectory.json +83 -0
  91. package/src/corpus/goldens/trajectory.text +10 -0
  92. package/src/corpus/goldens/usage-error.text +105 -0
  93. package/src/corpus/goldens/waivers.json +40 -0
  94. package/src/corpus/goldens/waivers.text +1 -0
  95. package/src/corpus/goldens-lsp/initialize.result.json +15 -0
  96. package/src/corpus/goldens-lsp/publish-cleared-empty.json +4 -0
  97. package/src/corpus/goldens-lsp/publish-fixed-empty.json +5 -0
  98. package/src/corpus/goldens-lsp/publish-unparseable.json +54 -0
  99. package/src/corpus/goldens-lsp/publish-violation.json +22 -0
  100. package/src/corpus/goldens-lsp/register-watched-files.json +72 -0
  101. package/src/go-work.mjs +8 -23
  102. package/src/governance/evolution-event.mjs +15 -0
  103. package/src/governance/evolution-store.mjs +59 -31
  104. package/src/governance/provenance-record.mjs +0 -152
  105. package/src/governance/verdict.mjs +26 -3
  106. package/src/intent/intent-manifest.json +14 -14
  107. package/src/lsp/server.mjs +5 -8
  108. package/src/lsp/workspace-index.mjs +55 -220
  109. package/src/options.mjs +10 -0
  110. package/src/providers/native/discover.mjs +13 -12
  111. package/src/providers/native/model.mjs +8 -3
  112. package/src/providers/nx-static.mjs +231 -0
  113. package/src/report/json.mjs +3 -2
  114. package/src/report/sarif.mjs +8 -3
  115. package/src/rules/edge-constraints.mjs +9 -0
  116. package/src/rules/index.mjs +26 -10
  117. package/src/rules/messages.mjs +64 -14
  118. package/src/rules/specifiers.mjs +21 -20
  119. package/src/tsconfig-paths.mjs +8 -14
  120. package/src/verdict.mjs +127 -16
@@ -37,17 +37,8 @@
37
37
  * or a polluted prototype cannot smuggle keys into a validated origin. This
38
38
  * module builds nothing from untrusted keys; it validates and, at write time,
39
39
  * builds a fresh object with only the three permitted keys.
40
- * ## The decision-lifecycle record
41
- *
42
- * The same discipline extends from a row to a DECISION (an ADR id — the
43
- * stable handle later waves reference). `recordDecisionLifecycle` records one
44
- * lifecycle event — a status transition, a supersession, or a bindings
45
- * change — attributed by the same `origin` shape and the same clock door:
46
- * `by`/`tool` are required, and `on` comes from `recordOrigin` and nowhere
47
- * else. A record that records nothing (a no-op transition) is refused loudly.
48
40
  */
49
41
 
50
- import { ADR_STATUSES } from "./adr-registry.mjs";
51
42
  import { clockViolations } from "./clock.mjs";
52
43
  import { describe, isPlainObject } from "../values.mjs";
53
44
 
@@ -175,146 +166,3 @@ export function recordOrigin({ by, tool, clock }) {
175
166
  // record, so two calls with the same clock are byte-identical.
176
167
  return { by, tool, on: clock.now() };
177
168
  }
178
- /**
179
- * The decision-lifecycle events one record can hold, each a single fact about
180
- * ONE decision (an ADR id — `docs/adr/NNN-slug.md` — the stable handle the
181
- * registry's `byId` map keys on). A decision's creation and every status
182
- * change, supersession, and bindings change is recorded as one of these.
183
- */
184
- export const DECISION_LIFECYCLE_KINDS = Object.freeze([
185
- // used by its own test
186
- "status-transition",
187
- "supersession",
188
- "bindings-change",
189
- ]);
190
-
191
- /**
192
- * @typedef {object} DecisionLifecycleRecord
193
- * @property {"status-transition"|"supersession"|"bindings-change"} kind
194
- * One recorded lifecycle event on one decision.
195
- * @property {string} decisionId The ADR id the event happened to — the stable
196
- * handle the ADR registry keys on (`docs/adr/NNN-slug.md`).
197
- * @property {string|null} [from] status-transition: the status the decision
198
- * left, or null when the event is the decision's creation (its proposed
199
- * entry).
200
- * @property {string} [to] status-transition: the status the decision entered.
201
- * @property {string[]} [superseded] supersession: the ADR id(s) this decision
202
- * replaced — `decisionId` is the RECORDING record, the successor.
203
- * @property {string[]} [added] bindings-change: constraint ids made
204
- * enforceable.
205
- * @property {string[]} [removed] bindings-change: constraint ids unbound.
206
- * @property {OriginRecord} origin WHO recorded the event and with what tool —
207
- * `on` produced by `recordOrigin`, the only door.
208
- */
209
-
210
- /**
211
- * Records one decision-lifecycle event, attributed by the same `origin`
212
- * discipline as a row: `by` and `tool` are required, and `on` comes from the
213
- * injected clock through `recordOrigin` — the only producer of an `on`, and
214
- * the refusal to run without one is its own, inherited here.
215
- *
216
- * The record carries ONLY the kind's own keys and the origin, built fresh, so
217
- * nothing from untrusted input rides along. A no-op event — a status
218
- * transition that changes nothing, a supersession naming no target, a
219
- * bindings change that adds and removes nothing — is refused loudly: a record
220
- * that records nothing would read as a transition that happened, the silent
221
- * direction this module exists to exclude.
222
- *
223
- * Statuses are validated against `ADR_STATUSES` (`./adr-registry.mjs`), the
224
- * single status vocabulary — a record can never attest a status the registry
225
- * could not hold.
226
- *
227
- * @param {{kind: "status-transition"|"supersession"|"bindings-change",
228
- * decisionId: string,
229
- * from?: string|null, to?: string,
230
- * superseded?: string[],
231
- * added?: string[], removed?: string[],
232
- * origin: {by: string, tool: string},
233
- * clock: import("./clock.mjs").Clock}} event
234
- * @returns {DecisionLifecycleRecord}
235
- * @throws {Error} on an unknown kind, a missing decisionId, a status outside
236
- * the registry's `ADR_STATUSES`, a no-op event, or an invalid origin/clock.
237
- */
238
- export function recordDecisionLifecycle({
239
- // used by its own test
240
- kind,
241
- decisionId,
242
- from = null,
243
- to,
244
- superseded,
245
- added,
246
- removed,
247
- origin,
248
- clock,
249
- }) {
250
- const violations = [];
251
- if (!DECISION_LIFECYCLE_KINDS.includes(kind)) {
252
- violations.push(
253
- `kind: must be one of ${DECISION_LIFECYCLE_KINDS.join(", ")}, got ${describe(kind)}`,
254
- );
255
- }
256
- if (typeof decisionId !== "string" || decisionId.trim() === "") {
257
- violations.push(
258
- `decisionId: must be a non-empty string naming the ADR, got ${describe(decisionId)}`,
259
- );
260
- }
261
- if (kind === "status-transition") {
262
- if (from !== null && !ADR_STATUSES.includes(from)) {
263
- violations.push(
264
- `from: must be null or one of ${ADR_STATUSES.join(", ")}, got ${describe(from)}`,
265
- );
266
- }
267
- if (!ADR_STATUSES.includes(to)) {
268
- violations.push(`to: must be one of ${ADR_STATUSES.join(", ")}, got ${describe(to)}`);
269
- }
270
- if (from !== null && from === to) {
271
- violations.push(
272
- `to: equals from (${JSON.stringify(from)}) — a status transition that changes nothing is not a recordable event`,
273
- );
274
- }
275
- } else if (kind === "supersession") {
276
- if (
277
- !Array.isArray(superseded) ||
278
- superseded.length === 0 ||
279
- superseded.some((ref) => typeof ref !== "string" || ref.trim() === "")
280
- ) {
281
- violations.push("superseded: must be a non-empty array of ADR ids this decision replaced");
282
- }
283
- } else if (kind === "bindings-change") {
284
- for (const [name, value] of [
285
- ["added", added],
286
- ["removed", removed],
287
- ]) {
288
- if (value !== undefined && !Array.isArray(value)) {
289
- violations.push(`${name}: must be an array of constraint ids, got ${describe(value)}`);
290
- } else if (
291
- Array.isArray(value) &&
292
- value.some((id) => typeof id !== "string" || id.trim() === "")
293
- ) {
294
- violations.push(`${name}: every entry must be a non-empty constraint id`);
295
- }
296
- }
297
- const addedList = Array.isArray(added) ? added : [];
298
- const removedList = Array.isArray(removed) ? removed : [];
299
- if (addedList.length === 0 && removedList.length === 0) {
300
- violations.push(
301
- "added/removed: a bindings change that adds nothing and removes nothing is not a recordable event",
302
- );
303
- }
304
- }
305
- if (violations.length > 0) {
306
- throw new Error(`decisionLifecycle: ${violations.join("; ")}`);
307
- }
308
- const eventFields =
309
- kind === "status-transition"
310
- ? { from, to }
311
- : kind === "supersession"
312
- ? { superseded }
313
- : { added: added ?? [], removed: removed ?? [] };
314
- return {
315
- kind,
316
- decisionId,
317
- ...eventFields,
318
- origin: recordOrigin({ by: origin?.by, tool: origin?.tool, clock }),
319
- };
320
- }
@@ -13,9 +13,17 @@
13
13
  * `"findings"` → `"fail"`
14
14
  * `"no-verdict"` → `"unknown"`
15
15
  *
16
- * and `"not_applicable"` has no source status in this release — it is the
17
- * vocabulary for Fitness functions and Waivers (a follow-up capability),
18
- * never for engine behavior today.
16
+ * and `"not_applicable"` has no source status in this release — no envelope
17
+ * status maps to it, so it never rides an envelope. Engine behavior does emit
18
+ * it today, on the paths that cannot judge: the fitness registry answers it
19
+ * for a declared function whose `match` selects no observed project, and
20
+ * again for `coverage-minimum` on a path-scoped run, which no scoped run can
21
+ * judge; decision fitness derives it for a decision without authority; the
22
+ * boundary metrics answer it when there is no boundary config to judge
23
+ * against (`./metrics.mjs`). A
24
+ * custom rule may return it as its own verdict — the host requires a
25
+ * `notApplicableReason` (`../custom-rules/host.mjs`) — but no engine path
26
+ * answers it on a rule's behalf.
19
27
  *
20
28
  * ## The invariants, I1–I5
21
29
  *
@@ -41,6 +49,21 @@
41
49
  * (`../verdict.mjs`) depend on the presentation layer. `../report/evidence.mjs`
42
50
  * re-exports `buildDecision` so the render-side callers keep their import
43
51
  * path — a path, never a second implementation.
52
+ *
53
+ * Layer: the verdict vocabulary and decision owner — `VERDICTS`, `isVerdict`,
54
+ * `verdictForStatus`, `fitnessVerdict`, and `buildDecision`. Its counterpart,
55
+ * `../verdict.mjs`, is the check lane built on top of `buildDecision` — the
56
+ * process's exit codes, the coverage clauses, and `verdictFor`, the per-lint
57
+ * verdict the `check` command words its envelope and its exit from. The two
58
+ * near-collision pairs cross that boundary, and the name decides which file
59
+ * a reader wants: `verdictForStatus` here looks one status up in a frozen
60
+ * map, while `../verdict.mjs`'s `verdictFor` folds a run's counts into
61
+ * status + exitCode; `VERDICT_FOR_STATUS` here is an independently frozen
62
+ * map, while `../verdict.mjs`'s `EXIT_FOR_STATUS` is derived from its own
63
+ * `EXIT`. Verdict vocabulary and decision construction live here; exit-code,
64
+ * coverage and check-lane concerns live there — and the layering stays
65
+ * one-directional (the check lane imports this module, never the reverse),
66
+ * so this module must not grow exit-code or coverage concerns.
44
67
  */
45
68
 
46
69
  import { describe, isNonEmptyString } from "../values.mjs";
@@ -52,7 +52,7 @@
52
52
  "type": "source-evidence",
53
53
  "path": "cli.mjs",
54
54
  "assertion": "Exit codes 0/1/3 distinguish clean/findings/cannot-look",
55
- "sha256": "81abe8243660b3cca913ee903c1fc0bfcdb6a240640c5302f18848e6a9473fe6"
55
+ "sha256": "2b6590f4039464d3569727d0a73db61dd86c18648a519ee034ebcc2d845ecfc7"
56
56
  }
57
57
  ],
58
58
  "status": "proven"
@@ -66,13 +66,13 @@
66
66
  "type": "behavioral-test",
67
67
  "path": "src/intent/intent.test.mjs",
68
68
  "assertion": "analysis output conforms to the frozen contract schema (no extra verdict/policy fields); analysis output is invariant under project tag changes (three workspaces differing only in project tag fields compared byte-for-byte)",
69
- "sha256": "85b98de1f9268c94020b8b728a3ebbf1e8b50f8c70731c5460c788ea00be3198"
69
+ "sha256": "749414363ef9991ae3697fc00ab5969751666867792d4bb4dbe528ec47ccd740"
70
70
  },
71
71
  {
72
72
  "type": "architecture-test",
73
73
  "path": "src/intent/intent.test.mjs",
74
74
  "assertion": "the gate walks every production analysis module and fails when judging vocabulary (judge/forbid/permit/allow/ban) appears in code",
75
- "sha256": "85b98de1f9268c94020b8b728a3ebbf1e8b50f8c70731c5460c788ea00be3198"
75
+ "sha256": "749414363ef9991ae3697fc00ab5969751666867792d4bb4dbe528ec47ccd740"
76
76
  },
77
77
  {
78
78
  "type": "source-evidence",
@@ -84,7 +84,7 @@
84
84
  "type": "source-evidence",
85
85
  "path": "AGENTS.md",
86
86
  "assertion": "src/graph/ is a lossy view of analysis, on purpose; src/analysis/ never judges",
87
- "sha256": "3209154935cc1463127721203da74dc8bf8ba40258b182c5faa7345946611e38"
87
+ "sha256": "552b54c1956370f024ffeecec95c0e0941a0c66d4a14094045b444a25a27f913"
88
88
  }
89
89
  ],
90
90
  "status": "proven"
@@ -104,19 +104,19 @@
104
104
  "type": "source-evidence",
105
105
  "path": "src/commands/graph.mjs",
106
106
  "assertion": "Plain string comparison, never localeCompare; INTERNAL_DATA_FIELDS stripped",
107
- "sha256": "436902ab3ca994c233318437a896630f969a2c8a22b0f93e598d309faed39d49"
107
+ "sha256": "4f493421e11b012ce7b9c1b111155c8ebdbca6ab4ad3fa37221fbe1a465bef46"
108
108
  },
109
109
  {
110
110
  "type": "source-evidence",
111
111
  "path": "src/report/json.mjs",
112
112
  "assertion": "SCHEMA_VERSION = 2 — the envelope's schemaVersion constant",
113
- "sha256": "090418f6f60dec51638976dff658c55f8a932012bfc7c8bc59952b0f03543340"
113
+ "sha256": "ac6db6e74b4ef7e54db12cc14ef57a7c5080ad081d7bf1273beb5ba543dcac24"
114
114
  },
115
115
  {
116
116
  "type": "source-evidence",
117
117
  "path": "src/commands/graph.mjs",
118
118
  "assertion": "computePolicyFingerprint produces SHA-256 of canonicalized policy",
119
- "sha256": "436902ab3ca994c233318437a896630f969a2c8a22b0f93e598d309faed39d49"
119
+ "sha256": "4f493421e11b012ce7b9c1b111155c8ebdbca6ab4ad3fa37221fbe1a465bef46"
120
120
  }
121
121
  ],
122
122
  "status": "proven"
@@ -136,7 +136,7 @@
136
136
  "type": "source-evidence",
137
137
  "path": "src/commands/diff.mjs",
138
138
  "assertion": "parseBaseline validates schemaVersion; refuses unknown versions",
139
- "sha256": "e28620e288b58e35916e8cd41de446b999bdc2c4e5fcb5f3a617ab0ee449b0fd"
139
+ "sha256": "4d44eea475cd4b06122a405718203d2e0018a163c1d42b17324400e7e4de5eea"
140
140
  }
141
141
  ],
142
142
  "status": "proven"
@@ -156,7 +156,7 @@
156
156
  "type": "source-evidence",
157
157
  "path": "src/commands/diff.mjs",
158
158
  "assertion": "computeDiff returns structural diff; policyMismatch detected via fingerprint; computeRuleImpact for depConstraints-only context",
159
- "sha256": "e28620e288b58e35916e8cd41de446b999bdc2c4e5fcb5f3a617ab0ee449b0fd"
159
+ "sha256": "4d44eea475cd4b06122a405718203d2e0018a163c1d42b17324400e7e4de5eea"
160
160
  }
161
161
  ],
162
162
  "status": "proven"
@@ -236,7 +236,7 @@
236
236
  "type": "behavioral-test",
237
237
  "path": "src/intent/intent.test.mjs",
238
238
  "assertion": "depConstraints verdicts from judgeEdge agree with evaluate in both directions (violating edge found by both, legal edge reported by neither); explain includes the same violations as evaluate at a given site",
239
- "sha256": "85b98de1f9268c94020b8b728a3ebbf1e8b50f8c70731c5460c788ea00be3198"
239
+ "sha256": "749414363ef9991ae3697fc00ab5969751666867792d4bb4dbe528ec47ccd740"
240
240
  },
241
241
  {
242
242
  "type": "behavioral-test",
@@ -254,19 +254,19 @@
254
254
  "type": "source-evidence",
255
255
  "path": "src/commands/context-command.mjs",
256
256
  "assertion": "coverage.notes warns that per-edge violations cover only depConstraints (3 of 15 violation types)",
257
- "sha256": "f906671ff4a5720d80ea5a3dab2779f1cfd3648fbc1e6a1f3a6d0e6efef21feb"
257
+ "sha256": "2d8a17dce1a5f4075ee02a7a8c1bdff94e70afe5cd609f63fe3cf6324f78aaf3"
258
258
  },
259
259
  {
260
260
  "type": "source-evidence",
261
261
  "path": "src/commands/impact.mjs",
262
262
  "assertion": "coverage.notes warns that per-edge violations cover only depConstraints (3 of 15 violation types)",
263
- "sha256": "152a53a0010d8cbd51d11e3ce6268fa50d1e2bcacab3d7bcb38dbd53fc120bbf"
263
+ "sha256": "440f20017cceae4b13c6bc5c653c7a8b99511e0c062dcc7abfb18859f3f0520c"
264
264
  },
265
265
  {
266
266
  "type": "source-evidence",
267
267
  "path": "src/commands/diff.mjs",
268
268
  "assertion": "coverage.notes warns when ruleImpact is computed (depConstraints only, 3 of 15)",
269
- "sha256": "e28620e288b58e35916e8cd41de446b999bdc2c4e5fcb5f3a617ab0ee449b0fd"
269
+ "sha256": "4d44eea475cd4b06122a405718203d2e0018a163c1d42b17324400e7e4de5eea"
270
270
  },
271
271
  {
272
272
  "type": "documentation",
@@ -292,7 +292,7 @@
292
292
  "type": "source-evidence",
293
293
  "path": "src/commands/graph.mjs",
294
294
  "assertion": "Plain string comparison throughout; never localeCompare",
295
- "sha256": "436902ab3ca994c233318437a896630f969a2c8a22b0f93e598d309faed39d49"
295
+ "sha256": "4f493421e11b012ce7b9c1b111155c8ebdbca6ab4ad3fa37221fbe1a465bef46"
296
296
  }
297
297
  ],
298
298
  "status": "proven"
@@ -60,12 +60,8 @@ import {
60
60
  TEXT_DOCUMENT_SYNC_KIND,
61
61
  uriToPath,
62
62
  } from "./protocol.mjs";
63
- import {
64
- buildWorkspaceIndex,
65
- listWorkspaceFiles,
66
- PROJECT_CONFIG_FILE,
67
- readWorkspaceFile,
68
- } from "./workspace-index.mjs";
63
+ import { PROJECT_CONFIG_FILE } from "../providers/native/discover.mjs";
64
+ import { buildWorkspaceIndex, listWorkspaceFiles, readWorkspaceFile } from "./workspace-index.mjs";
69
65
 
70
66
  /**
71
67
  * A project's own `package.json`, and the two spellings of its Module
@@ -232,8 +228,9 @@ const POLYGLOT_GRAPH_MANIFESTS = Object.freeze([
232
228
  * the annotations cached against the old one. The stale waiver then publishes
233
229
  * `[]` for a real violation for the rest of the session, which is the silent
234
230
  * direction exactly (`../../../../AGENTS.md`). `package.json` earns the entry a
235
- * second way as well: it is where `./workspace-index.mjs`'s `discoverProjects`
236
- * takes a project's NAME when its `project.json` states none, so an edit to it
231
+ * second way as well: it is where the static acquisition
232
+ * (`../providers/nx-static.mjs`'s `discoverProjects`) takes a project's NAME
233
+ * when its `project.json` states none, so an edit to it
237
234
  * can move a project in the graph and not only waive something in it.
238
235
  *
239
236
  * The polyglot graph manifests are here for that same argument one level out,