instar 1.3.704 → 1.3.705

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 (67) hide show
  1. package/dist/commands/server.d.ts.map +1 -1
  2. package/dist/commands/server.js +216 -17
  3. package/dist/commands/server.js.map +1 -1
  4. package/dist/core/DeliverMessageHandler.d.ts +16 -0
  5. package/dist/core/DeliverMessageHandler.d.ts.map +1 -1
  6. package/dist/core/DeliverMessageHandler.js +0 -0
  7. package/dist/core/DeliverMessageHandler.js.map +1 -1
  8. package/dist/core/PostUpdateMigrator.d.ts +15 -0
  9. package/dist/core/PostUpdateMigrator.d.ts.map +1 -1
  10. package/dist/core/PostUpdateMigrator.js +108 -0
  11. package/dist/core/PostUpdateMigrator.js.map +1 -1
  12. package/dist/core/QueueDrainLoop.d.ts +6 -2
  13. package/dist/core/QueueDrainLoop.d.ts.map +1 -1
  14. package/dist/core/QueueDrainLoop.js +0 -0
  15. package/dist/core/QueueDrainLoop.js.map +1 -1
  16. package/dist/core/SessionRouter.d.ts +24 -4
  17. package/dist/core/SessionRouter.d.ts.map +1 -1
  18. package/dist/core/SessionRouter.js +25 -2
  19. package/dist/core/SessionRouter.js.map +1 -1
  20. package/dist/core/meshRejectionLog.d.ts +37 -0
  21. package/dist/core/meshRejectionLog.d.ts.map +1 -0
  22. package/dist/core/meshRejectionLog.js +73 -0
  23. package/dist/core/meshRejectionLog.js.map +1 -0
  24. package/dist/core/registryHighWater.d.ts +59 -0
  25. package/dist/core/registryHighWater.d.ts.map +1 -0
  26. package/dist/core/registryHighWater.js +120 -0
  27. package/dist/core/registryHighWater.js.map +1 -0
  28. package/dist/core/senderRejectionNotice.d.ts +89 -0
  29. package/dist/core/senderRejectionNotice.d.ts.map +1 -0
  30. package/dist/core/senderRejectionNotice.js +149 -0
  31. package/dist/core/senderRejectionNotice.js.map +1 -0
  32. package/dist/core/senderValidationGate.d.ts +80 -0
  33. package/dist/core/senderValidationGate.d.ts.map +1 -0
  34. package/dist/core/senderValidationGate.js +133 -0
  35. package/dist/core/senderValidationGate.js.map +1 -0
  36. package/dist/core/types.d.ts +12 -0
  37. package/dist/core/types.d.ts.map +1 -1
  38. package/dist/core/types.js.map +1 -1
  39. package/dist/messaging/MessageProcessingLedger.d.ts +33 -5
  40. package/dist/messaging/MessageProcessingLedger.d.ts.map +1 -1
  41. package/dist/messaging/MessageProcessingLedger.js +50 -7
  42. package/dist/messaging/MessageProcessingLedger.js.map +1 -1
  43. package/dist/messaging/ingressDedup.d.ts.map +1 -1
  44. package/dist/messaging/ingressDedup.js +9 -0
  45. package/dist/messaging/ingressDedup.js.map +1 -1
  46. package/dist/scaffold/templates.d.ts.map +1 -1
  47. package/dist/scaffold/templates.js +2 -1
  48. package/dist/scaffold/templates.js.map +1 -1
  49. package/dist/server/CapabilityIndex.d.ts.map +1 -1
  50. package/dist/server/CapabilityIndex.js +1 -0
  51. package/dist/server/CapabilityIndex.js.map +1 -1
  52. package/dist/server/routes.d.ts.map +1 -1
  53. package/dist/server/routes.js +36 -0
  54. package/dist/server/routes.js.map +1 -1
  55. package/dist/users/UserManager.d.ts +22 -1
  56. package/dist/users/UserManager.d.ts.map +1 -1
  57. package/dist/users/UserManager.js +87 -2
  58. package/dist/users/UserManager.js.map +1 -1
  59. package/dist/users/testIdentityMarkers.d.ts +94 -0
  60. package/dist/users/testIdentityMarkers.d.ts.map +1 -0
  61. package/dist/users/testIdentityMarkers.js +170 -0
  62. package/dist/users/testIdentityMarkers.js.map +1 -0
  63. package/package.json +1 -1
  64. package/src/data/builtin-manifest.json +63 -63
  65. package/src/scaffold/templates.ts +2 -1
  66. package/upgrades/1.3.705.md +79 -0
  67. package/upgrades/side-effects/silent-loss-refusal-conservation.md +124 -0
