openmausbot 0.1.94 → 0.1.95

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 (145) hide show
  1. package/dist/assets/{DesktopViewer-bxM7NV3N.js → DesktopViewer-BwWpc4RK.js} +1 -1
  2. package/dist/assets/{abnfDiagram-O67JEVCF-BhMdJhRJ.js → abnfDiagram-O67JEVCF-jsQkIqTn.js} +1 -1
  3. package/dist/assets/{arc-B5itKDcx.js → arc-7kei4Hsu.js} +1 -1
  4. package/dist/assets/{architectureDiagram-NJMV4G6O-C5d7UY6U.js → architectureDiagram-NJMV4G6O-CRWDFDMq.js} +1 -1
  5. package/dist/assets/{blockDiagram-BEXU5L5S-BrZIhMmu.js → blockDiagram-BEXU5L5S-CTKW_IKs.js} +1 -1
  6. package/dist/assets/{c4Diagram-YGBWAQC7-7I0ArfbD.js → c4Diagram-YGBWAQC7-BBTW7-6M.js} +1 -1
  7. package/dist/assets/channel-DS2NbT5x.js +1 -0
  8. package/dist/assets/{chunk-2Q5K7J3B-BnEsyN36.js → chunk-2Q5K7J3B-M_Ox-MkD.js} +1 -1
  9. package/dist/assets/{chunk-3FUC2YCW-BXATQ52s.js → chunk-3FUC2YCW-D2YiN-Ud.js} +2 -2
  10. package/dist/assets/{chunk-5VM5RSS4-B0BpTkEx.js → chunk-5VM5RSS4-BmVYJ0f8.js} +1 -1
  11. package/dist/assets/{chunk-GTNCS2PH-BtLTz6FR.js → chunk-GTNCS2PH-BtiLVVnZ.js} +1 -1
  12. package/dist/assets/{chunk-GWA4HPMP-D6gcZOYt.js → chunk-GWA4HPMP-DFYSb6J6.js} +1 -1
  13. package/dist/assets/{chunk-JWPE2WC7-DCLrosvf.js → chunk-JWPE2WC7-mknKBzgV.js} +1 -1
  14. package/dist/assets/{chunk-NETBCI7D-B9JsknV9.js → chunk-NETBCI7D-DgSYGiOu.js} +1 -1
  15. package/dist/assets/{chunk-WEXAMYUT-CsoTxw7z.js → chunk-WEXAMYUT-C7ZvuguH.js} +1 -1
  16. package/dist/assets/{chunk-XXDRQBXY-0F_frB0c.js → chunk-XXDRQBXY-CPqxINpA.js} +1 -1
  17. package/dist/assets/{classDiagram-v2-NBCMYWYE-DkrpnflX.js → classDiagram-v2-NBCMYWYE-Cd6xfJaC.js} +1 -1
  18. package/dist/assets/{cose-bilkent-JH36ORCC-BNDwYBt9.js → cose-bilkent-JH36ORCC-BSXY5qRh.js} +1 -1
  19. package/dist/assets/{cynefin-OW5HDTMX-JUkNr1Mk.js → cynefin-OW5HDTMX-D_lhEMj1.js} +1 -1
  20. package/dist/assets/{cynefinDiagram-VND7K2PF-DKeh9N4M.js → cynefinDiagram-VND7K2PF-Da9FrFwk.js} +1 -1
  21. package/dist/assets/{dagre-6A5THRUB-ve-6T_wX.js → dagre-6A5THRUB-T77jMOXe.js} +1 -1
  22. package/dist/assets/{diagram-22UHCM2B-BuJ2d8rT.js → diagram-22UHCM2B-Dkj96X5E.js} +1 -1
  23. package/dist/assets/{diagram-3UASUU5V-BgOs_Ni-.js → diagram-3UASUU5V-CMi9zlD_.js} +1 -1
  24. package/dist/assets/{diagram-ATOU4E4O-DMK6VmcP.js → diagram-ATOU4E4O-CXK6YUfS.js} +1 -1
  25. package/dist/assets/{diagram-CDSNMT55-DksASlcY.js → diagram-CDSNMT55-BE7B1u9Q.js} +1 -1
  26. package/dist/assets/{diagram-MLGK6HIB-Bgn8I5k6.js → diagram-MLGK6HIB-CCMQphKr.js} +1 -1
  27. package/dist/assets/{diagram-MPIPVDR6-zK0jqO8N.js → diagram-MPIPVDR6-iHJ_-tGH.js} +1 -1
  28. package/dist/assets/{ebnfDiagram-ZINNZB2B-vKrbzTwr.js → ebnfDiagram-ZINNZB2B-DONsCWQ7.js} +1 -1
  29. package/dist/assets/{elk-276RUBZZ-Bzv2mPNf.js → elk-276RUBZZ-CU_WOaXk.js} +1 -1
  30. package/dist/assets/{erDiagram-OPXOYQCR-CvOyYuxu.js → erDiagram-OPXOYQCR-BeYwM04G.js} +1 -1
  31. package/dist/assets/{flowDiagram-KWPJA3E3-CtbnDbc0.js → flowDiagram-KWPJA3E3-Bdw9DqEl.js} +1 -1
  32. package/dist/assets/{ganttDiagram-FUAMR5RP-c4dMRYyG.js → ganttDiagram-FUAMR5RP-C9iwq3qm.js} +1 -1
  33. package/dist/assets/{gitGraphDiagram-X574FWY7-B34uaQho.js → gitGraphDiagram-X574FWY7-Dx-VWzUg.js} +1 -1
  34. package/dist/assets/{index-CPiqc_DN.js → index-KygHRE3E.js} +1 -1
  35. package/dist/assets/index-NF7XCHAy.css +1 -0
  36. package/dist/assets/index-X_5ydXIE.js +610 -0
  37. package/dist/assets/{infoDiagram-VRGFBTTK-o64ma4CI.js → infoDiagram-VRGFBTTK-BG7uaEd4.js} +1 -1
  38. package/dist/assets/{ishikawaDiagram-OU5B5YK6-DV4C9BAm.js → ishikawaDiagram-OU5B5YK6-D72WAXnM.js} +1 -1
  39. package/dist/assets/{journeyDiagram-ZHPQQLJL-Bf0AHk1H.js → journeyDiagram-ZHPQQLJL-DKH1gjYT.js} +1 -1
  40. package/dist/assets/{kanban-definition-PNTS6WVX-B1UMSKmE.js → kanban-definition-PNTS6WVX-3upm9JUT.js} +1 -1
  41. package/dist/assets/{linear-BpKhuyLm.js → linear-CcR4pc0-.js} +1 -1
  42. package/dist/assets/{mermaid.core-B_BKNCw5.js → mermaid.core-C6yU5FSS.js} +5 -5
  43. package/dist/assets/{mindmap-definition-NLK3R4M7-DeARruT1.js → mindmap-definition-NLK3R4M7-DOI2xEuv.js} +1 -1
  44. package/dist/assets/{pegDiagram-GJSIUBJH-BOQEk_1D.js → pegDiagram-GJSIUBJH-BVWJSgLd.js} +1 -1
  45. package/dist/assets/{pieDiagram-5QR66LMP-EIfoiTZo.js → pieDiagram-5QR66LMP-jtbYezhq.js} +1 -1
  46. package/dist/assets/{quadrantDiagram-O4NWA36T-GgZwT-fi.js → quadrantDiagram-O4NWA36T-g0u8mtPX.js} +1 -1
  47. package/dist/assets/{railroadDiagram-XR7U4H2S-D9rDQomj.js → railroadDiagram-XR7U4H2S-k8689Wny.js} +1 -1
  48. package/dist/assets/{requirementDiagram-PLB6GJNP-DAh1MIeo.js → requirementDiagram-PLB6GJNP-DsJ22PDt.js} +1 -1
  49. package/dist/assets/{sankeyDiagram-IPEJSGJF-CPr6Uz64.js → sankeyDiagram-IPEJSGJF-CneWBRgG.js} +1 -1
  50. package/dist/assets/{sequenceDiagram-PO4LG4MO-BU6VIdcm.js → sequenceDiagram-PO4LG4MO-DWsFCWap.js} +1 -1
  51. package/dist/assets/{sizeCapture-INFHLROL-qF2HO41r.js → sizeCapture-INFHLROL-Bvf0YE3S.js} +1 -1
  52. package/dist/assets/{stateDiagram-v2-GCMORJYK-DlJ8G4MD.js → stateDiagram-v2-GCMORJYK-Bxb3Iei8.js} +1 -1
  53. package/dist/assets/{swimlanes-2SLR337P-DzYE8I54.js → swimlanes-2SLR337P-DLkk7W4A.js} +1 -1
  54. package/dist/assets/swimlanesDiagram-TC7HE7FX-C6bZtBXk.js +8 -0
  55. package/dist/assets/{timeline-definition-EJHVYXUP-B7wzEQ0A.js → timeline-definition-EJHVYXUP-KR9bIHYC.js} +1 -1
  56. package/dist/assets/{usecaseDiagram-POWQR4AR-BvGgrxIP.js → usecaseDiagram-POWQR4AR-DfsOrj8t.js} +1 -1
  57. package/dist/assets/{vennDiagram-UO4OBE2U-CEECdgQg.js → vennDiagram-UO4OBE2U-DRSTzG3h.js} +1 -1
  58. package/dist/assets/{wardleyDiagram-VNRHLVJA-XQHA0P_P.js → wardleyDiagram-VNRHLVJA-DtEdhPgT.js} +1 -1
  59. package/dist/assets/{xychartDiagram-PMCCYNJV-B5mLcZI2.js → xychartDiagram-PMCCYNJV-B-XhTxjG.js} +1 -1
  60. package/dist/index.html +2 -2
  61. package/dist-server/cloud-home-start.js +2 -1
  62. package/dist-server/companion/src/routes.js +39 -0
  63. package/dist-server/container-mcp.js +2 -2
  64. package/dist-server/drivers/agents-proxy.js +58 -38
  65. package/dist-server/enterprise/server/index.js +2 -1
  66. package/dist-server/{browser-proxy.js → harness-mcp-proxy.js} +35 -19
  67. package/dist-server/index.js +3159 -2313
  68. package/dist-server/local-computer.js +2 -1
  69. package/dist-server/openmausbot.js +314 -1336
  70. package/dist-server/pair-cli.js +314 -1336
  71. package/dist-server/proxy-paths.js +2 -1
  72. package/dist-server/server/account-signin.js +0 -2
  73. package/dist-server/server/activity.js +201 -0
  74. package/dist-server/server/auto-approve.js +6 -0
  75. package/dist-server/server/automatic-recovery.js +1 -1
  76. package/dist-server/server/boat-create-idempotency.js +0 -7
  77. package/dist-server/server/boat-delete-journal.js +0 -4
  78. package/dist-server/server/bot-package.js +1 -19
  79. package/dist-server/server/browser-runtime.js +1 -2
  80. package/dist-server/server/chief-of-staff.js +2 -3
  81. package/dist-server/server/cloud-backend.js +0 -4
  82. package/dist-server/server/cloud-computer-tools.js +110 -0
  83. package/dist-server/server/cloud-home.js +0 -1
  84. package/dist-server/server/cloud-lending.js +0 -3
  85. package/dist-server/server/composio.js +31 -2
  86. package/dist-server/server/computer-control.js +0 -15
  87. package/dist-server/server/computer-observation.js +0 -74
  88. package/dist-server/server/config.js +29 -1
  89. package/dist-server/server/container-computer.js +7 -19
  90. package/dist-server/server/contracts.js +9 -0
  91. package/dist-server/server/control-client.js +4 -10
  92. package/dist-server/server/drivers/acp/core.js +7 -5
  93. package/dist-server/server/drivers/agents-call.js +42 -29
  94. package/dist-server/server/drivers/agents-catalog.js +24 -11
  95. package/dist-server/server/drivers/agents-proxy.js +8 -30
  96. package/dist-server/server/drivers/antigravity.js +1 -4
  97. package/dist-server/server/drivers/boatagent.js +23 -4
  98. package/dist-server/server/drivers/cerebras.js +3 -3
  99. package/dist-server/server/drivers/chat-mcp-tools.js +4 -7
  100. package/dist-server/server/drivers/claude.js +16 -14
  101. package/dist-server/server/drivers/openai-chat.js +3 -6
  102. package/dist-server/server/drivers/retry.js +8 -4
  103. package/dist-server/server/engine-install.js +1 -5
  104. package/dist-server/server/harness/registry.js +0 -1
  105. package/dist-server/server/{browser-proxy.js → harness-mcp-proxy.js} +40 -20
  106. package/dist-server/server/index.js +789 -256
  107. package/dist-server/server/lending-memory.js +12 -8
  108. package/dist-server/server/memory-entries.js +38 -8
  109. package/dist-server/server/memory-organize.js +1 -8
  110. package/dist-server/server/memory-topics.js +4 -4
  111. package/dist-server/server/memory-upkeep.js +13 -15
  112. package/dist-server/server/message-file.js +5 -9
  113. package/dist-server/server/outbound-counts.js +79 -0
  114. package/dist-server/server/outbound-requests.js +60 -0
  115. package/dist-server/server/package-import.js +1 -1
  116. package/dist-server/server/peer-delivery.js +1 -0
  117. package/dist-server/server/proxy-paths.js +2 -1
  118. package/dist-server/server/room-handoffs.js +5 -13
  119. package/dist-server/server/routine-requests.js +1 -1
  120. package/dist-server/server/routines.js +5 -1
  121. package/dist-server/server/setup-mode.js +0 -2
  122. package/dist-server/server/skill-learn.js +0 -1
  123. package/dist-server/server/skill-library.js +0 -15
  124. package/dist-server/server/store.js +9 -1
  125. package/dist-server/server/surface.js +65 -20
  126. package/dist-server/server/system-prompt.js +4 -4
  127. package/dist-server/server/team-memory.js +209 -0
  128. package/dist-server/server/thread-events.js +2 -2
  129. package/dist-server/server/vps-computer.js +4 -14
  130. package/dist-server/server/workspace.js +85 -47
  131. package/dist-server/shared/activity.js +3 -0
  132. package/dist-server/shared/bot-avatar.js +8 -0
  133. package/dist-server/shared/connector-scopes.js +78 -0
  134. package/dist-server/shared/outbound.js +128 -0
  135. package/dist-server/shared/tool-surface.js +3 -2
  136. package/dist-server/vps-container-mcp.js +2 -2
  137. package/enterprise/server/index.js +2 -1
  138. package/package.json +1 -1
  139. package/dist/assets/channel-CdJX6i8k.js +0 -1
  140. package/dist/assets/index-CPYrGsv1.js +0 -610
  141. package/dist/assets/index-CzT42GR8.css +0 -1
  142. package/dist/assets/swimlanesDiagram-TC7HE7FX-D-U4GtLQ.js +0 -8
  143. package/dist-server/server/drivers/chat-boat-tools.js +0 -90
  144. package/dist-server/server/drivers/grokagent.js +0 -4
  145. package/dist-server/server/openmaus-status-capsule.js +0 -329
