@cat-factory/server 0.179.0 → 0.181.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 (34) hide show
  1. package/dist/agents/ContainerAgentExecutor.d.ts.map +1 -1
  2. package/dist/agents/ContainerAgentExecutor.js +6 -8
  3. package/dist/agents/ContainerAgentExecutor.js.map +1 -1
  4. package/dist/agents/contextFiles.d.ts +9 -10
  5. package/dist/agents/contextFiles.d.ts.map +1 -1
  6. package/dist/agents/contextFiles.js +27 -19
  7. package/dist/agents/contextFiles.js.map +1 -1
  8. package/dist/config/infraReachability.d.ts +33 -0
  9. package/dist/config/infraReachability.d.ts.map +1 -0
  10. package/dist/config/infraReachability.js +62 -0
  11. package/dist/config/infraReachability.js.map +1 -0
  12. package/dist/config/types.d.ts +32 -0
  13. package/dist/config/types.d.ts.map +1 -1
  14. package/dist/events/FanOutEventPublisher.d.ts +3 -1
  15. package/dist/events/FanOutEventPublisher.d.ts.map +1 -1
  16. package/dist/events/FanOutEventPublisher.js +13 -0
  17. package/dist/events/FanOutEventPublisher.js.map +1 -1
  18. package/dist/index.d.ts +3 -1
  19. package/dist/index.d.ts.map +1 -1
  20. package/dist/index.js +2 -0
  21. package/dist/index.js.map +1 -1
  22. package/dist/modules/workspaces/WorkspaceController.d.ts +0 -51
  23. package/dist/modules/workspaces/WorkspaceController.d.ts.map +1 -1
  24. package/dist/modules/workspaces/WorkspaceController.js +13 -70
  25. package/dist/modules/workspaces/WorkspaceController.js.map +1 -1
  26. package/dist/modules/workspaces/infraSetup.d.ts +65 -0
  27. package/dist/modules/workspaces/infraSetup.d.ts.map +1 -0
  28. package/dist/modules/workspaces/infraSetup.js +89 -0
  29. package/dist/modules/workspaces/infraSetup.js.map +1 -0
  30. package/dist/runtime/infraReachability.d.ts +16 -0
  31. package/dist/runtime/infraReachability.d.ts.map +1 -0
  32. package/dist/runtime/infraReachability.js +188 -0
  33. package/dist/runtime/infraReachability.js.map +1 -0
  34. package/package.json +8 -8
