pi-mega-compact 0.20.14 → 0.20.16

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 (94) hide show
  1. package/dist/config/vector-cortex.js +20 -0
  2. package/dist/config.js +1 -1
  3. package/dist/extensions/dashboard-server/api-contracts/vector-cortex-diagnostics.js +35 -0
  4. package/dist/extensions/dashboard-server/route-dispatch.js +6 -0
  5. package/dist/extensions/dashboard-server/routes-rag-settings-vector-cortex.js +1 -0
  6. package/dist/extensions/dashboard-server/routes-vector-cortex-diagnostics.js +68 -0
  7. package/dist/src/config/vector-cortex.js +20 -0
  8. package/dist/src/config.js +1 -1
  9. package/dist/src/vector-cortex/cache/_diagnostics-fixture.js +31 -0
  10. package/dist/src/vector-cortex/cache/breaker.js +110 -0
  11. package/dist/src/vector-cortex/cache/diagnostics-emit.js +64 -0
  12. package/dist/src/vector-cortex/cache/diagnostics-types.js +15 -0
  13. package/dist/src/vector-cortex/cache/diagnostics.js +97 -0
  14. package/dist/src/vector-cortex/migrations/request-hash-v2-ops.js +154 -0
  15. package/dist/src/vector-cortex/migrations/request-hash-v2-types.js +30 -0
  16. package/dist/src/vector-cortex/migrations/request-hash-v2.js +42 -147
  17. package/dist/vector-cortex/cache/_diagnostics-fixture.js +31 -0
  18. package/dist/vector-cortex/cache/breaker.js +110 -0
  19. package/dist/vector-cortex/cache/diagnostics-emit.js +64 -0
  20. package/dist/vector-cortex/cache/diagnostics-types.js +15 -0
  21. package/dist/vector-cortex/cache/diagnostics.js +97 -0
  22. package/dist/vector-cortex/migrations/request-hash-v2-ops.js +154 -0
  23. package/dist/vector-cortex/migrations/request-hash-v2-types.js +30 -0
  24. package/dist/vector-cortex/migrations/request-hash-v2.js +42 -147
  25. package/extensions/dashboard-client/dist/assets/{AreaChart-VUd_iOtO.js → AreaChart-B_FKg8xJ.js} +2 -2
  26. package/extensions/dashboard-client/dist/assets/{AreaChart-VUd_iOtO.js.map → AreaChart-B_FKg8xJ.js.map} +1 -1
  27. package/extensions/dashboard-client/dist/assets/{BarChart-BoqeJ5mM.js → BarChart-BU5RJ0In.js} +2 -2
  28. package/extensions/dashboard-client/dist/assets/{BarChart-BoqeJ5mM.js.map → BarChart-BU5RJ0In.js.map} +1 -1
  29. package/extensions/dashboard-client/dist/assets/{CacheTab-1ON7meDK.js → CacheTab-CbX033mt.js} +2 -2
  30. package/extensions/dashboard-client/dist/assets/{CacheTab-1ON7meDK.js.map → CacheTab-CbX033mt.js.map} +1 -1
  31. package/extensions/dashboard-client/dist/assets/{EventsTab-Dr9eqt1k.js → EventsTab-D8Z_4gSB.js} +2 -2
  32. package/extensions/dashboard-client/dist/assets/{EventsTab-Dr9eqt1k.js.map → EventsTab-D8Z_4gSB.js.map} +1 -1
  33. package/extensions/dashboard-client/dist/assets/{HealthTab-Ciaigd4i.js → HealthTab-BUUkoQXo.js} +2 -2
  34. package/extensions/dashboard-client/dist/assets/{HealthTab-Ciaigd4i.js.map → HealthTab-BUUkoQXo.js.map} +1 -1
  35. package/extensions/dashboard-client/dist/assets/{MaintenanceTab-DjZRr3Lf.js → MaintenanceTab-DKZQmY1T.js} +2 -2
  36. package/extensions/dashboard-client/dist/assets/{MaintenanceTab-DjZRr3Lf.js.map → MaintenanceTab-DKZQmY1T.js.map} +1 -1
  37. package/extensions/dashboard-client/dist/assets/{MemoryMapTab-BpZXHA7j.js → MemoryMapTab-DwMGbe3h.js} +2 -2
  38. package/extensions/dashboard-client/dist/assets/{MemoryMapTab-BpZXHA7j.js.map → MemoryMapTab-DwMGbe3h.js.map} +1 -1
  39. package/extensions/dashboard-client/dist/assets/{MetricsTab-QemocY5k.js → MetricsTab-C85lieXW.js} +2 -2
  40. package/extensions/dashboard-client/dist/assets/{MetricsTab-QemocY5k.js.map → MetricsTab-C85lieXW.js.map} +1 -1
  41. package/extensions/dashboard-client/dist/assets/{OverviewTab-VtC1F-mO.js → OverviewTab-D7VPibBT.js} +2 -2
  42. package/extensions/dashboard-client/dist/assets/{OverviewTab-VtC1F-mO.js.map → OverviewTab-D7VPibBT.js.map} +1 -1
  43. package/extensions/dashboard-client/dist/assets/{ReposTab-CJD1cBxp.js → ReposTab-eIHk_mDG.js} +2 -2
  44. package/extensions/dashboard-client/dist/assets/{ReposTab-CJD1cBxp.js.map → ReposTab-eIHk_mDG.js.map} +1 -1
  45. package/extensions/dashboard-client/dist/assets/{SessionsTab-Cj0erPR4.js → SessionsTab-EYOHEzc3.js} +2 -2
  46. package/extensions/dashboard-client/dist/assets/{SessionsTab-Cj0erPR4.js.map → SessionsTab-EYOHEzc3.js.map} +1 -1
  47. package/extensions/dashboard-client/dist/assets/{SetupTab-AOVROZ4G.js → SetupTab-DXpiXu4i.js} +2 -2
  48. package/extensions/dashboard-client/dist/assets/{SetupTab-AOVROZ4G.js.map → SetupTab-DXpiXu4i.js.map} +1 -1
  49. package/extensions/dashboard-client/dist/assets/{TimeSavedCard-ZliVn8DH.js → TimeSavedCard-DUsUC_sm.js} +2 -2
  50. package/extensions/dashboard-client/dist/assets/{TimeSavedCard-ZliVn8DH.js.map → TimeSavedCard-DUsUC_sm.js.map} +1 -1
  51. package/extensions/dashboard-client/dist/assets/{TurnsTab-DsoTWeIh.js → TurnsTab-w7qdB0px.js} +2 -2
  52. package/extensions/dashboard-client/dist/assets/{TurnsTab-DsoTWeIh.js.map → TurnsTab-w7qdB0px.js.map} +1 -1
  53. package/extensions/dashboard-client/dist/assets/VectorCortexTab-BmgdxV5K.js +2 -0
  54. package/extensions/dashboard-client/dist/assets/VectorCortexTab-BmgdxV5K.js.map +1 -0
  55. package/extensions/dashboard-client/dist/assets/{WikiTab-CK8fcW1l.js → WikiTab-B4hwpXpw.js} +2 -2
  56. package/extensions/dashboard-client/dist/assets/{WikiTab-CK8fcW1l.js.map → WikiTab-B4hwpXpw.js.map} +1 -1
  57. package/extensions/dashboard-client/dist/assets/{button-DdPcvex1.js → button-BnbvfQjm.js} +2 -2
  58. package/extensions/dashboard-client/dist/assets/{button-DdPcvex1.js.map → button-BnbvfQjm.js.map} +1 -1
  59. package/extensions/dashboard-client/dist/assets/{card-DXFuZph_.js → card-DCyvWfpF.js} +2 -2
  60. package/extensions/dashboard-client/dist/assets/{card-DXFuZph_.js.map → card-DCyvWfpF.js.map} +1 -1
  61. package/extensions/dashboard-client/dist/assets/{generateCategoricalChart-BagDVGWn.js → generateCategoricalChart-b3HeKJLU.js} +2 -2
  62. package/extensions/dashboard-client/dist/assets/{generateCategoricalChart-BagDVGWn.js.map → generateCategoricalChart-b3HeKJLU.js.map} +1 -1
  63. package/extensions/dashboard-client/dist/assets/{index-DVdDtRY4.js → index-DhlcXMlE.js} +3 -3
  64. package/extensions/dashboard-client/dist/assets/{index-DVdDtRY4.js.map → index-DhlcXMlE.js.map} +1 -1
  65. package/extensions/dashboard-client/dist/assets/{switch-CtdtGyUR.js → switch-B74pQOFy.js} +2 -2
  66. package/extensions/dashboard-client/dist/assets/{switch-CtdtGyUR.js.map → switch-B74pQOFy.js.map} +1 -1
  67. package/extensions/dashboard-client/dist/assets/{toggle-Cvvwlbye.js → toggle-bXDrMX-A.js} +2 -2
  68. package/extensions/dashboard-client/dist/assets/{toggle-Cvvwlbye.js.map → toggle-bXDrMX-A.js.map} +1 -1
  69. package/extensions/dashboard-client/dist/assets/{useSSE-DvlceHjV.js → useSSE-Yq86SUA0.js} +2 -2
  70. package/extensions/dashboard-client/dist/assets/{useSSE-DvlceHjV.js.map → useSSE-Yq86SUA0.js.map} +1 -1
  71. package/extensions/dashboard-client/dist/index.html +1 -1
  72. package/extensions/dashboard-client/src/api/vector-cortex.ts +9 -0
  73. package/extensions/dashboard-client/src/tabs/VectorCortexDiagnosticsCard.tsx +46 -0
  74. package/extensions/dashboard-client/src/tabs/VectorCortexTab.tsx +25 -121
  75. package/extensions/dashboard-client/src/tabs/useVectorCortexPoll.ts +123 -0
  76. package/extensions/dashboard-client/src/types/vector-cortex-vc7.ts +63 -0
  77. package/extensions/dashboard-client/src/types/vector-cortex.ts +5 -33
  78. package/extensions/dashboard-server/api-contracts/vector-cortex-diagnostics.ts +76 -0
  79. package/extensions/dashboard-server/route-dispatch.ts +5 -0
  80. package/extensions/dashboard-server/routes-rag-settings-vector-cortex.ts +6 -0
  81. package/extensions/dashboard-server/routes-vector-cortex-diagnostics.ts +77 -0
  82. package/package.json +1 -1
  83. package/src/config/vector-cortex.ts +21 -0
  84. package/src/config.ts +1 -0
  85. package/src/vector-cortex/cache/_diagnostics-fixture.ts +32 -0
  86. package/src/vector-cortex/cache/breaker.ts +124 -0
  87. package/src/vector-cortex/cache/diagnostics-emit.ts +90 -0
  88. package/src/vector-cortex/cache/diagnostics-types.ts +87 -0
  89. package/src/vector-cortex/cache/diagnostics.ts +119 -0
  90. package/src/vector-cortex/migrations/request-hash-v2-ops.ts +201 -0
  91. package/src/vector-cortex/migrations/request-hash-v2-types.ts +87 -0
  92. package/src/vector-cortex/migrations/request-hash-v2.ts +65 -213
  93. package/extensions/dashboard-client/dist/assets/VectorCortexTab-BBa7rp6C.js +0 -2
  94. package/extensions/dashboard-client/dist/assets/VectorCortexTab-BBa7rp6C.js.map +0 -1
