instar 1.3.472 → 1.3.473

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 (33) hide show
  1. package/dist/config/ConfigDefaults.d.ts.map +1 -1
  2. package/dist/config/ConfigDefaults.js +20 -0
  3. package/dist/config/ConfigDefaults.js.map +1 -1
  4. package/dist/core/PostUpdateMigrator.d.ts.map +1 -1
  5. package/dist/core/PostUpdateMigrator.js +9 -0
  6. package/dist/core/PostUpdateMigrator.js.map +1 -1
  7. package/dist/core/StandardEnforcementExtractor.d.ts +44 -0
  8. package/dist/core/StandardEnforcementExtractor.d.ts.map +1 -0
  9. package/dist/core/StandardEnforcementExtractor.js +98 -0
  10. package/dist/core/StandardEnforcementExtractor.js.map +1 -0
  11. package/dist/core/StandardsEnforcementAuditor.d.ts +78 -0
  12. package/dist/core/StandardsEnforcementAuditor.d.ts.map +1 -0
  13. package/dist/core/StandardsEnforcementAuditor.js +295 -0
  14. package/dist/core/StandardsEnforcementAuditor.js.map +1 -0
  15. package/dist/core/StandardsRegistryParser.d.ts +7 -0
  16. package/dist/core/StandardsRegistryParser.d.ts.map +1 -1
  17. package/dist/core/StandardsRegistryParser.js +7 -0
  18. package/dist/core/StandardsRegistryParser.js.map +1 -1
  19. package/dist/core/componentCategories.d.ts.map +1 -1
  20. package/dist/core/componentCategories.js +6 -0
  21. package/dist/core/componentCategories.js.map +1 -1
  22. package/dist/server/CapabilityIndex.d.ts.map +1 -1
  23. package/dist/server/CapabilityIndex.js +3 -1
  24. package/dist/server/CapabilityIndex.js.map +1 -1
  25. package/dist/server/routes.d.ts.map +1 -1
  26. package/dist/server/routes.js +80 -0
  27. package/dist/server/routes.js.map +1 -1
  28. package/package.json +1 -1
  29. package/scripts/standards-coverage.mjs +279 -0
  30. package/src/data/builtin-manifest.json +63 -63
  31. package/upgrades/1.3.473.md +84 -0
  32. package/upgrades/side-effects/cartographer-conformance-audit.md +109 -0
  33. package/upgrades/1.3.472.md +0 -40