@@ -0,0 +1,124 @@
1
+ # Side-Effects Review — silent-loss-refusal-conservation
2
+
3
+ Spec: `docs/specs/silent-loss-refusal-conservation.md` (converged, approved, operator-preapproved topic 29836).
4
+ Change: 5 increments (A RouteOutcome honesty, B receiver trace, C unified loss notice, D wiring-time registry gate + fixture refusal, E agent awareness) + 2 migrations.
5
+
6
+ ## Over-block (could this REFUSE a message it should deliver?)
7
+
8
+ - The wiring gate's whole design is fail-TOWARD-delivery for the incident class: a
9
+ degenerate / never-populated / clean-ENOENT / operator-unresolvable registry
10
+ DISARMS (delivers). The only paths that REJECT are (a) a HEALTHY populated
11
+ registry that genuinely doesn't resolve the sender (real deauthorization — the
12
+ existing, intended behavior) and (b) an UNKNOWN_UNSAFE (corrupt/partial/tampered)
13
+ store, which fails CLOSED by design — but even there the LOCALLY-bound operator
14
+ passes via the topic-operator binding (KYP), and the rejection is conserved
15
+ through the §C notice so the sender is TOLD (never silent).
16
+ - Risk: `classifyRegistry` reads the RAW file and counts fixture rows as
17
+ "populated". A fixture-clobbered store therefore classifies `populated`, and a
18
+ NON-operator real sender with no bound operator for that topic would be rejected
19
+ in the window BEFORE the §4 boot migration quarantines the fixtures. Mitigations:
20
+ the migration runs at boot; the operator ALWAYS passes via the operator-resolution
21
+ disarm; the rejection is a loud §C notice, never silent loss. Net: strictly
22
+ better than today (today: silent total loss for everyone).
23
+ - New-user first message: a genuinely fresh install (`[]`, no high-water) disarms →
24
+ the operator's first message is delivered. `legitimate-user-named-Olivia-registers`
25
+ pins that a display name is NEVER a fixture criterion.
26
+
27
+ ## Under-block (could this DELIVER something it should refuse?)
28
+
29
+ - The degenerate disarm delivers WITHOUT sender re-validation. This is intentional
30
+ and bounded: it only applies to a registry that would otherwise reject EVERYONE
31
+ (protecting nothing). The mesh's outer wall is unchanged — MeshRpc is still
32
+ signed, recipient-bound, router-only; only the DEFENSE-IN-DEPTH sender re-check
33
+ is disarmed, not the transport authz.
34
+ - The read-only probe UserManager (no server key) KEEPS a fixture-with-allow-marker
35
+ it cannot verify. Only reachable by a near-impossible legit fixture-collision AND
36
+ a data-only forger simultaneously; the AUTHORITATIVE server load (with the key)
37
+ quarantines a bogus marker. A fixture uid resolving in a non-authoritative probe
38
+ does not authorize anything (it is not a real sender). Documented out-of-scope:
39
+ a fully-FS-privileged local process (§2.D honest threat model).
40
+
41
+ ## Abstraction (right seams? single funnels?)
42
+
43
+ - The refusal is a FIRST-CLASS `RouteOutcome.action:'rejected'` + a distinct
44
+ `LedgerState:'rejected'` terminal — enumerated into EVERY consumer (router
45
+ consumers, forceReplace, drain escape, `decideIngress`/`beginProcessing`/`isActedOn`).
46
+ A ratchet test pins that no consumer maps `rejected`→success.
47
+ - The loss notice is ONE funnel (`SenderRejectionNoticer`) shared by the live path
48
+ (Telegram/Slack) AND the drain `reportLoss('sender-deauthorized')` — unified on
49
+ ONE canonical cause so the two paths can't emit two wordings.
50
+ - The fixture matcher, high-water, and allow-marker sign/verify are single-source
51
+ modules imported by the write path, load path, gate, AND the §4 migration — they
52
+ cannot drift.
53
+
54
+ ## Signal-vs-authority
55
+
56
+ - The divergence signal (local-resolves + remote-rejects) is ADVISORY only — it
57
+ raises one deduped coherence alert, NEVER auto-remediation (it cannot distinguish
58
+ a degenerate registry from a lawful deauth still replicating). Auto re-place is a
59
+ tracked follow-up.
60
+ - The receiver-side trace (`onRejected` → `mesh-rejections.jsonl`) is metadata-only
61
+ observability — it never changes the NACK. A trace fault is swallowed.
62
+ - The gate's alerts are deduped/rate-limited signals; the ARM/DISARM decision is
63
+ the authority, driven only by verified registry STATE (never a config flag).
64
+
65
+ ## Adjacent systems
66
+
67
+ - `MessageProcessingLedger` gains a `rejected` state + `rejected_at` column
68
+ (idempotent `ALTER TABLE ADD COLUMN`, self-initializing — no migrator step). The
69
+ three ledger consumers are enumerated so a redelivery is DROPPED, not resurrected
70
+ (closes the double-notify-on-redelivery class).
71
+ - `UserManager` write path now THROWS `TestIdentityRefusedError` on a fixture id.
72
+ Full-suite risk: suites/harnesses that legitimately write `livetest`/`g3test`/`u-*`
73
+ ids. Mitigation: the double-keyed escape (`INSTAR_ALLOW_TEST_IDENTITIES=1` + the
74
+ on-disk test-home marker) is set for legitimately-fixture-writing suites; the
75
+ load path refuse-and-SKIPS (never throws → never fails boot).
76
+ - `high-water` write on load/register is monotonic + one-time + best-effort (never
77
+ breaks a write). It shares users.json's FS trust boundary (no separate envelope).
78
+
79
+ ## Rollback
80
+
81
+ - Single PR; `git revert` restores all CODE behavior. CARVE-OUT (§6): the §4
82
+ boot-remediation QUARANTINES fixture rows out of users.json to a timestamped
83
+ backup — a revert removes the migration code but does not (and should not)
84
+ restore quarantined rows; a wrongly-quarantined legitimate user is recovered from
85
+ that backup. The boot classification is READ-ONLY (no self-heal write), so it
86
+ leaves no state to unwind. Surviving inert artifacts: `logs/mesh-rejections.jsonl`,
87
+ `state/registry-high-water.json`, any already-sent notices/alerts.
88
+ - Per-increment rollback is clean (disjoint seams): router mapping / handler deps /
89
+ notice consumer / wiring gate + UserManager / template.
90
+
91
+ ## Always-on justification
92
+
93
+ Reachability / no-silent-loss floor ("The Agent Is Always Reachable" class): the
94
+ constitution forbids dark-shipping the guarantee that a message is delivered or
95
+ loudly accounted for. A/B/E are pure honesty + hygiene (identical on every healthy
96
+ path). C fires only where today = silent loss. D's disarm fires only in degenerate
97
+ states that today reject everyone; its own failure mode (a probe throwing on a
98
+ transiently-locked POPULATED store) is pinned to ARM by `populated-registry-always-arms`,
99
+ so the new code cannot regress the existing security control.
100
+
101
+ ## Follow-up: CI-surfaced test adjustments (2026-07-02)
102
+
103
+ The full sharded CI suite surfaced pre-existing tests the change interacts with.
104
+ Fixed WITHOUT weakening the production fixture-refusal or the no-silent-fallbacks
105
+ guard, via the intended escape/annotation mechanisms:
106
+
107
+ - **Fixture-writing tests** (e2e coordination-mandate + authorization-request; integration
108
+ permissions-routes) now use the intended DOUBLE-KEYED test escape via a shared
109
+ `tests/helpers/allow-test-identities.ts` (env `INSTAR_ALLOW_TEST_IDENTITIES=1` + the
110
+ on-disk `.instar-test-home` marker). Production behavior is unchanged — a stray env var
111
+ alone still cannot disable the guard.
112
+ - **`no-silent-fallbacks` ratchet**: my four new-file intentional fail-toward-delivery
113
+ catches + the four inbound-wiring construction catches in `server.ts` are annotated
114
+ `@silent-fallback-ok` with a per-site reason. Net flagged count returns to baseline
115
+ 491 — NO baseline bump; the guard is not weakened.
116
+ - **`feature-delivery-completeness`**: the migrator "Sender-Rejection Notices" section is
117
+ added to `legacyMigratorSections` (template + migrator behavioral awareness, no
118
+ framework-shadowed route).
119
+ - **`capabilities-discoverability`**: the `/users` route prefix (`POST /users/allow-test-identity`)
120
+ is classified in `CapabilityIndex.INTERNAL_PREFIXES` (dashboard-PIN-gated, operator/support-only,
121
+ not an agent-invokable capability).
122
+ - **`session-pool-activation-wiring`**: the fail-safe scan window grew 5200→6500 to contain
123
+ the `rejected` short-circuit added inside the inbound interception block (documented
124
+ window-maintenance pattern).