@@ -4,46 +4,19 @@
4
4
  * GET /api/vector-cortex/evaluation. VC0C (task 5): live safety envelope health
5
5
  * card (breaker state, window/probe/backoff, durable spool frontier/lag) from
6
6
  * GET /api/vector-cortex/health plus an admin "reset cooldown" action. Polls
7
- * every 5s.
7
+ * every 5s via useVectorCortexPoll.
8
8
  */
9
9
 
10
- import { useState, useEffect, useCallback } from "react";
10
+ import { useState } from "react";
11
11
  import {
12
- fetchVectorCortexEvaluation,
13
- fetchVectorCortexHealth,
14
- fetchVectorCortexLedger,
15
- fetchVectorCortexQuery,
16
- fetchVectorCortexReconstruct,
17
- fetchVectorCortexPlans,
18
- fetchVectorCortexRender,
19
- fetchVectorCortexRollout,
20
- fetchVectorCortexClosureProof,
21
- fetchVectorCortexRestore,
22
- fetchVectorCortexRepair,
23
- fetchVectorCortexCrystals,
24
- fetchVectorCortexEconomics,
25
- fetchVectorCortexShards,
26
- fetchVectorCortexTopology,
27
12
  resetVectorCortexBreaker,
28
- type VectorCortexEvaluationSummary,
13
+ fetchVectorCortexHealth,
29
14
  type VectorCortexHealthCard,
30
- type VectorCortexLedgerView,
31
- type VectorCortexQueryView,
32
- type VectorCortexReconstructView,
33
- type VectorCortexPlansView,
34
- type VectorCortexRenderView,
35
- type VectorCortexRolloutView,
36
- type VectorCortexClosureProofView,
37
- type VectorCortexRestoreView,
38
- type VectorCortexRepairView,
39
- type VectorCortexCrystalsView,
40
- type VectorCortexEconomicsView,
41
- type VectorCortexShardsView,
42
- type VectorCortexTopologyView,
43
15
  } from "../api/vector-cortex";