@@ -1,329 +0,0 @@
1
- import { createHash } from "node:crypto";
2
- import { closeSync, constants, fstatSync, lstatSync, openSync, readFileSync, } from "node:fs";
3
- import { homedir } from "node:os";
4
- import { dirname, join } from "node:path";
5
- import { z } from "zod";
6
- import { parseJson } from "./schema.js";
7
- const SCHEMA = "aos.openmausbot_status.v1";
8
- const TTL_SECONDS = 300;
9
- const MAX_CACHE_BYTES = 16_384;
10
- const DIGEST = /^sha256:[a-f0-9]{64}$/;
11
- const UTC_TIMESTAMP = /^\d{4}-\d{2}-\d{2}T\d{2}:\d{2}:\d{2}Z$/;
12
- const digestSchema = z.string().regex(DIGEST);
13
- const slotSchema = z.object({
14
- slot: z.string().regex(/^vm-[1-4]$/),
15
- container: z.enum(["running", "stopped", "missing"]),
16
- readiness: z.enum(["ready", "not_ready"]),
17
- network: z.enum(["loopback", "unsafe", "unknown"]),
18
- security: z.enum(["hardened", "unsafe", "unknown"]),
19
- persistence: z.enum(["durable", "unsafe", "unknown"]),
20
- }).strict();
21
- const uiSchema = z.object({
22
- two_up: z.boolean(),
23
- max_visible: z.union([z.literal(1), z.literal(2)]),
24
- max_interactive: z.literal(1),
25
- default_watch_only: z.boolean(),
26
- }).strict();
27
- const capsuleSchema = z.object({
28
- schema: z.literal(SCHEMA),
29
- observed_at: z.string().regex(UTC_TIMESTAMP),
30
- fresh_until: z.string().regex(UTC_TIMESTAMP),
31
- ttl_seconds: z.literal(TTL_SECONDS),
32
- source_sha256: digestSchema.nullable(),
33
- dual_view_sha256: digestSchema.nullable(),
34
- receipt_sha256: digestSchema,
35
- refresh_status: z.enum(["success", "failed"]),
36
- failure_reason: z.enum([
37
- "config_unavailable",
38
- "bots_unavailable",
39
- "vm_status_unavailable",
40
- "capacity_exceeded",
41
- "source_hash_unavailable",
42
- "source_hash_mismatch",
43
- ]).optional(),
44
- runtime_state: z.enum(["ready", "degraded", "unknown"]),
45
- mode: z.enum(["shared", "per-bot", "unknown"]),
46
- max_instances: z.number().int().min(1).max(4).nullable(),
47
- ready_count: z.number().int().min(0).max(4),
48
- slots: z.array(slotSchema).max(4),
49
- ui: uiSchema,
50
- }).strict();
51
- const jsonObjectSchema = z.record(z.string(), z.custom());
52
- export const OPENMAUS_STATUS_CACHE_PATH = join(homedir(), ".local/state/aos-session-bridge/openmausbot/latest.json");
53
- function canonicalValue(value) {
54
- if (Array.isArray(value))
55
- return value.map(canonicalValue);
56
- const parsedObject = jsonObjectSchema.safeParse(value);
57
- if (!parsedObject.success)
58
- return value;
59
- const sorted = {};
60
- for (const key of Object.keys(parsedObject.data).sort()) {
61
- const child = parsedObject.data[key];
62
- if (child !== undefined)
63
- sorted[key] = canonicalValue(child);
64
- }
65
- return sorted;
66
- }
67
- function canonical(value) {
68
- return JSON.stringify(canonicalValue(value));
69
- }
70
- function sha256(value) {
71
- return `sha256:${createHash("sha256").update(value, "utf8").digest("hex")}`;
72
- }
73
- function timestamp(value) {
74
- const parsed = Date.parse(value);
75
- if (!Number.isFinite(parsed))
76
- return null;
77
- if (new Date(parsed).toISOString().replace(".000Z", "Z") !== value)
78
- return null;
79
- return parsed;
80
- }
81
- function expectedUi(twoUp) {
82
- return {
83
- two_up: twoUp,
84
- max_visible: twoUp ? 2 : 1,
85
- max_interactive: 1,
86
- default_watch_only: twoUp,
87
- };
88
- }
89
- function sameUi(left, right) {
90
- return (left.two_up === right.two_up &&
91
- left.max_visible === right.max_visible &&
92
- left.max_interactive === right.max_interactive &&
93
- left.default_watch_only === right.default_watch_only);
94
- }
95
- function unsignedDocument(capsule) {
96
- const document = {
97
- schema: capsule.schema,
98
- observed_at: capsule.observed_at,
99
- fresh_until: capsule.fresh_until,
100
- ttl_seconds: capsule.ttl_seconds,
101
- source_sha256: capsule.source_sha256,
102
- dual_view_sha256: capsule.dual_view_sha256,
103
- refresh_status: capsule.refresh_status,
104
- runtime_state: capsule.runtime_state,
105
- mode: capsule.mode,
106
- max_instances: capsule.max_instances,
107
- ready_count: capsule.ready_count,
108
- slots: capsule.slots.map((slot) => ({
109
- slot: slot.slot,
110
- container: slot.container,
111
- readiness: slot.readiness,
112
- network: slot.network,
113
- security: slot.security,
114
- persistence: slot.persistence,
115
- })),
116
- ui: {
117
- two_up: capsule.ui.two_up,
118
- max_visible: capsule.ui.max_visible,
119
- max_interactive: capsule.ui.max_interactive,
120
- default_watch_only: capsule.ui.default_watch_only,
121
- },
122
- };
123
- if (capsule.failure_reason !== undefined)
124
- document.failure_reason = capsule.failure_reason;
125
- return document;
126
- }
127
- function validSlotState(slot) {
128
- return (slot.readiness !== "ready" ||
129
- (slot.container === "running" &&
130
- slot.network === "loopback" &&
131
- slot.security === "hardened" &&
132
- slot.persistence === "durable"));
133
- }
134
- function validateCapsule(value) {
135
- const parsed = capsuleSchema.safeParse(value);
136
- if (!parsed.success)
137
- return null;
138
- const capsule = parsed.data;
139
- const observed = timestamp(capsule.observed_at);
140
- const freshUntil = timestamp(capsule.fresh_until);
141
- if (observed === null || freshUntil === null || freshUntil - observed !== TTL_SECONDS * 1000)
142
- return null;
143
- if (capsule.receipt_sha256 !== sha256(canonical(unsignedDocument(capsule))))
144
- return null;
145
- if (!capsule.slots.every((slot, index) => slot.slot === `vm-${index + 1}` && validSlotState(slot))) {
146
- return null;
147
- }
148
- const readyCount = capsule.slots.filter((slot) => slot.readiness === "ready").length;
149
- if (capsule.ready_count !== readyCount)
150
- return null;
151
- const twoUp = Boolean(capsule.refresh_status === "success" &&
152
- capsule.mode === "per-bot" &&
153
- capsule.max_instances !== null &&
154
- capsule.max_instances >= 2 &&
155
- capsule.source_sha256 !== null &&
156
- capsule.dual_view_sha256 !== null &&
157
- capsule.source_sha256 === capsule.dual_view_sha256);
158
- if (!sameUi(capsule.ui, expectedUi(twoUp)))
159
- return null;
160
- if (capsule.refresh_status === "failed") {
161
- if (capsule.failure_reason === undefined ||
162
- capsule.runtime_state !== "unknown" ||
163
- capsule.mode !== "unknown" ||
164
- capsule.max_instances !== null ||
165
- capsule.ready_count !== 0 ||
166
- capsule.slots.length !== 0 ||
167
- !sameUi(capsule.ui, expectedUi(false)))
168
- return null;
169
- }
170
- else {
171
- const expectedRuntime = capsule.slots.length > 0 && readyCount === capsule.slots.length ? "ready" : "degraded";
172
- if (capsule.failure_reason !== undefined ||
173
- capsule.runtime_state !== expectedRuntime ||
174
- (capsule.mode !== "shared" && capsule.mode !== "per-bot") ||
175
- capsule.max_instances === null ||
176
- readyCount > capsule.max_instances ||
177
- capsule.source_sha256 === null ||
178
- capsule.dual_view_sha256 === null ||
179
- capsule.source_sha256 !== capsule.dual_view_sha256)
180
- return null;
181
- }
182
- return capsule;
183
- }
184
- function privateCache(path) {
185
- const uid = process.getuid?.();
186
- if (uid === undefined)
187
- return null;
188
- let descriptor = null;
189
- try {
190
- const parentStatus = lstatSync(dirname(path));
191
- const fileStatus = lstatSync(path);
192
- if (parentStatus.isSymbolicLink() ||
193
- !parentStatus.isDirectory() ||
194
- parentStatus.uid !== uid ||
195
- (parentStatus.mode & 0o777) !== 0o700)
196
- return null;
197
- if (fileStatus.isSymbolicLink() ||
198
- !fileStatus.isFile() ||
199
- fileStatus.uid !== uid ||
200
- (fileStatus.mode & 0o777) !== 0o600 ||
201
- fileStatus.size > MAX_CACHE_BYTES)
202
- return null;
203
- descriptor = openSync(path, constants.O_RDONLY | (constants.O_NOFOLLOW ?? 0));
204
- const openedStatus = fstatSync(descriptor);
205
- if (!openedStatus.isFile() ||
206
- openedStatus.uid !== uid ||
207
- (openedStatus.mode & 0o777) !== 0o600 ||
208
- openedStatus.dev !== fileStatus.dev ||
209
- openedStatus.ino !== fileStatus.ino ||
210
- openedStatus.size > MAX_CACHE_BYTES)
211
- return null;
212
- const contents = readFileSync(descriptor);
213
- return contents.length <= MAX_CACHE_BYTES ? contents : null;
214
- }
215
- catch {
216
- return null;
217
- }
218
- finally {
219
- if (descriptor !== null) {
220
- try {
221
- closeSync(descriptor);
222
- }
223
- catch {
224
- // Cleanup failures must not escape the fail-closed cache read.
225
- }
226
- }
227
- }
228
- }
229
- function unknownDigest(reason, freshness = "unknown", receipt) {
230
- return {
231
- schema: SCHEMA,
232
- freshness,
233
- reason,
234
- ...receipt,
235
- runtimeState: "unknown",
236
- mode: "unknown",
237
- maxInstances: null,
238
- readyCount: 0,
239
- slots: [],
240
- ui: {
241
- twoUp: false,
242
- maxVisible: 1,
243
- maxInteractive: 1,
244
- defaultWatchOnly: false,
245
- oneActiveController: true,
246
- },
247
- };
248
- }
249
- export function readOpenMausStatus(options = {}) {
250
- const raw = privateCache(options.cachePath ?? OPENMAUS_STATUS_CACHE_PATH);
251
- if (raw === null)
252
- return unknownDigest("missing_or_insecure");
253
- let capsule;
254
- try {
255
- capsule = validateCapsule(parseJson(raw.toString("utf8")));
256
- }
257
- catch {
258
- capsule = null;
259
- }
260
- if (capsule === null)
261
- return unknownDigest("invalid");
262
- const observed = timestamp(capsule.observed_at);
263
- const freshUntil = timestamp(capsule.fresh_until);
264
- const now = (options.now ?? new Date()).getTime();
265
- const receipt = { observedAt: capsule.observed_at, receiptSha256: capsule.receipt_sha256 };
266
- if (!Number.isFinite(now) || now < observed)
267
- return unknownDigest("clock_skew");
268
- if (now >= freshUntil)
269
- return unknownDigest("stale", "stale", receipt);
270
- if (capsule.refresh_status === "failed")
271
- return unknownDigest("refresh_failed", "fresh", receipt);
272
- const result = {
273
- schema: SCHEMA,
274
- freshness: "fresh",
275
- ...receipt,
276
- runtimeState: capsule.runtime_state,
277
- mode: capsule.mode,
278
- maxInstances: capsule.max_instances,
279
- readyCount: capsule.ready_count,
280
- slots: capsule.slots,
281
- ui: {
282
- twoUp: capsule.ui.two_up,
283
- maxVisible: capsule.ui.max_visible,
284
- maxInteractive: 1,
285
- defaultWatchOnly: capsule.ui.default_watch_only,
286
- oneActiveController: true,
287
- },
288
- };
289
- if (capsule.source_sha256 !== null)
290
- result.sourceSha256 = capsule.source_sha256;
291
- if (capsule.dual_view_sha256 !== null)
292
- result.dualViewSha256 = capsule.dual_view_sha256;
293
- return result;
294
- }
295
- export function openMausStatusSystemPrompt(options = {}) {
296
- const status = readOpenMausStatus(options);
297
- const receipt = [
298
- status.observedAt ? `observed_at=${status.observedAt}` : null,
299
- status.receiptSha256 ? `receipt_sha256=${status.receiptSha256}` : null,
300
- status.sourceSha256 ? `source_sha256=${status.sourceSha256}` : null,
301
- status.dualViewSha256 ? `accepted_dual_view_sha256=${status.dualViewSha256}` : null,
302
- status.sourceSha256 && status.dualViewSha256
303
- ? `source_match=${status.sourceSha256 === status.dualViewSha256}`
304
- : null,
305
- ].filter(Boolean).join("; ");
306
- const runtime = status.freshness === "fresh" && status.reason === undefined
307
- ? [
308
- `runtime_state=${status.runtimeState}`,
309
- `mode=${status.mode}`,
310
- `maximum_instances=${status.maxInstances}`,
311
- `ready_count=${status.readyCount}`,
312
- ].join("; ")
313
- : "runtime_state=unknown; mode=unknown; maximum_instances=unknown; ready_count=0";
314
- const slots = status.slots.length
315
- ? status.slots
316
- .map((slot) => `${slot.slot}(container=${slot.container},readiness=${slot.readiness},network=${slot.network},security=${slot.security},persistence=${slot.persistence})`)
317
- .join(",")
318
- : "none";
319
- return [
320
- "TRUSTED OPENMAUSBOT STATUS (read-only, validated, no transcript or credential data):",
321
- `schema=${status.schema}; freshness=${status.freshness}${status.reason ? `; reason=${status.reason}` : ""}`,
322
- receipt || "receipt=unavailable",
323
- runtime,
324
- `anonymous_slots=${slots}`,
325
- `ui.two_up=${status.ui.twoUp}; ui.max_visible=${status.ui.maxVisible}; ui.max_interactive=1; ui.default_watch_only=${status.ui.defaultWatchOnly}; one_active_controller=true`,
326
- "Opening a viewer or two-up workspace never starts or provisions a VM. Only one pane may be interactive at a time; switching control must release the previous pane before activating the next.",
327
- "Treat missing, stale, failed, clock-skewed, malformed, or receipt-hash-mismatched runtime data as unknown. Do not infer bot identities, viewer URLs, paths, messages, models, accounts, or credentials from this block.",
328
- ].join("\n");
329
- }