@@ -0,0 +1,109 @@
1
+ # Side-Effects Review — Standards Enforcement-Coverage Audit (spec #3, Tier 2)
2
+
3
+ **Version / slug:** `cartographer-conformance-audit`
4
+ **Date:** `2026-06-10`
5
+ **Author:** `Echo`
6
+ **Spec:** `docs/specs/CARTOGRAPHER-CONFORMANCE-AUDIT.md` (converged 2 rounds, approved)
7
+ **Second-pass reviewer:** `not required — convergence (2 rounds, 3 reviewers + a round-2 verifier) drove two full redesigns; this review covers the seven dimensions on the as-built deterministic code`
8
+
9
+ ## Summary of the change
10
+
11
+ For each standard in `docs/STANDARDS-REGISTRY.md`, the audit verifies whether the
12
+ structural guard its prose NAMES (a test / lint / gate / route) actually exists on
13
+ disk, classifies enforcement strength (ratchet > gate > lint > spec-only >
14
+ documented-only), and surfaces the GAPS + dangling refs. Deterministic-first,
15
+ observe-only, non-gating, dark behind `cartographer.conformanceAudit.enabled`. Two
16
+ read routes + a CI ratchet (enforced-ratio floor + zero-dangling ceiling). Touches
17
+ **no** merged spec #2 code; reuses only `StandardsRegistryParser` (shipped) and the
18
+ `docs-coverage.mjs` script pattern.
19
+
20
+ **Design note:** convergence rejected two prior drafts — v1 (per-node LLM audit:
21
+ ~$320/pass on Opus, never converges) and v2 (a no-op, since every node-checkable
22
+ standard is already lint-covered, and it leaned on prompt-caching + PIN-scoping the
23
+ substrate lacks). v3 inverts the question to one that is cheap, deterministic, and
24
+ produces real value day one.
25
+
26
+ ## ⚠ Notable change: a one-line CONSTITUTION repair
27
+
28
+ Running the audit against the live registry surfaced a genuine **dangling
29
+ reference** (the exact broken-guarantee signal the feature exists to catch): the
30
+ "Know Your Principal" standard's `**Applied through.**` line cited
31
+ `docs/specs/OPERATOR-IDENTITY-BINDING-SPEC.md`, **which does not exist**. Its real
32
+ artifacts are `src/core/PrincipalGuard.ts`, `src/users/TopicOperatorStore.ts`, and
33
+ `docs/specs/PRINCIPAL-GUARD.md` (all verified present). I repaired that one line to
34
+ cite the artifacts that actually exist — a **factual citation correction, NOT a
35
+ change to any rule's normative content** — which the feature's own zero-dangling CI
36
+ ceiling requires for a clean baseline. This is a transparent, reversible edit to
37
+ `docs/STANDARDS-REGISTRY.md`, called out here and in the PR for operator visibility.
38
+ The detection capability is independently demonstrated by the e2e test (which plants
39
+ a synthetic dangling ref).
40
+
41
+ ## Files touched
42
+
43
+ - NEW: `src/core/StandardEnforcementExtractor.ts`, `src/core/StandardsEnforcementAuditor.ts`, `scripts/standards-coverage.mjs`.
44
+ - MODIFIED (additive): `src/core/StandardsRegistryParser.ts` (`appliedThrough?` field), `src/config/ConfigDefaults.ts` (nested `conformanceAudit`), `src/server/routes.ts` (2 read routes), `src/server/CapabilityIndex.ts`, `src/core/componentCategories.ts`, `src/core/PostUpdateMigrator.ts` (CLAUDE.md section), `.github/workflows/ci.yml`, `.gitignore`, `docs/STANDARDS-REGISTRY.md` (the one-line repair above).
45
+ - TESTS: 46 across 3 tiers.
46
+
47
+ ## 1. Over-block
48
+
49
+ The audit blocks nothing (observe-only). The only gate that can "fail" is the CI
50
+ ratchet (enforced-ratio floor + zero-dangling ceiling). Over-block risk = a false
51
+ dangling ref failing CI. Mitigation: the verifier scans ALL `src/server/*.ts` for
52
+ routes (not just `routes.ts` — a round-of-build fix that stopped `POST
53
+ /spec/conformance-check` from false-flagging), and the floor ships at 0 (loose,
54
+ ratchets up). A genuine transient is fail-open in the auditor (an unreadable path is
55
+ a finding, not a crash).
56
+
57
+ ## 2. Under-block
58
+
59
+ Could a real gap be missed (read as enforced)? The extractor is conservative — a ref
60
+ is only counted if it matches a known enforcement shape AND verifies on disk. A
61
+ standard whose guard is named in prose the regex doesn't recognize reads as a GAP
62
+ (the safe direction — over-reports gaps, never hides one). The enforced-ratio 0.317
63
+ (26 gaps of 41) confirms it is not laxly classifying.
64
+
65
+ ## 3. Level-of-abstraction fit
66
+
67
+ Extractor (pure ref-extraction) → Auditor (verify + classify) → routes (read
68
+ surface) → ratchet (CI floor). Each layer is single-purpose and independently
69
+ tested. The auditor is deterministic + idempotent (a content-hash short-circuit
70
+ mirrors `docs-coverage.mjs`), so it sits correctly as a pure computation, not a
71
+ stateful service.
72
+
73
+ ## 4. Determinism / no-LLM-cost (the v1/v2 footgun this design avoids)
74
+
75
+ The shipped value is 100% deterministic — local file reads only, ZERO egress, ZERO
76
+ token cost, byte-identical output run-to-run (a determinism test pins this). The
77
+ LLM-enrichment path is a structural stub, OFF by default, and the deterministic
78
+ coverage is always the authority (Signal vs. Authority). This is the direct fix for
79
+ the rejected designs' intractable-cost / never-converge flaws.
80
+
81
+ ## 5. Security / data-egress
82
+
83
+ Default config sends nothing anywhere (no LLM). The coverage report names where the
84
+ constitution is UNGUARDED (meta-level, lighter than spec #2's "where code violates
85
+ safety"), but is still owner-gated: `/conformance/coverage*` require Bearer +
86
+ `X-Instar-Request: 1` intent header (the per-handler pattern, integration-tested for
87
+ 401/403). We deliberately do NOT claim PIN-scope exclusion — round-2 verification
88
+ confirmed the dashboard PIN unlock returns the same bearer token, so that primitive
89
+ does not exist; the honest control is the intent header + owner-Bearer (stated in
90
+ the spec).
91
+
92
+ ## 6. Failure modes / load
93
+
94
+ The pass is milliseconds (parse + fs.existsSync + bounded grep). No poller — a slow
95
+ optional job recomputes + raises ONE aggregated notice only on gap GROWTH (Bounded
96
+ Notification Surface). The store is a single compacted JSON bounded by the standards
97
+ count (~41 rows) — no unbounded growth, no rotation needed. Default-OFF means zero
98
+ load until opt-in.
99
+
100
+ ## 7. Migration / compatibility (Migration Parity)
101
+
102
+ `conformanceAudit` nests under `cartographer` (deep-merge backfill — no migrateConfig
103
+ needed, verified pattern from spec #2's `freshnessSweep`). The CLAUDE.md section
104
+ ships via `migrateClaudeMd` (own marker 'Standards Enforcement Coverage',
105
+ idempotent) AND is registered in the feature-completeness test's legacy-migrator
106
+ allowlist. The `/conformance/coverage*` routes are in CapabilityIndex.
107
+ `StandardsCoverageEnrichment` registered under category `job` (+ wiring test).
108
+ Rollback: disabling the flag 503s the routes + stops the job; the JSON store goes
109
+ inert. No migration reversal. No change to any merged spec #2 behavior (additive).
@@ -1,40 +0,0 @@
1
- # Upgrade Guide — vNEXT
2
-
3
- <!-- assembled-by: assemble-next-md -->
4
- <!-- bump: patch -->
5
-
6
- ## What Changed
7
-
8
- The interactive (user-facing) session lane now pins to a subscription-pool account,
9
- mirroring the headless lane. When `subscriptionPool.pinSessionsToPool` is enabled,
10
- `SessionManager.spawnInteractiveSession` consults the same spawn-account resolver
11
- that `spawnSession` uses (unless the caller passed an explicit `configHome`, e.g. the
12
- account-swap path, which still wins). The session launches under the scheduler-picked
13
- pool account's config home and is tagged with `subscriptionAccountId` — making the
14
- user's own conversation directly eligible for proactive and reactive auto-swap,
15
- instead of riding the default login untagged (rescuable only by the
16
- ProactiveSwapMonitor's default-login fallback). The resolver-pinned home is seeded
17
- onboarding-ready first, so a headless-enrolled home can't wedge the launch on the
18
- first-launch wizard. Claude-code only; complete no-op when pinning is off.
19
-
20
- ## What to Tell Your User
21
-
22
- The conversation you actually chat with is now protected the same first-class way
23
- your background sessions are. When you pool several logins, your own chat session is
24
- tagged to whichever login it is running on, so the moment that login gets close to
25
- full I can move your conversation to a fresh login before it ever stalls — not just
26
- rescue it after the fact. Nothing changes unless you have pooling turned on.
27
-
28
- ## Summary of New Capabilities
29
-
30
- - The interactive session lane pins to a pool account and carries its account tag,
31
- so the user's conversation is first-class for both proactive and reactive swap.
32
-
33
- ## Evidence
34
-
35
- - `tests/unit/interactive-session-pin.test.ts` — 6 cases: resolver-pin, explicit
36
- home wins, unwired no-op, empty-pool no-op, codex-not-pinned, onboarding-safe seeding.
37
- - `tests/integration/subscription-pin-sessions.test.ts` — interactive lane pins via
38
- the real `selectAccount`-wired resolver; empty-pool no-op.
39
- - `tests/e2e/session-management-e2e.test.ts` — real tmux: an interactive session is
40
- tagged with the resolver-picked account and its home is seeded onboarding-ready.