44
16
  import { Card, CardContent, CardHeader, CardTitle } from "../components/ui/card";
45
17
  import { Badge } from "../components/ui/badge";
46
18
  import { Metric } from "./VectorCortexMetric";
19
+ import { useVectorCortexPoll } from "./useVectorCortexPoll";
47
20
  import { VectorCortexRenderCard } from "./VectorCortexRenderCard";
48
21
  import { VectorCortexRolloutCard } from "./VectorCortexRolloutCard";
49
22
  import { VectorCortexClosureCard } from "./VectorCortexClosureCard";
@@ -51,6 +24,7 @@ import { VectorCortexRestoreCard } from "./VectorCortexRestoreCard";
51
24
  import { VectorCortexRepairCard } from "./VectorCortexRepairCard";
52
25
  import { VectorCortexCrystalsCard } from "./VectorCortexCrystalsCard";
53
26
  import { VectorCortexEconomicsCard } from "./VectorCortexEconomicsCard";
27
+ import { VectorCortexDiagnosticsCard } from "./VectorCortexDiagnosticsCard";
54
28
  import {
55
29
  VectorCortexShardsCard,
56
30
  VectorCortexReconstructCard,
@@ -69,81 +43,10 @@ function ModeChip({ mode, count }: { mode: string; count: number }): React.React
69
43
  }
70
44
 
71
45
  export default function VectorCortexTab(): React.ReactElement {
72
- const [data, setData] = useState<VectorCortexEvaluationSummary | null>(null);
73
- const [err, setError] = useState<string | null>(null);
74
- const [loading, setLoading] = useState(true);
75
- const [health, setHealth] = useState<VectorCortexHealthCard | null>(null);
46
+ const [poll, refetch] = useVectorCortexPoll();
76
47
  const [resetMsg, setResetMsg] = useState<string | null>(null);
77
- const [ledger, setLedger] = useState<VectorCortexLedgerView | null>(null);
78
- const [topology, setTopology] = useState<VectorCortexTopologyView | null>(null);
79
- const [query, setQuery] = useState<VectorCortexQueryView | null>(null);
80
- const [shards, setShards] = useState<VectorCortexShardsView | null>(null);
81
- const [reconstruct, setReconstruct] = useState<VectorCortexReconstructView | null>(null);
82
- const [plans, setPlans] = useState<VectorCortexPlansView | null>(null);
83
- const [render, setRender] = useState<VectorCortexRenderView | null>(null);
84
- const [rollout, setRollout] = useState<VectorCortexRolloutView | null>(null);
85
- const [closureProof, setClosureProof] = useState<VectorCortexClosureProofView | null>(null);
86
- const [restore, setRestore] = useState<VectorCortexRestoreView | null>(null);
87
- const [repair, setRepair] = useState<VectorCortexRepairView | null>(null);
88
- const [crystals, setCrystals] = useState<VectorCortexCrystalsView | null>(null);
89
- const [economics, setEconomics] = useState<VectorCortexEconomicsView | null>(null);
90
-
91
- const poll = useCallback(() => {
92
- fetchVectorCortexEvaluation()
93
- .then(setData)
94
- .catch((e: unknown) =>
95
- setError(e instanceof Error ? e.message : String(e)),
96
- )
97
- .finally(() => setLoading(false));
98
- fetchVectorCortexHealth().then(setHealth).catch(() => {
99
- /* health card is best-effort (VC0C) */
100
- });
101
- fetchVectorCortexLedger().then(setLedger).catch(() => {
102
- /* ledger card is best-effort (VC1B) */
103
- });
104
- fetchVectorCortexTopology().then(setTopology).catch(() => {
105
- /* topology card is best-effort (VC3A) */
106
- });
107
- fetchVectorCortexQuery().then(setQuery).catch(() => {
108
- /* query diagnostics card is best-effort (VC3C) */
109
- });
110
- fetchVectorCortexShards().then(setShards).catch(() => {
111
- /* dual-tier shards card is best-effort (VC4A) */
112
- });
113
- fetchVectorCortexReconstruct().then(setReconstruct).catch(() => {
114
- /* reconstruction-fidelity card is best-effort (VC4C) */
115
- });
116
- fetchVectorCortexPlans().then(setPlans).catch(() => {
117
- /* plan manifest card is best-effort (VC5A) */
118
- });
119
- fetchVectorCortexRender().then(setRender).catch(() => {
120
- /* render conformance card is best-effort (VC5B) */
121
- });
122
- fetchVectorCortexRollout().then(setRollout).catch(() => {
123
- /* rollout card is best-effort (VC5C) */
124
- });
125
- fetchVectorCortexClosureProof().then(setClosureProof).catch(() => {
126
- /* closure-optimization card is best-effort (VC6A) */
127
- });
128
- fetchVectorCortexRestore().then(setRestore).catch(() => {
129
- /* exact-source-restoration card is best-effort (VC6B) */
130
- });
131
- fetchVectorCortexRepair().then(setRepair).catch(() => {
132
- /* self-healing derived-state card is best-effort (VC6C) */
133
- });
134
- fetchVectorCortexCrystals().then(setCrystals).catch(() => {
135
- /* frozen-range-crystal card is best-effort (VC7A) */
136
- });
137
- fetchVectorCortexEconomics().then(setEconomics).catch(() => {
138
- /* provider-cache-economics card is best-effort (VC7B) */
139
- });
140
- }, []);
141
48
 
142
- useEffect(() => {
143
- poll();
144
- const id = setInterval(poll, 5000);
145
- return () => clearInterval(id);
146
- }, [poll]);
49
+ const { loading, error, data, health } = poll;
147
50
 
148
51
  const onReset = () => {
149
52
  resetVectorCortexBreaker("provider")
@@ -153,7 +56,7 @@ export default function VectorCortexTab(): React.ReactElement {
153
56
  );
154
57
  return fetchVectorCortexHealth();
155
58
  })