@@ -0,0 +1,188 @@
1
+ import { INFRA_SETUP_PROBED_AREAS } from '@cat-factory/contracts';
2
+ import { decideReachability, describeError, recordedUnreachableAreas, redactSecrets, runBestEffort, } from '@cat-factory/kernel';
3
+ import { infraSetupAreaApplies } from '../modules/workspaces/infraSetup.js';
4
+ /**
5
+ * Run one reachability pass across every workspace. Returns how many areas started failing and how
6
+ * many recovered — the two numbers worth a log line; an unchanged pass reports zeros and stays
7
+ * quiet. Enumerates boards from the workspace projection (`workspaceService.list(null)`), the same
8
+ * tenant-enumeration shape the platform-health and artifact-retention sweeps use.
9
+ *
10
+ * Time comes from the notification service's injected clock (`raise`/`clearByType` stamp `now`
11
+ * themselves) and from `Date.now()` for the pushed event, matching every other publisher.
12
+ */
13
+ export async function sweepInfraReachability(container, logger) {
14
+ const cfg = container.config.infraReachability;
15
+ const notifications = container.notifications;
16
+ if (!cfg.enabled || !notifications)
17
+ return { raised: 0, cleared: 0 };
18
+ // NEVER from a mothership-mode node. This is a DEPLOYMENT-level sweep: every board such a node
19
+ // can see belongs to the org, so each laptop running it would probe every workspace's
20
+ // infrastructure and then race every other laptop on the same shared cards. The mothership runs
21
+ // it. This is also why the card read stays mothership-INTERNAL (`listOpenByType` is classified
22
+ // `sweeper`, not allow-listed on the persistence RPC) — without this guard the pass would fail
23
+ // with `unknown_method` on every interval instead of being cleanly out of scope.
24
+ if (container.config.localMode?.mothership)
25
+ return { raised: 0, cleared: 0 };
26
+ const sources = probeSources(container);
27
+ // Nothing on this deployment can be probed (neither integration is wired, or neither area applies
28
+ // here), so the pass would enumerate every board only to skip it. Bail before the workspace read.
29
+ if (!sources.ephemeralEnvironments && !sources.agentExecutor)
30
+ return { raised: 0, cleared: 0 };
31
+ const workspaces = await container.workspaceService.list(null);
32
+ const workspaceIds = workspaces.map((ws) => ws.id);
33
+ // Which boards already hold an open card — ONE batched read up front rather than a
34
+ // `findOpenByType` point-read per workspace inside the loop (that N+1 would run across the whole
35
+ // deployment every pass). It is also the state `decideReachability` compares against, so the
36
+ // healthy steady state costs exactly this one read plus the probes.
37
+ const cards = await notifications.service.listOpenByType(workspaceIds, 'infra_unreachable');
38
+ let raised = 0;
39
+ let cleared = 0;
40
+ for (const workspaceId of workspaceIds) {
41
+ try {
42
+ const previous = recordedUnreachableAreas(cards.get(workspaceId));
43
+ const observed = await probeWorkspace(sources, workspaceId, cfg.probeTimeoutMs);
44
+ const decision = decideReachability(previous, observed);
45
+ // Gate on the RECORD, not on the transitions: an area that is no longer configured drops out
46
+ // of the record while announcing nothing, and short-circuiting on `transitions` would leave
47
+ // its card open forever (nothing else ever clears it).
48
+ if (!decision.recordChanged && decision.transitions.length === 0)
49
+ continue;
50
+ // Persist FIRST, announce second. The card is the durable record the next pass compares
51
+ // against, so a push that fails after it commits costs one live banner update (the board's
52
+ // own snapshot still folds the card on next load); a push that succeeded against a record
53
+ // that never landed would re-announce the same outage on every subsequent pass.
54
+ if (decision.recordChanged) {
55
+ if (decision.unreachableAreas.length > 0) {
56
+ await notifications.service.raise(workspaceId, {
57
+ type: 'infra_unreachable',
58
+ blockId: null,
59
+ executionId: null,
60
+ ...cardContent(decision.unreachableAreas),
61
+ payload: { unreachableAreas: decision.unreachableAreas },
62
+ });
63
+ }
64
+ else {
65
+ await notifications.service.clearByType(workspaceId, 'infra_unreachable');
66
+ }
67
+ }
68
+ for (const change of decision.transitions) {
69
+ if (change.status === 'unreachable')
70
+ raised += 1;
71
+ else
72
+ cleared += 1;
73
+ await publish(container, workspaceId, change);
74
+ }
75
+ }
76
+ catch (err) {
77
+ logger?.warn('infra-reachability: failed to evaluate workspace', {
78
+ scope: 'infra-reachability',
79
+ workspaceId,
80
+ ...describeError(err),
81
+ });
82
+ }
83
+ }
84
+ return { raised, cleared };
85
+ }
86
+ /**
87
+ * Bind the per-area probes this deployment can actually run. An area that is absent here is one
88
+ * `decideReachability` never hears about, so it keeps whatever the card recorded rather than being
89
+ * reported as recovered by a deployment that never asked.
90
+ *
91
+ * Wiring is necessary but NOT sufficient: each area must also APPLY to this deployment
92
+ * (`infraSetupAreaApplies`, the same predicate the snapshot projection reports `not_applicable`
93
+ * from). Gating on the wired module alone was strictly looser than the projection — on Cloudflare
94
+ * and local mode the runner pool is an optional alternate target, so a dead one raised a card and
95
+ * paged Slack for an area whose banner the projection then refused to render. Probe only what this
96
+ * deployment would actually nag about.
97
+ */
98
+ function probeSources(container) {
99
+ const environments = container.environments?.connectionService;
100
+ const runners = container.runners?.connectionService;
101
+ const applies = (area) => infraSetupAreaApplies(container, area);
102
+ return {
103
+ ...(environments && applies('ephemeralEnvironments')
104
+ ? { ephemeralEnvironments: (ws) => environments.probeSavedConnection(ws) }
105
+ : {}),
106
+ ...(runners && applies('agentExecutor')
107
+ ? { agentExecutor: (ws) => runners.probeSavedConnection(ws) }
108
+ : {}),
109
+ };
110
+ }
111
+ /**
112
+ * Probe every wired area for one workspace, concurrently — the areas are independent connections,
113
+ * so a slow apiserver must not serialise behind a slow runner pool.
114
+ */
115
+ async function probeWorkspace(sources, workspaceId, timeoutMs) {
116
+ const wired = INFRA_SETUP_PROBED_AREAS.filter((area) => sources[area]);
117
+ return Promise.all(wired.map((area) => probeArea(() => sources[area](workspaceId), area, timeoutMs)));
118
+ }
119
+ /**
120
+ * Run one area's probe into a {@link ProbeOutcome}.
121
+ *
122
+ * FOUR results, deliberately distinct (degrade loudly), because they need four dispositions:
123
+ * - a probe that ANSWERED `ok: false`, or didn't answer inside the budget ⇒ a real outage;
124
+ * - a probe that THREW, or that could not be asked (`unprobeable`) ⇒ INDETERMINATE, leaving the
125
+ * record untouched. A throw is a local fault (the connection wouldn't resolve, its secret bundle
126
+ * wouldn't decrypt — classically a node with no access to the sealing key), and blaming the
127
+ * operator's cluster for our own missing key is exactly the "never infer a cause from the
128
+ * presence of an error" trap;
129
+ * - nothing registered (`absent`) ⇒ NOT_CONFIGURED, which forgets a recorded outage without
130
+ * announcing a recovery, so a card can't outlive the connection it reports on.
131
+ *
132
+ * NOTE the timeout only stops us WAITING: the underlying request keeps running to its own
133
+ * completion, because neither connection-test port takes an `AbortSignal` today. Threading one
134
+ * through both provider ports (and every backend that implements them) is the real fix and is out
135
+ * of this change's scope; the cost is a wasted in-flight request per timed-out probe, bounded by
136
+ * the interval.
137
+ */
138
+ async function probeArea(probe, area, timeoutMs) {
139
+ let timer;
140
+ try {
141
+ const timeout = new Promise((resolve) => {
142
+ timer = setTimeout(() => resolve('timeout'), timeoutMs);
143
+ });
144
+ const probed = await Promise.race([probe(), timeout]);
145
+ if (probed === 'timeout') {
146
+ return { area, verdict: 'unreachable', detail: `No answer within ${timeoutMs}ms` };
147
+ }
148
+ if (probed.state === 'absent')
149
+ return { area, verdict: 'not_configured' };
150
+ if (probed.state === 'unprobeable') {
151
+ return { area, verdict: 'indeterminate', detail: probed.reason };
152
+ }
153
+ if (probed.result.ok)
154
+ return { area, verdict: 'reachable' };
155
+ // A provider's failure message routinely echoes the request URL it called, which can carry a
156
+ // token in the query — so it is scrubbed here, at the point it becomes operator-facing text.
157
+ const detail = probed.result.message ? redactSecrets(probed.result.message) : null;
158
+ return { area, verdict: 'unreachable', ...(detail ? { detail } : {}) };
159
+ }
160
+ catch {
161
+ return { area, verdict: 'indeterminate' };
162
+ }
163
+ finally {
164
+ if (timer)
165
+ clearTimeout(timer);
166
+ }
167
+ }
168
+ /** Human-facing card text, derived from the failing AREAS only (see the payload's dedup note). */
169
+ function cardContent(areas) {
170
+ const names = {
171
+ ephemeralEnvironments: 'the ephemeral-environment provider',
172
+ agentExecutor: 'the self-hosted runner pool',
173
+ binaryStorage: 'binary storage',
174
+ };
175
+ const listed = areas.map((area) => names[area]).join(' and ');
176
+ return {
177
+ title: 'Infrastructure is unreachable',
178
+ body: `A live probe could not reach ${listed}. It is configured, so this is an outage rather than a setup gap — the agents that depend on it cannot run until it answers again.`,
179
+ };
180
+ }
181
+ /** Push one transition, best-effort: a failed push must never abort the pass. */
182
+ async function publish(container, workspaceId, change) {
183
+ const publisher = container.executionEventPublisher;
184
+ if (!publisher.infraSetupChanged)
185
+ return;
186
+ await runBestEffort(container.logger, 'infra-reachability publish', () => publisher.infraSetupChanged(workspaceId, change), { workspaceId, area: change.area, status: change.status });
187
+ }
188
+ //# sourceMappingURL=infraReachability.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"infraReachability.js","sourceRoot":"","sources":["../../src/runtime/infraReachability.ts"],"names":[],"mappings":"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"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@cat-factory/server",
3
- "version": "0.179.0",
3
+ "version": "0.181.0",
4
4
  "description": "Runtime-neutral HTTP layer for the Agent Architecture Board: the Hono controllers, middleware (auth/authz/CORS/error), request helpers and the gateway seams shared by every deployment facade (Cloudflare Worker, Node service).",
5
5
  "repository": {
6
6
  "type": "git",
@@ -30,13 +30,13 @@
30
30
  "hono": "^4.12.32",
31
31
  "pino": "^10.3.1",
32
32
  "valibot": "^1.4.2",
33
- "@cat-factory/agents": "0.88.0",
34
- "@cat-factory/contracts": "0.197.0",
35
- "@cat-factory/integrations": "0.111.1",
36
- "@cat-factory/kernel": "0.194.0",
37
- "@cat-factory/orchestration": "0.171.1",
38
- "@cat-factory/prompt-fragments": "0.15.20",
39
- "@cat-factory/spend": "0.12.124"
33
+ "@cat-factory/agents": "0.89.1",
34
+ "@cat-factory/contracts": "0.198.0",
35
+ "@cat-factory/integrations": "0.112.0",
36
+ "@cat-factory/kernel": "0.196.0",
37
+ "@cat-factory/orchestration": "0.172.1",
38
+ "@cat-factory/prompt-fragments": "0.15.21",
39
+ "@cat-factory/spend": "0.12.126"
40
40
  },
41
41
  "devDependencies": {
42
42
  "@types/node": "^26.1.1",