156
- .then(setHealth)
59
+ .then((h: VectorCortexHealthCard | null) => { void h; refetch(); })
157
60
  .catch((e: unknown) =>
158
61
  setResetMsg(e instanceof Error ? e.message : String(e)),
159
62
  );
@@ -161,8 +64,8 @@ export default function VectorCortexTab(): React.ReactElement {
161
64
 
162
65
  if (loading && !data)
163
66
  return <div className="vc-loading">Loading vector-cortex evaluation…</div>;
164
- if (err && !data)
165
- return <div className="vc-error">Error: {err}</div>;
67
+ if (error && !data)
68
+ return <div className="vc-error">Error: {error}</div>;
166
69
  if (!data)
167
70
  return <div className="vc-empty">No evaluation data available.</div>;
168
71
 
@@ -281,24 +184,25 @@ export default function VectorCortexTab(): React.ReactElement {
281
184
  }
282
185
  />
283
186
  <Metric label="Spool lag" value={String(health.spoolLag)} />
284
- <Metric label="Encoder mode" value={health.encoderMode} />
285
- <Metric label="Encoder asset" value={health.encoderAssetDigest ? health.encoderAssetDigest.slice(0, 12) : "none"} />
187
+ <Metric label="Encoder mode" value={health.encoderMode} />
188
+ <Metric label="Encoder asset" value={health.encoderAssetDigest ? health.encoderAssetDigest.slice(0, 12) : "none"} />
286
189
  </div>
287
190
  )}
288
191
  </CardContent>
289
192
  </Card>
290
- <VectorCortexTopologyCard topology={topology} query={query} />
291
- <VectorCortexShardsCard view={shards} />
292
- <VectorCortexReconstructCard view={reconstruct} />
293
- <VectorCortexPlansCard view={plans} />
294
- <VectorCortexRenderCard view={render} />
295
- <VectorCortexRolloutCard view={rollout} />
296
- <VectorCortexClosureCard view={closureProof} />
297
- <VectorCortexRestoreCard view={restore} />
298
- <VectorCortexRepairCard view={repair} />
299
- <VectorCortexCrystalsCard view={crystals} />
300
- <VectorCortexEconomicsCard view={economics} />
301
- <VectorCortexLedgerCard ledger={ledger} />
193
+ <VectorCortexTopologyCard topology={poll.topology} query={poll.query} />
194
+ <VectorCortexShardsCard view={poll.shards} />
195
+ <VectorCortexReconstructCard view={poll.reconstruct} />
196
+ <VectorCortexPlansCard view={poll.plans} />
197
+ <VectorCortexRenderCard view={poll.render} />
198
+ <VectorCortexRolloutCard view={poll.rollout} />
199
+ <VectorCortexClosureCard view={poll.closureProof} />
200
+ <VectorCortexRestoreCard view={poll.restore} />
201
+ <VectorCortexRepairCard view={poll.repair} />
202
+ <VectorCortexCrystalsCard view={poll.crystals} />
203
+ <VectorCortexEconomicsCard view={poll.economics} />
204
+ <VectorCortexDiagnosticsCard view={poll.diagnostics} />
205
+ <VectorCortexLedgerCard ledger={poll.ledger} />
302
206
  </div>
303
207
  );
304
208
  }
@@ -0,0 +1,123 @@
1
+ /**
2
+ * useVectorCortexPoll — extracted from VectorCortexTab to keep the tab under
3
+ * the 400-line soft limit. Fetches all vector-cortex reader views in parallel
4
+ * every 5s; each fetch is best-effort (a failure sets its slice to null/state).
5
+ */
6
+ import { useState, useEffect, useCallback } from "react";
7
+ import {
8
+ fetchVectorCortexEvaluation,
9
+ fetchVectorCortexHealth,
10
+ fetchVectorCortexLedger,
11
+ fetchVectorCortexQuery,
12
+ fetchVectorCortexReconstruct,
13
+ fetchVectorCortexPlans,
14
+ fetchVectorCortexRender,
15
+ fetchVectorCortexRollout,
16
+ fetchVectorCortexClosureProof,
17
+ fetchVectorCortexRestore,
18
+ fetchVectorCortexRepair,
19
+ fetchVectorCortexCrystals,
20
+ fetchVectorCortexEconomics,
21
+ fetchVectorCortexDiagnostics,
22
+ fetchVectorCortexShards,
23
+ fetchVectorCortexTopology,
24
+ type VectorCortexEvaluationSummary,
25
+ type VectorCortexHealthCard,
26
+ type VectorCortexLedgerView,
27
+ type VectorCortexQueryView,
28
+ type VectorCortexReconstructView,
29
+ type VectorCortexPlansView,
30
+ type VectorCortexRenderView,
31
+ type VectorCortexRolloutView,
32
+ type VectorCortexClosureProofView,
33
+ type VectorCortexRestoreView,
34
+ type VectorCortexRepairView,
35
+ type VectorCortexCrystalsView,
36
+ type VectorCortexEconomicsView,
37
+ type VectorCortexDiagnosticsView,
38
+ type VectorCortexShardsView,
39
+ type VectorCortexTopologyView,
40
+ } from "../api/vector-cortex";
41
+
42
+ export interface VectorCortexPollState {
43
+ loading: boolean;
44
+ error: string | null;
45
+ data: VectorCortexEvaluationSummary | null;
46
+ health: VectorCortexHealthCard | null;
47
+ ledger: VectorCortexLedgerView | null;
48
+ topology: VectorCortexTopologyView | null;
49
+ query: VectorCortexQueryView | null;
50
+ shards: VectorCortexShardsView | null;
51
+ reconstruct: VectorCortexReconstructView | null;
52
+ plans: VectorCortexPlansView | null;
53
+ render: VectorCortexRenderView | null;
54
+ rollout: VectorCortexRolloutView | null;
55
+ closureProof: VectorCortexClosureProofView | null;
56
+ restore: VectorCortexRestoreView | null;
57
+ repair: VectorCortexRepairView | null;
58
+ crystals: VectorCortexCrystalsView | null;
59
+ economics: VectorCortexEconomicsView | null;
60
+ diagnostics: VectorCortexDiagnosticsView | null;
61
+ }
62
+
63
+ export function useVectorCortexPoll(): [
64
+ VectorCortexPollState,
65
+ () => void,
66
+ ] {
67
+ const [state, setState] = useState<VectorCortexPollState>({
68
+ loading: true,
69
+ error: null,
70
+ data: null,
71
+ health: null,
72
+ ledger: null,
73
+ topology: null,
74
+ query: null,
75
+ shards: null,
76
+ reconstruct: null,
77
+ plans: null,
78
+ render: null,
79
+ rollout: null,
80
+ closureProof: null,
81
+ restore: null,
82
+ repair: null,
83
+ crystals: null,
84
+ economics: null,
85
+ diagnostics: null,
86
+ });
87
+
88
+ const poll = useCallback(() => {
89
+ setState((prev) => ({ ...prev, loading: true }));
90
+ fetchVectorCortexEvaluation()
91
+ .then((data) => setState((prev) => ({ ...prev, data, loading: false, error: null })))
92
+ .catch((e: unknown) =>
93
+ setState((prev) => ({
94
+ ...prev,
95
+ loading: false,
96
+ error: e instanceof Error ? e.message : String(e),
97
+ })),
98
+ );
99
+ fetchVectorCortexHealth().then((health) => setState((p) => ({ ...p, health }))).catch(() => {});
100
+ fetchVectorCortexLedger().then((ledger) => setState((p) => ({ ...p, ledger }))).catch(() => {});
101
+ fetchVectorCortexTopology().then((topology) => setState((p) => ({ ...p, topology }))).catch(() => {});
102
+ fetchVectorCortexQuery().then((query) => setState((p) => ({ ...p, query }))).catch(() => {});
103
+ fetchVectorCortexShards().then((shards) => setState((p) => ({ ...p, shards }))).catch(() => {});
104
+ fetchVectorCortexReconstruct().then((reconstruct) => setState((p) => ({ ...p, reconstruct }))).catch(() => {});
105
+ fetchVectorCortexPlans().then((plans) => setState((p) => ({ ...p, plans }))).catch(() => {});
106
+ fetchVectorCortexRender().then((render) => setState((p) => ({ ...p, render }))).catch(() => {});
107
+ fetchVectorCortexRollout().then((rollout) => setState((p) => ({ ...p, rollout }))).catch(() => {});
108
+ fetchVectorCortexClosureProof().then((closureProof) => setState((p) => ({ ...p, closureProof }))).catch(() => {});
109
+ fetchVectorCortexRestore().then((restore) => setState((p) => ({ ...p, restore }))).catch(() => {});
110
+ fetchVectorCortexRepair().then((repair) => setState((p) => ({ ...p, repair }))).catch(() => {});
111
+ fetchVectorCortexCrystals().then((crystals) => setState((p) => ({ ...p, crystals }))).catch(() => {});
112
+ fetchVectorCortexEconomics().then((economics) => setState((p) => ({ ...p, economics }))).catch(() => {});
113
+ fetchVectorCortexDiagnostics().then((diagnostics) => setState((p) => ({ ...p, diagnostics }))).catch(() => {});
114
+ }, []);
115
+
116
+ useEffect(() => {
117
+ poll();
118
+ const id = setInterval(poll, 5000);
119
+ return () => clearInterval(id);
120
+ }, [poll]);
121
+
122
+ return [state, poll];
123
+ }
@@ -0,0 +1,63 @@
1
+ /**
2
+ * dashboard-client/src/types/vector-cortex-vc7.ts — VC7-era client view types.
3
+ *
4
+ * Extracted from vector-cortex.ts to keep the parent file under the 300-line
5
+ * soft limit (soft-as-hard gate). Each interface mirrors a reader-only server
6
+ * API contract: counts + codes only, never prompt payloads, digests, or session
7
+ * bytes.
8
+ */
9
+
10
+ /**
11
+ * Reader-only frozen-crystal cache view (VC7A). Counts + byte volumes + CRY_*
12
+ * codes only — a crystal is a rendered prompt, so no frozen bytes, covered
13
+ * ranges, digests, or session ids ever reach the client.
14
+ */
15
+ export interface VectorCortexCrystalsView {
16
+ enabled: boolean;
17
+ mode: "A" | "B" | "C";
18
+ crystalCount: number;
19
+ totalBytes: number;
20
+ hits: number;
21
+ misses: number;
22
+ hitBytes: number;
23
+ writes: number;
24
+ duplicateWrites: number;
25
+ collisions: number;
26
+ lastFailure: string | null;
27
+ updatedAt: string;
28
+ }
29
+
30
+ /**
31
+ * Reader-only cache-economics diagnostics view (VC7B). Counts + ECON_* codes only
32
+ * — never prices, digests, ranges, or session ids.
33
+ */
34
+ export interface VectorCortexEconomicsView {
35
+ enabled: boolean;
36
+ mode: "A" | "B" | "C";
37
+ profileCount: number;
38
+ provenExclusions: number;
39
+ unprovenExclusions: number;
40
+ lastFailure: string | null;
41
+ updatedAt: string;
42
+ }
43
+
44
+ /**
45
+ * Reader-only cache miss-diagnostics view (VC7C). One count per EXCLUSIVE miss
46
+ * class plus breaker state and CACHE_* / M5_* codes only — a miss diagnostic would
47
+ * otherwise carry the missed request itself, so no request payload, request
48
+ * digest, covered range, span digest, or session id ever reaches the client.
49
+ */
50
+ export interface VectorCortexDiagnosticsView {
51
+ enabled: boolean;
52
+ mode: "A" | "B" | "C";
53
+ profileMisses: number;
54
+ rangeMisses: number;
55
+ dependencyMisses: number;
56
+ requestMisses: number;
57
+ generationMisses: number;
58
+ unknownMisses: number;
59
+ serveBlocked: number;
60
+ breakerState: string;
61
+ lastFailure: string | null;
62
+ updatedAt: string;
63
+ }
@@ -256,36 +256,8 @@ export interface VectorCortexClosureProofView {
256
256
  updatedAt: string;
257
257
  }
258
258
 
259
- /**
260
- * Reader-only frozen-crystal cache view (VC7A). Counts + byte volumes + CRY_*
261
- * codes only — a crystal is a rendered prompt, so no frozen bytes, covered
262
- * ranges, digests, or session ids ever reach the client.
263
- */
264
- export interface VectorCortexCrystalsView {
265
- enabled: boolean;
266
- mode: "A" | "B" | "C";
267
- crystalCount: number;
268
- totalBytes: number;
269
- hits: number;
270
- misses: number;
271
- hitBytes: number;
272
- writes: number;
273
- duplicateWrites: number;
274
- collisions: number;
275
- lastFailure: string | null;
276
- updatedAt: string;
277
- }
278
-
279
- /**
280
- * Reader-only cache-economics diagnostics view (VC7B). Counts + ECON_* codes only
281
- * — never prices, digests, ranges, or session ids.
282
- */
283
- export interface VectorCortexEconomicsView {
284
- enabled: boolean;
285
- mode: "A" | "B" | "C";
286
- profileCount: number;
287
- provenExclusions: number;
288
- unprovenExclusions: number;
289
- lastFailure: string | null;
290
- updatedAt: string;
291
- }
259
+ export type {
260
+ VectorCortexCrystalsView,
261
+ VectorCortexEconomicsView,
262
+ VectorCortexDiagnosticsView,
263
+ } from "./vector-cortex-vc7.js";
@@ -0,0 +1,76 @@
1
+ /**
2
+ * api-contracts/vector-cortex-diagnostics.ts — VC7C cache-diagnostics API
3
+ * contract.
4
+ *
5
+ * PREVENT-PI-004: type definitions only, no network code.
6
+ * PREVENT-011: no `any` type.
7
+ *
8
+ * Reader-only GET /api/vector-cortex/cache-diagnostics view (VC7C).
9
+ *
10
+ * COUNTS + CODES ONLY, and this surface is the most dangerous one in the whole
11
+ * VC7 cache phase. A cache MISS DIAGNOSTIC exists to answer "why did this exact
12
+ * request not hit the cache?", and the honest answer is naturally phrased in
13
+ * terms of the very things that must never leave the process: the full request
14
+ * payload that was hashed, its RequestHashV2 digest, the covered source ranges,
15
+ * the span/covered digests, the provider profile digest and the session id that
16
+ * frames the conversation. Every one of those is precisely the evidence a
17
+ * debugger would want inline — which is exactly why an unguarded diagnostic
18
+ * field here leaks the framed conversation itself (SECURITY_PRIVACY). The
19
+ * classification is therefore projected down to a COUNT PER MISS CLASS before it
20
+ * ever reaches this contract: the class names are a closed enumeration fixed by
21
+ * the sprint, so a count discloses nothing about content.
22
+ *
23
+ * This view exposes ONLY:
24
+ * - whether the VC7C flag is enabled and the runtime triad mode it implies;
25
+ * - one count per exclusive miss class (profile, range, dependency, request,
26
+ * generation, unknown) — classification is exclusive, so a single miss
27
+ * increments exactly one of these six counters and they sum to the total;
28
+ * - how many cache serves the breaker blocked (a count, never the blocked key
29
+ * or the entry it would have served);
30
+ * - the breaker's observable state and the last CACHE/M5 rejection code.
31
+ * Request payloads, request digests, covered ranges, span digests, profile
32
+ * digests, and session ids live in the structured event log / conformance
33
+ * corpus, never here.
34
+ */
35
+
36
+ /** Runtime triad mode implied by the VC7C flag state. */
37
+ export type VectorCortexDiagnosticsMode = "A" | "B" | "C";
38
+
39
+ /**
40
+ * Reader-only cache-diagnostics view for
41
+ * GET /api/vector-cortex/cache-diagnostics (VC7C).
42
+ */
43
+ export interface VectorCortexDiagnosticsView {
44
+ /** Whether the VC7C cache-diagnostics flag is enabled. */
45
+ readonly enabled: boolean;
46
+ /**
47
+ * Runtime triad mode: "A" a crystal was served from cache,
48
+ * "B" a fresh render was forced by a breaker condition,
49
+ * "C" all caches are bypassed (flag off, or render and cache diagnostics
50
+ * disagree) so nothing is served from cache.
51
+ */
52
+ readonly mode: VectorCortexDiagnosticsMode;
53
+ /** Misses classified as a provider-profile mismatch (count only). */
54
+ readonly profileMisses: number;
55
+ /** Misses classified as a covered-range mismatch (count only). */
56
+ readonly rangeMisses: number;
57
+ /** Misses classified as a dependency high-water mismatch (count only). */
58
+ readonly dependencyMisses: number;
59
+ /** Misses classified as a request (RequestHashV2) mismatch (count only). */
60
+ readonly requestMisses: number;
61
+ /** Misses classified as a stale/invalidated generation (count only). */
62
+ readonly generationMisses: number;
63
+ /** Misses no earlier class claimed — the terminal fallback (count only). */
64
+ readonly unknownMisses: number;
65
+ /**
66
+ * Cache serves the breaker demoted BEFORE serving, on collision, stale
67
+ * generation, digest failure, or profile mismatch (a count, never the key).
68
+ */
69
+ readonly serveBlocked: number;
70
+ /** Observable cache-breaker state (a state name, not a payload). */
71
+ readonly breakerState: string;
72
+ /** Last diagnostics rejection reason (a CACHE or M5 code), or null. */
73
+ readonly lastFailure: string | null;
74
+ /** ISO timestamp of the snapshot. */
75
+ readonly updatedAt: string;
76
+ }
@@ -68,6 +68,10 @@ import { handleVectorCortexCrystals } from "./routes-vector-cortex-crystals.js";
68
68
  // independent of the crystals handler and every file stays well under the
69
69
  // 400-line extension soft limit.
70
70
  import { handleVectorCortexEconomics } from "./routes-vector-cortex-economics.js";
71
+ // VC7C cache miss diagnostics + breakers gets its own module so the
72
+ // diagnostics seam stays independent of economics and every file stays well
73
+ // under the 400-line extension soft limit.
74
+ import { handleVectorCortexDiagnostics } from "./routes-vector-cortex-diagnostics.js";
71
75
 
72
76
  /**
73
77
  * Dispatch a request through every registered route handler.
@@ -124,5 +128,6 @@ export function dispatchRoutes(
124
128
  if (handleVectorCortexRepair(req, res, ctx)) return true;
125
129
  if (handleVectorCortexCrystals(req, res, ctx)) return true;
126
130
  if (handleVectorCortexEconomics(req, res, ctx)) return true;
131
+ if (handleVectorCortexDiagnostics(req, res, ctx)) return true;
127
132
  return false;
128
133
  }
@@ -168,5 +168,11 @@ export const VECTOR_CORTEX_SETTINGS: SettingGroup = {
168
168
  "Provider cache economics: extends the VC5B provider registry with cache economics (read/write price, TTL, minimum prefix, and a mandatory exclusion fixture id). Answers whether reusing a frozen crystal is actually worth it — a cache WRITE typically costs more than an uncached token, so a cache only pays off once a written prefix is re-read enough times before TTL expiry. Net savings are reported (never clamped at zero, so a losing cache stays visible) and every exclusion MUST name a proving conformance fixture or it is rejected (ECON_EXCLUSION_UNPROVEN). A compiled crystal boundary still reuses the VC7A key unchanged, and a randomized session-level experiment assigns arms by a stable hash so a lost assignment journal re-derives the same arm. OFF = byte-identical predecessor (VC7A); the economics/compiler/experiment arithmetic still runs, only the reporter + dashboard seam is suppressed.",
169
169
  true,
170
170
  ),
171
+ boolDirect(
172
+ "MEGACOMPACT_VC7C",
173
+ "VC7C Cache Diagnostics & Breakers",
174
+ "Cache miss diagnostics + cache-level breakers + the completed M5 request-hash-v2 switch. Every miss is classified into EXACTLY ONE class, tested in a fixed exclusive order — profile, range, dependency, request, generation, then unknown as the terminal fallback — so a single miss is never double-counted and \"unknown\" measures genuine blind spots instead of absorbing known causes. Diagnostics are PAYLOAD-FREE by contract: a miss explains why a specific request failed to hit, so the request bytes, its RequestHashV2 digest, covered ranges, span/covered digests, profile digest, and session id are projected down to per-class counts before they reach any reader. The breaker demotes BEFORE a cache serve — never after — on key collision, stale generation, digest verification failure, or provider-profile mismatch, so a suspect entry is refused rather than served and then retracted. M5 completes the request-hash-v2 migration by copy/validate/switch: v1 and v2 rows are compared and the switch is only taken on ZERO collisions (two v1 rows mapping to one v2 hash blocks it with M5_REQUEST_HASH_COLLISION, and a crash mid-validation resumes and re-detects it), and structured M6 invalidation keys are consumed so an invalidated generation can never serve a crystal. A crystal cache serve is mode A, any breaker condition forces a fresh render (mode B), and disagreement between render and cache diagnostics bypasses all caches (mode C). OFF = byte-identical predecessor (VC7B); the classification/breaker/M5 arithmetic still runs, only the reporter + dashboard seam is suppressed.",
175
+ true,
176
+ ),
171
177
  ],
172
178
  };
@@ -0,0 +1,77 @@
1
+ /**
2
+ * dashboard-server/routes-vector-cortex-diagnostics.ts — VC7C cache-diagnostics
3
+ * dashboard route.
4
+ *
5
+ * Reader-only GET /api/vector-cortex/cache-diagnostics returning the cache miss
6
+ * classification aggregate: whether the VC7C flag is enabled, the runtime triad
7
+ * mode, one count per exclusive miss class (profile, range, dependency, request,
8
+ * generation, unknown), how many cache serves the breaker blocked, the breaker
9
+ * state, and the last CACHE/M5 failure code.
10
+ *
11
+ * COUNTS + CODES ONLY. A cache miss diagnostic answers "why did THIS request
12
+ * miss?", so the natural (and forbidden) payload is the request itself: the
13
+ * hashed request bytes, its RequestHashV2 digest, the covered source ranges, the
14
+ * span/covered digests, the provider profile digest, and the session id. This
15
+ * route NEVER exposes any of them — the classification is projected to a count
16
+ * per closed-enumeration class before it reaches the wire (reader-only,
17
+ * SECURITY_PRIVACY). There is no mutation seam: misses are classified and
18
+ * breakers are tripped by the cache serve path, never by a dashboard request,
19
+ * and in particular the breaker can NOT be reset through this route. Non-GET is
20
+ * rejected outright.
21
+ *
22
+ * Split into its own file (rather than grown into routes-vector-cortex-economics.ts)
23
+ * to keep every extensions/ file well under the 400-line soft-as-hard limit.
24
+ *
25
+ * Guardrails: PREVENT-PI-004 (local in-process state only), PREVENT-011 (no
26
+ * `any`), reader-only aggregate (counts + codes only).
27
+ */
28
+
29
+ import type { IncomingMessage, ServerResponse } from "node:http";
30
+ import type { RouteContext } from "./routes-core.js";
31
+ import { VC7C_ENABLED } from "../../src/config.js";
32
+ import { sendJson } from "./routes-vector-cortex-shared.js";
33
+ import type { VectorCortexDiagnosticsView } from "./api-contracts/vector-cortex-diagnostics.js";
34
+
35
+ /**
36
+ * Reader-only GET /api/vector-cortex/cache-diagnostics (VC7C).
37
+ *
38
+ * Per-miss-class counts, breaker state, and CACHE and M5 codes only — a static
39
+ * reader-only aggregate seam with the same shape as the VC7B economics handler.
40
+ */
41
+ export function handleVectorCortexDiagnostics(
42
+ req: IncomingMessage,
43
+ res: ServerResponse,
44
+ _ctx: RouteContext,
45
+ ): boolean {
46
+ const url = req.url ?? "";
47
+ const path = url.split("?")[0] ?? url;
48
+ if (path !== "/api/vector-cortex/cache-diagnostics") return false;
49
+ if (req.method !== "GET") {
50
+ sendJson(res, 405, { error: "method_not_allowed" });
51
+ return true;
52
+ }
53
+
54
+ const enabled = VC7C_ENABLED();
55
+ // Flag-off routes to mode C: with VC7C off the diagnostics/breaker reporter is
56
+ // suppressed, so no cache serve is attested here and the surface reports the
57
+ // all-cache bypass outcome. Reporting A (crystal served) or B (fresh render
58
+ // forced by a breaker) would attest a cache decision this seam is not wired to
59
+ // observe. Mirrors how the VC7A/VC7B OFF views report the mode they take.
60
+ const mode: "A" | "B" | "C" = enabled ? "A" : "C";
61
+ const body: VectorCortexDiagnosticsView = {
62
+ enabled,
63
+ mode,
64
+ profileMisses: 0,
65
+ rangeMisses: 0,
66
+ dependencyMisses: 0,
67
+ requestMisses: 0,
68
+ generationMisses: 0,
69
+ unknownMisses: 0,
70
+ serveBlocked: 0,
71
+ breakerState: "closed",
72
+ lastFailure: null,
73
+ updatedAt: new Date().toISOString(),
74
+ };
75
+ sendJson(res, 200, body);
76
+ return true;
77
+ }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "pi-mega-compact",
3
- "version": "0.20.14",
3
+ "version": "0.20.16",
4
4
  "description": "Layered, local, vector-backed context compressor for pi — supersede/collapse/cluster compaction with deduped inline recall.",
5
5
  "type": "module",
6
6
  "license": "BSD-3-Clause",
@@ -218,6 +218,27 @@ export const VC7A_ENABLED = (): boolean => sprintFlag("MEGACOMPACT_VC7A");
218
218
  */
219
219
  export const VC7B_ENABLED = (): boolean => sprintFlag("MEGACOMPACT_VC7B");
220
220
 
221
+ /**
222
+ * VC7C — cache miss diagnostics, cache-level breakers and the completed M5
223
+ * request-hash-v2 switch. Default ON. `MEGACOMPACT_VC7C=0` disables and is
224
+ * byte-identical to the predecessor (VC7B): the miss `classify`, the breaker
225
+ * demotion decision and the M5 request-hash-v2 ARITHMETIC STILL RUN (they are
226
+ * PURE — an exclusive ordered comparison over already-computed digests plus a
227
+ * canonical length-prefixed SHA-256, with no clock, storage, or network), so a
228
+ * miss is classified into the SAME single class, a collision / stale generation
229
+ * / digest failure / profile mismatch still demotes BEFORE any cache serve, and
230
+ * the v2 hash of a given request is unchanged with the flag off. A cache is
231
+ * never allowed to serve a stale or colliding entry merely because reporting is
232
+ * off — that would be a correctness change, not a reporting change.
233
+ *
234
+ * The flag gates ONLY the `vector_cortex_cache_miss_classified` /
235
+ * `vector_cortex_cache_serve_blocked` events and the cache-diagnostics dashboard
236
+ * seam, which reports `enabled:false` + mode C when off. This flag MUST also be
237
+ * a dashboard SETTINGS toggle (visible in config UI, never in
238
+ * EXCLUDED_SETTINGS), mirroring VC4A..VC7B.
239
+ */
240
+ export const VC7C_ENABLED = (): boolean => sprintFlag("MEGACOMPACT_VC7C");
241
+
221
242
  // Breaker state machine constants (TRIAD_RESILIENCE.md §breaker) extracted to
222
243
  // vector-cortex-breakers.ts to keep this file under the 300-line soft limit.
223
244
  export {
package/src/config.ts CHANGED
@@ -174,6 +174,7 @@ export {
174
174
  VC6C_ENABLED,
175
175
  VC7A_ENABLED,
176
176
  VC7B_ENABLED,
177
+ VC7C_ENABLED,
177
178
  BREAKER_WINDOW_MS,
178
179
  BREAKER_MIN_ATTEMPTS,
179
180
  BREAKER_PERF_FAILURES,