humanish 0.106.1 → 0.108.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 (668) hide show
  1. package/ARCHITECTURE.md +38 -32
  2. package/CHANGELOG.md +28 -0
  3. package/CONTEXT.md +51 -41
  4. package/README.md +152 -174
  5. package/SECURITY.md +16 -26
  6. package/TELEMETRY.md +8 -6
  7. package/dist/actors/affordance.d.ts +4 -4
  8. package/dist/actors/affordance.js +12 -12
  9. package/dist/actors/agent-session.d.ts +2 -2
  10. package/dist/actors/agent-session.js +7 -7
  11. package/dist/actors/codex/app-server-actor-trace.d.ts +1 -1
  12. package/dist/actors/codex/app-server-actor-trace.js +1 -1
  13. package/dist/actors/codex/app-server-client.js +2 -1
  14. package/dist/actors/codex/app-server-trace.d.ts +0 -1
  15. package/dist/actors/codex/app-server-trace.js +1 -3
  16. package/dist/actors/codex/app-server-ui.js +1 -1
  17. package/dist/actors/codex/app-server.js +2 -1
  18. package/dist/actors/codex/codex-admission.d.ts +91 -0
  19. package/dist/actors/codex/codex-admission.js +150 -0
  20. package/dist/actors/codex/protocol-compat.d.ts +27 -0
  21. package/dist/actors/codex/protocol-compat.js +357 -0
  22. package/dist/actors/codex/protocol-contract.d.ts +61 -0
  23. package/dist/actors/codex/protocol-contract.js +471 -0
  24. package/dist/actors/codex/restricted-executable.d.ts +28 -4
  25. package/dist/actors/codex/restricted-executable.js +104 -29
  26. package/dist/actors/codex/restricted-launch.d.ts +9 -2
  27. package/dist/actors/codex/restricted-launch.js +43 -4
  28. package/dist/actors/codex/restricted-notifications.d.ts +101 -0
  29. package/dist/actors/codex/restricted-notifications.js +277 -0
  30. package/dist/actors/codex/restricted-participant.d.ts +30 -0
  31. package/dist/actors/codex/restricted-participant.js +66 -6
  32. package/dist/actors/codex/restricted-policy.d.ts +11 -3
  33. package/dist/actors/codex/restricted-policy.js +2 -2
  34. package/dist/actors/codex/restricted-session.d.ts +16 -3
  35. package/dist/actors/codex/restricted-session.js +60 -22
  36. package/dist/actors/codex/restricted-transport.d.ts +29 -0
  37. package/dist/actors/codex/restricted-transport.js +139 -27
  38. package/dist/actors/codex/restricted-turn.d.ts +19 -4
  39. package/dist/actors/codex/restricted-turn.js +43 -30
  40. package/dist/actors/computer-use/actor.d.ts +17 -17
  41. package/dist/actors/computer-use/actor.js +6 -6
  42. package/dist/actors/computer-use/admission-limit.d.ts +1 -1
  43. package/dist/actors/computer-use/admission-limit.js +1 -1
  44. package/dist/actors/computer-use/loop/actions.d.ts +3 -3
  45. package/dist/actors/computer-use/loop/actions.js +10 -10
  46. package/dist/actors/computer-use/loop/backstop.d.ts +3 -3
  47. package/dist/actors/computer-use/loop/backstop.js +15 -13
  48. package/dist/actors/computer-use/loop/ending.d.ts +7 -7
  49. package/dist/actors/computer-use/loop/ending.js +9 -9
  50. package/dist/actors/computer-use/loop/observation.d.ts +2 -2
  51. package/dist/actors/computer-use/loop/observation.js +9 -9
  52. package/dist/actors/computer-use/loop/provider-call.d.ts +1 -1
  53. package/dist/actors/computer-use/loop/provider-call.js +1 -1
  54. package/dist/actors/computer-use/loop/session.js +3 -3
  55. package/dist/actors/computer-use/loop/spend.d.ts +2 -2
  56. package/dist/actors/computer-use/loop/spend.js +4 -4
  57. package/dist/actors/computer-use/loop/trace.js +11 -10
  58. package/dist/actors/computer-use/loop/types.d.ts +37 -26
  59. package/dist/actors/computer-use/loop/usage.js +2 -2
  60. package/dist/actors/computer-use/loop.js +4 -4
  61. package/dist/actors/computer-use/openai-context.d.ts +37 -0
  62. package/dist/actors/computer-use/openai-context.js +214 -0
  63. package/dist/actors/computer-use/openai-provider.d.ts +12 -9
  64. package/dist/actors/computer-use/openai-provider.js +47 -36
  65. package/dist/actors/computer-use/openai-requests.d.ts +36 -10
  66. package/dist/actors/computer-use/openai-requests.js +82 -15
  67. package/dist/actors/computer-use/openai-wire.d.ts +19 -7
  68. package/dist/actors/computer-use/openai-wire.js +36 -34
  69. package/dist/actors/contract.d.ts +86 -49
  70. package/dist/actors/contract.js +29 -23
  71. package/dist/actors/local-agent/claude-session.d.ts +1 -1
  72. package/dist/actors/local-agent/claude-session.js +10 -9
  73. package/dist/actors/local-agent/cli.d.ts +8 -6
  74. package/dist/actors/local-agent/cli.js +24 -28
  75. package/dist/actors/local-agent/readiness.d.ts +2 -2
  76. package/dist/actors/local-agent/readiness.js +4 -4
  77. package/dist/actors/reasoning-effort.js +6 -6
  78. package/dist/actors/registry.d.ts +10 -10
  79. package/dist/actors/registry.js +18 -17
  80. package/dist/actors/scripted-browser/actor.d.ts +8 -8
  81. package/dist/actors/scripted-browser/actor.js +16 -16
  82. package/dist/actors/scripted-browser/browser-command.js +1 -1
  83. package/dist/actors/scripted-browser/journey.js +15 -4
  84. package/dist/actors/scripted-browser/steps.js +19 -1
  85. package/dist/actors/scripted-browser/types.d.ts +12 -2
  86. package/dist/actors/stop-conditions.d.ts +1 -1
  87. package/dist/actors/stop-conditions.js +1 -3
  88. package/dist/analysis/automatic-completion.d.ts +13 -8
  89. package/dist/analysis/automatic-completion.js +14 -8
  90. package/dist/analysis/automatic-config.d.ts +1 -1
  91. package/dist/analysis/automatic-config.js +2 -2
  92. package/dist/analysis/automatic.d.ts +10 -4
  93. package/dist/analysis/automatic.js +17 -13
  94. package/dist/analysis/codex-config.d.ts +6 -2
  95. package/dist/analysis/codex-config.js +22 -14
  96. package/dist/analysis/diagnostics.d.ts +23 -0
  97. package/dist/analysis/diagnostics.js +112 -0
  98. package/dist/analysis/evidence-sources.js +2 -2
  99. package/dist/analysis/evidence.js +6 -6
  100. package/dist/analysis/execute.d.ts +7 -1
  101. package/dist/analysis/execute.js +39 -12
  102. package/dist/analysis/job.d.ts +8 -5
  103. package/dist/analysis/job.js +15 -14
  104. package/dist/analysis/load.d.ts +1 -1
  105. package/dist/analysis/load.js +5 -5
  106. package/dist/analysis/provider.d.ts +9 -1
  107. package/dist/analysis/restricted-codex.d.ts +2 -0
  108. package/dist/analysis/restricted-codex.js +10 -1
  109. package/dist/analysis/service.d.ts +2 -0
  110. package/dist/analysis/service.js +35 -16
  111. package/dist/analysis/sharing.d.ts +2 -2
  112. package/dist/analysis/sharing.js +5 -5
  113. package/dist/analysis/store-executions.d.ts +5 -5
  114. package/dist/analysis/store-executions.js +12 -12
  115. package/dist/analysis/store.d.ts +4 -4
  116. package/dist/analysis/store.js +13 -13
  117. package/dist/cli/commands/analysis-signals.d.ts +2 -1
  118. package/dist/cli/commands/analysis-signals.js +4 -1
  119. package/dist/cli/commands/analyze.js +23 -18
  120. package/dist/cli/commands/codex.js +9 -9
  121. package/dist/cli/commands/comms.js +62 -34
  122. package/dist/cli/commands/feedback.js +20 -21
  123. package/dist/cli/commands/lab-format.d.ts +5 -4
  124. package/dist/cli/commands/lab-format.js +35 -23
  125. package/dist/cli/commands/lab-route-computer-use.d.ts +0 -2
  126. package/dist/cli/commands/lab-route-computer-use.js +32 -21
  127. package/dist/cli/commands/lab-route-preview.d.ts +1 -3
  128. package/dist/cli/commands/lab-route-preview.js +7 -7
  129. package/dist/cli/commands/lab-route-run.d.ts +6 -4
  130. package/dist/cli/commands/lab-route-run.js +6 -2
  131. package/dist/cli/commands/lab-route-scripted.d.ts +0 -2
  132. package/dist/cli/commands/lab-route-scripted.js +0 -1
  133. package/dist/cli/commands/lab-route-shared-world.d.ts +0 -2
  134. package/dist/cli/commands/lab-route-shared-world.js +3 -4
  135. package/dist/cli/commands/lab-route-terminal.d.ts +0 -2
  136. package/dist/cli/commands/lab-route-terminal.js +0 -1
  137. package/dist/cli/commands/lab-run.js +84 -54
  138. package/dist/cli/commands/lab-scorer.d.ts +2 -4
  139. package/dist/cli/commands/lab-scorer.js +1 -1
  140. package/dist/cli/commands/migrate.d.ts +4 -0
  141. package/dist/cli/commands/migrate.js +65 -0
  142. package/dist/cli/commands/observe.js +168 -107
  143. package/dist/cli/commands/run-command.d.ts +10 -0
  144. package/dist/cli/commands/run-command.js +85 -0
  145. package/dist/cli/commands/run-signals.d.ts +30 -0
  146. package/dist/cli/commands/run-signals.js +146 -0
  147. package/dist/cli/commands/runs.js +137 -136
  148. package/dist/cli/commands/setup.d.ts +2 -2
  149. package/dist/cli/commands/setup.js +26 -21
  150. package/dist/cli/commands/study.d.ts +3 -0
  151. package/dist/cli/commands/study.js +182 -0
  152. package/dist/cli/commands/tui.d.ts +4 -4
  153. package/dist/cli/commands/tui.js +21 -21
  154. package/dist/cli/commands/watch.js +64 -77
  155. package/dist/cli/deprecations.d.ts +18 -0
  156. package/dist/cli/deprecations.js +48 -0
  157. package/dist/cli/doctor.d.ts +18 -5
  158. package/dist/cli/doctor.js +111 -48
  159. package/dist/cli/first-run-path.d.ts +12 -10
  160. package/dist/cli/first-run-path.js +30 -28
  161. package/dist/cli/io.d.ts +46 -10
  162. package/dist/cli/io.js +109 -30
  163. package/dist/cli/observer-follow.d.ts +2 -2
  164. package/dist/cli/observer-follow.js +5 -6
  165. package/dist/cli/orientation.d.ts +6 -3
  166. package/dist/cli/orientation.js +43 -39
  167. package/dist/cli/product-sentence.d.ts +6 -0
  168. package/dist/cli/product-sentence.js +6 -0
  169. package/dist/cli/program.d.ts +6 -1
  170. package/dist/cli/program.js +112 -43
  171. package/dist/cli/telemetry.d.ts +17 -17
  172. package/dist/cli/telemetry.js +49 -41
  173. package/dist/cli.js +1 -1
  174. package/dist/comms/capture-surface.d.ts +14 -13
  175. package/dist/comms/capture-surface.js +23 -22
  176. package/dist/comms/catch-host.d.ts +8 -8
  177. package/dist/comms/catch-host.js +14 -14
  178. package/dist/comms/connections.js +4 -4
  179. package/dist/comms/email-catch.d.ts +3 -3
  180. package/dist/comms/email-catch.js +8 -8
  181. package/dist/comms/external-evidence.d.ts +27 -0
  182. package/dist/comms/external-evidence.js +93 -0
  183. package/dist/comms/extract.js +2 -2
  184. package/dist/comms/fake-inbox.d.ts +2 -2
  185. package/dist/comms/fake-inbox.js +2 -2
  186. package/dist/comms/lease-store.js +7 -7
  187. package/dist/comms/receiving-render.d.ts +1 -1
  188. package/dist/comms/receiving-render.js +2 -2
  189. package/dist/comms/sandbox-catch-script.d.ts +6 -6
  190. package/dist/comms/sandbox-catch-script.js +6 -6
  191. package/dist/comms/sandbox-catch.d.ts +36 -37
  192. package/dist/comms/sandbox-catch.js +34 -35
  193. package/dist/comms/setup.js +42 -8
  194. package/dist/comms/thread-evidence.d.ts +1 -1
  195. package/dist/comms/thread-evidence.js +6 -6
  196. package/dist/comms/types.d.ts +6 -6
  197. package/dist/comms/types.js +4 -4
  198. package/dist/evidence/browser-hygiene.d.ts +1 -1
  199. package/dist/evidence/browser-hygiene.js +1 -1
  200. package/dist/evidence/frame-signature.d.ts +1 -1
  201. package/dist/evidence/frame-signature.js +4 -4
  202. package/dist/evidence/redaction.d.ts +3 -3
  203. package/dist/evidence/redaction.js +5 -5
  204. package/dist/evidence/secret-scrub.d.ts +9 -0
  205. package/dist/evidence/secret-scrub.js +96 -0
  206. package/dist/feedback/draft.js +41 -85
  207. package/dist/feedback/export-bundle.js +5 -5
  208. package/dist/feedback/export.d.ts +5 -1
  209. package/dist/feedback/export.js +16 -17
  210. package/dist/feedback/feedback.d.ts +3 -3
  211. package/dist/feedback/feedback.js +21 -3
  212. package/dist/guest/chromium-text.js +2 -2
  213. package/dist/guest/desktop-native.d.ts +1 -1
  214. package/dist/guest/runtime.js +1 -1
  215. package/dist/index.d.ts +14 -15
  216. package/dist/index.js +10 -11
  217. package/dist/keys/key-resolution.d.ts +7 -5
  218. package/dist/keys/key-resolution.js +40 -38
  219. package/dist/lab/adapter-extension.d.ts +35 -13
  220. package/dist/lab/adapter-extension.js +50 -134
  221. package/dist/lab/adapter-scorer-loader.d.ts +32 -12
  222. package/dist/lab/adapter-scorer-loader.js +56 -32
  223. package/dist/lab/composition-rules.js +58 -58
  224. package/dist/lab/config.js +85 -43
  225. package/dist/lab/deprecated-fields.d.ts +10 -0
  226. package/dist/lab/deprecated-fields.js +24 -0
  227. package/dist/lab/device-presets.d.ts +10 -10
  228. package/dist/lab/device-presets.js +11 -11
  229. package/dist/lab/discover.d.ts +13 -9
  230. package/dist/lab/discover.js +118 -60
  231. package/dist/lab/doctor.d.ts +53 -11
  232. package/dist/lab/doctor.js +193 -47
  233. package/dist/lab/init-plan.js +1 -3
  234. package/dist/lab/init-templates.js +147 -147
  235. package/dist/lab/init.d.ts +1 -1
  236. package/dist/lab/init.js +41 -9
  237. package/dist/lab/keys.d.ts +2 -0
  238. package/dist/lab/keys.js +43 -9
  239. package/dist/lab/lab-deps.d.ts +80 -0
  240. package/dist/lab/lab-deps.js +4 -0
  241. package/dist/lab/parse/actors.js +17 -16
  242. package/dist/lab/parse/comms.js +8 -7
  243. package/dist/lab/parse/execution.js +15 -14
  244. package/dist/lab/parse/study-v3.d.ts +23 -0
  245. package/dist/lab/parse/study-v3.js +259 -0
  246. package/dist/lab/parse/subject-state.d.ts +7 -7
  247. package/dist/lab/parse/subject-state.js +18 -17
  248. package/dist/lab/parse/subject.js +30 -29
  249. package/dist/lab/parse/values.d.ts +1 -2
  250. package/dist/lab/parse/values.js +3 -6
  251. package/dist/lab/persona-resolve.d.ts +7 -7
  252. package/dist/lab/persona-resolve.js +8 -8
  253. package/dist/lab/persona.js +1 -3
  254. package/dist/lab/plan-base.d.ts +0 -2
  255. package/dist/lab/plan-base.js +6 -4
  256. package/dist/lab/plan-participants.d.ts +7 -7
  257. package/dist/lab/plan-participants.js +2 -2
  258. package/dist/lab/plan-types.d.ts +26 -8
  259. package/dist/lab/plan.d.ts +4 -18
  260. package/dist/lab/plan.js +24 -79
  261. package/dist/lab/preflight-probes.js +11 -11
  262. package/dist/lab/preflight-result.d.ts +2 -1
  263. package/dist/lab/preflight-result.js +5 -6
  264. package/dist/lab/preflight.d.ts +7 -8
  265. package/dist/lab/preflight.js +6 -6
  266. package/dist/lab/requirements.d.ts +20 -0
  267. package/dist/lab/requirements.js +54 -0
  268. package/dist/lab/route-inputs.d.ts +23 -12
  269. package/dist/lab/route-inputs.js +48 -51
  270. package/dist/lab/routing.d.ts +42 -41
  271. package/dist/lab/routing.js +66 -68
  272. package/dist/lab/run-lab-events.d.ts +3 -11
  273. package/dist/lab/run-lab-events.js +2 -16
  274. package/dist/lab/run-lab-homes.d.ts +76 -0
  275. package/dist/lab/run-lab-homes.js +7 -0
  276. package/dist/lab/run-lab-options.d.ts +12 -66
  277. package/dist/lab/run-lab-options.js +58 -285
  278. package/dist/lab/summary.d.ts +15 -9
  279. package/dist/lab/summary.js +24 -17
  280. package/dist/lab/tasks.d.ts +15 -15
  281. package/dist/lab/tasks.js +14 -14
  282. package/dist/lab/types.d.ts +201 -195
  283. package/dist/lab/types.js +2 -0
  284. package/dist/lab/validation.d.ts +21 -21
  285. package/dist/lab/validation.js +61 -59
  286. package/dist/lab/warnings.d.ts +10 -0
  287. package/dist/lab/warnings.js +70 -41
  288. package/dist/library-aliases.d.ts +56 -0
  289. package/dist/library-aliases.js +22 -0
  290. package/dist/observer/artifact.d.ts +2 -2
  291. package/dist/observer/artifact.js +9 -9
  292. package/dist/observer/data.d.ts +6 -6
  293. package/dist/observer/data.js +7 -6
  294. package/dist/observer/exposure.d.ts +1 -1
  295. package/dist/observer/exposure.js +11 -11
  296. package/dist/observer/http.js +1 -1
  297. package/dist/observer/library.d.ts +1 -1
  298. package/dist/observer/library.js +4 -2
  299. package/dist/observer/listen.js +5 -4
  300. package/dist/observer/render.d.ts +1 -1
  301. package/dist/observer/render.js +12 -7
  302. package/dist/observer/run-routes.d.ts +4 -4
  303. package/dist/observer/run-routes.js +6 -6
  304. package/dist/observer/serve.d.ts +17 -0
  305. package/dist/observer/serve.js +41 -6
  306. package/dist/observer/tunnel.js +1 -1
  307. package/dist/observer-app.html +4 -4
  308. package/dist/routes/computer-use/bundle-parts.d.ts +9 -9
  309. package/dist/routes/computer-use/bundle-parts.js +24 -17
  310. package/dist/routes/computer-use/bundle.d.ts +4 -11
  311. package/dist/routes/computer-use/bundle.js +12 -18
  312. package/dist/routes/computer-use/diagnostics.d.ts +1 -1
  313. package/dist/routes/computer-use/diagnostics.js +1 -1
  314. package/dist/routes/computer-use/e2b-desktop/comms.d.ts +11 -11
  315. package/dist/routes/computer-use/e2b-desktop/comms.js +24 -27
  316. package/dist/routes/computer-use/e2b-desktop/desktop.d.ts +2 -2
  317. package/dist/routes/computer-use/e2b-desktop/desktop.js +8 -11
  318. package/dist/routes/computer-use/e2b-desktop/fidelity.d.ts +16 -15
  319. package/dist/routes/computer-use/e2b-desktop/fidelity.js +20 -19
  320. package/dist/routes/computer-use/e2b-desktop/prepare.d.ts +3 -3
  321. package/dist/routes/computer-use/e2b-desktop/prepare.js +40 -43
  322. package/dist/routes/computer-use/e2b-desktop/start.d.ts +1 -1
  323. package/dist/routes/computer-use/e2b-desktop/start.js +32 -30
  324. package/dist/routes/computer-use/e2b-desktop/state.d.ts +5 -4
  325. package/dist/routes/computer-use/e2b-desktop/state.js +5 -3
  326. package/dist/routes/computer-use/e2b-desktop/teardown.d.ts +1 -1
  327. package/dist/routes/computer-use/e2b-desktop/teardown.js +33 -20
  328. package/dist/routes/computer-use/external-comms.d.ts +4 -4
  329. package/dist/routes/computer-use/external-comms.js +19 -43
  330. package/dist/routes/computer-use/fanout-bundle.d.ts +3 -3
  331. package/dist/routes/computer-use/fanout-bundle.js +38 -42
  332. package/dist/routes/computer-use/{fanout-lanes.js → fanout-records.js} +33 -28
  333. package/dist/routes/computer-use/in-process-desktop.d.ts +3 -10
  334. package/dist/routes/computer-use/in-process-desktop.js +3 -9
  335. package/dist/routes/computer-use/live-flush.d.ts +7 -5
  336. package/dist/routes/computer-use/live-flush.js +20 -28
  337. package/dist/routes/computer-use/{run-lanes.d.ts → live-phase.d.ts} +4 -2
  338. package/dist/routes/computer-use/{run-lanes.js → live-phase.js} +17 -16
  339. package/dist/routes/computer-use/local-tree-pack.d.ts +3 -3
  340. package/dist/routes/computer-use/local-tree-pack.js +4 -5
  341. package/dist/routes/computer-use/local-vm.d.ts +11 -8
  342. package/dist/routes/computer-use/local-vm.js +40 -67
  343. package/dist/routes/computer-use/participant-desktop.d.ts +8 -23
  344. package/dist/routes/computer-use/participant-desktop.js +5 -25
  345. package/dist/routes/computer-use/{lanes.d.ts → participant-execution.d.ts} +11 -11
  346. package/dist/routes/computer-use/{lanes.js → participant-execution.js} +39 -26
  347. package/dist/routes/computer-use/participant-facts.d.ts +7 -1
  348. package/dist/routes/computer-use/participant-facts.js +12 -1
  349. package/dist/routes/computer-use/participant-model.d.ts +25 -11
  350. package/dist/routes/computer-use/participant-model.js +76 -34
  351. package/dist/routes/computer-use/participant-prompt.d.ts +13 -13
  352. package/dist/routes/computer-use/participant-prompt.js +8 -8
  353. package/dist/routes/computer-use/participant-runs.d.ts +11 -11
  354. package/dist/routes/computer-use/participant-runs.js +18 -18
  355. package/dist/routes/computer-use/plan.d.ts +21 -29
  356. package/dist/routes/computer-use/plan.js +70 -78
  357. package/dist/routes/computer-use/preflight.d.ts +3 -5
  358. package/dist/routes/computer-use/preflight.js +40 -36
  359. package/dist/routes/computer-use/rerun-selection.js +11 -7
  360. package/dist/routes/computer-use/result.d.ts +1 -1
  361. package/dist/routes/computer-use/result.js +48 -38
  362. package/dist/routes/computer-use/route.d.ts +5 -5
  363. package/dist/routes/computer-use/route.js +36 -33
  364. package/dist/routes/computer-use/self-report.d.ts +8 -8
  365. package/dist/routes/computer-use/self-report.js +33 -33
  366. package/dist/routes/computer-use/setup.d.ts +9 -15
  367. package/dist/routes/computer-use/setup.js +106 -83
  368. package/dist/routes/computer-use/single-bundle.d.ts +13 -16
  369. package/dist/routes/computer-use/single-bundle.js +46 -53
  370. package/dist/routes/computer-use/subject-projection.d.ts +6 -8
  371. package/dist/routes/computer-use/subject-projection.js +24 -23
  372. package/dist/routes/computer-use/types.d.ts +195 -238
  373. package/dist/routes/computer-use/types.js +21 -13
  374. package/dist/routes/preview.d.ts +8 -2
  375. package/dist/routes/preview.js +8 -5
  376. package/dist/routes/scripted/bundle.d.ts +5 -8
  377. package/dist/routes/scripted/bundle.js +23 -27
  378. package/dist/routes/scripted/plan.d.ts +6 -8
  379. package/dist/routes/scripted/plan.js +15 -13
  380. package/dist/routes/scripted/result.d.ts +4 -1
  381. package/dist/routes/scripted/result.js +15 -11
  382. package/dist/routes/scripted/route.js +15 -17
  383. package/dist/routes/scripted/scenario.d.ts +1 -1
  384. package/dist/routes/scripted/scenario.js +3 -3
  385. package/dist/routes/scripted/setup.d.ts +3 -2
  386. package/dist/routes/scripted/setup.js +27 -26
  387. package/dist/routes/scripted/subject.d.ts +8 -3
  388. package/dist/routes/scripted/subject.js +10 -6
  389. package/dist/routes/scripted/surface-records.js +4 -4
  390. package/dist/routes/scripted/surface-sessions.d.ts +2 -2
  391. package/dist/routes/scripted/surface-sessions.js +4 -4
  392. package/dist/routes/scripted/types.d.ts +21 -40
  393. package/dist/routes/scripted/types.js +2 -3
  394. package/dist/routes/shared-world/{seat-records.js → bundle-records.js} +17 -16
  395. package/dist/routes/shared-world/bundle.d.ts +7 -7
  396. package/dist/routes/shared-world/bundle.js +60 -62
  397. package/dist/routes/shared-world/checkpoints.d.ts +5 -5
  398. package/dist/routes/shared-world/checkpoints.js +5 -5
  399. package/dist/routes/shared-world/comms.d.ts +8 -7
  400. package/dist/routes/shared-world/comms.js +38 -51
  401. package/dist/routes/shared-world/external-public.d.ts +6 -5
  402. package/dist/routes/shared-world/external-public.js +28 -25
  403. package/dist/routes/shared-world/handoff.d.ts +10 -9
  404. package/dist/routes/shared-world/handoff.js +89 -81
  405. package/dist/routes/shared-world/lobby-code.d.ts +7 -7
  406. package/dist/routes/shared-world/lobby-code.js +22 -22
  407. package/dist/routes/shared-world/{seats.d.ts → participant-specs.d.ts} +15 -12
  408. package/dist/routes/shared-world/{seats.js → participant-specs.js} +65 -63
  409. package/dist/routes/shared-world/plan.d.ts +2 -6
  410. package/dist/routes/shared-world/plan.js +8 -9
  411. package/dist/routes/shared-world/provenance.d.ts +4 -4
  412. package/dist/routes/shared-world/provenance.js +4 -4
  413. package/dist/routes/shared-world/provisioned.d.ts +3 -2
  414. package/dist/routes/shared-world/provisioned.js +55 -48
  415. package/dist/routes/shared-world/result.js +47 -36
  416. package/dist/routes/shared-world/route.js +54 -57
  417. package/dist/routes/shared-world/setup.d.ts +6 -5
  418. package/dist/routes/shared-world/setup.js +16 -18
  419. package/dist/routes/shared-world/types.d.ts +70 -141
  420. package/dist/routes/shared-world/types.js +5 -5
  421. package/dist/routes/terminal/adapter.d.ts +10 -10
  422. package/dist/routes/terminal/adapter.js +32 -129
  423. package/dist/routes/terminal/bundle.d.ts +10 -15
  424. package/dist/routes/terminal/bundle.js +43 -52
  425. package/dist/routes/terminal/credentials.d.ts +4 -4
  426. package/dist/routes/terminal/credentials.js +20 -20
  427. package/dist/routes/terminal/dry-run.d.ts +1 -1
  428. package/dist/routes/terminal/dry-run.js +13 -15
  429. package/dist/routes/terminal/encoding.d.ts +1 -1
  430. package/dist/routes/terminal/encoding.js +4 -4
  431. package/dist/routes/terminal/ledger.d.ts +8 -8
  432. package/dist/routes/terminal/ledger.js +22 -22
  433. package/dist/routes/terminal/live-finish.d.ts +1 -2
  434. package/dist/routes/terminal/live-finish.js +24 -23
  435. package/dist/routes/terminal/live-sandbox.d.ts +3 -2
  436. package/dist/routes/terminal/live-sandbox.js +31 -32
  437. package/dist/routes/terminal/participant-text.d.ts +23 -0
  438. package/dist/routes/terminal/participant-text.js +165 -0
  439. package/dist/routes/terminal/persona.js +1 -1
  440. package/dist/routes/terminal/plan.d.ts +2 -6
  441. package/dist/routes/terminal/plan.js +23 -19
  442. package/dist/routes/terminal/recorder.d.ts +6 -1
  443. package/dist/routes/terminal/recorder.js +12 -4
  444. package/dist/routes/terminal/result.js +12 -12
  445. package/dist/routes/terminal/route.js +30 -31
  446. package/dist/routes/terminal/runtime.d.ts +3 -2
  447. package/dist/routes/terminal/runtime.js +3 -3
  448. package/dist/routes/terminal/sandbox.d.ts +4 -4
  449. package/dist/routes/terminal/sandbox.js +10 -10
  450. package/dist/routes/terminal/session.js +22 -19
  451. package/dist/routes/terminal/token-usage.d.ts +1 -1
  452. package/dist/routes/terminal/token-usage.js +10 -11
  453. package/dist/routes/terminal/trace.d.ts +7 -10
  454. package/dist/routes/terminal/trace.js +11 -66
  455. package/dist/routes/terminal/types.d.ts +104 -114
  456. package/dist/routes/terminal/types.js +12 -7
  457. package/dist/run/active-runs.d.ts +13 -0
  458. package/dist/run/active-runs.js +12 -0
  459. package/dist/run/bundle-shape.d.ts +2 -1
  460. package/dist/run/bundle-shape.js +7 -7
  461. package/dist/run/bundle.d.ts +99 -92
  462. package/dist/run/bundle.js +10 -8
  463. package/dist/run/cost-summary.js +6 -5
  464. package/dist/run/costs.d.ts +6 -6
  465. package/dist/run/costs.js +17 -11
  466. package/dist/run/detail.d.ts +9 -9
  467. package/dist/run/detail.js +10 -10
  468. package/dist/run/dry-run-inputs.js +1 -1
  469. package/dist/run/dry-run.js +23 -30
  470. package/dist/run/{study-files.d.ts → evidence-files.d.ts} +4 -4
  471. package/dist/run/{study-files.js → evidence-files.js} +5 -5
  472. package/dist/run/feedback-shape.js +1 -1
  473. package/dist/run/judge.d.ts +34 -16
  474. package/dist/run/judge.js +41 -14
  475. package/dist/run/locate.d.ts +2 -0
  476. package/dist/run/locate.js +3 -1
  477. package/dist/run/outcomes.d.ts +3 -3
  478. package/dist/run/outcomes.js +3 -3
  479. package/dist/run/participant-records.d.ts +2 -2
  480. package/dist/run/participant-records.js +2 -2
  481. package/dist/run/paths.d.ts +1 -1
  482. package/dist/run/paths.js +2 -2
  483. package/dist/run/pricing.d.ts +30 -15
  484. package/dist/run/pricing.js +49 -30
  485. package/dist/run/projection.d.ts +27 -27
  486. package/dist/run/projection.js +23 -23
  487. package/dist/run/reclaim.d.ts +6 -0
  488. package/dist/run/reclaim.js +15 -5
  489. package/dist/run/results.d.ts +5 -5
  490. package/dist/run/run-index.d.ts +9 -7
  491. package/dist/run/run-index.js +24 -25
  492. package/dist/run/run-not-found.d.ts +5 -0
  493. package/dist/run/run-not-found.js +15 -0
  494. package/dist/run/run.d.ts +7 -4
  495. package/dist/run/run.js +10 -6
  496. package/dist/run/sandbox-receipts.d.ts +5 -5
  497. package/dist/run/sandbox-receipts.js +6 -6
  498. package/dist/run/shared-world-evidence.d.ts +67 -66
  499. package/dist/run/shared-world-evidence.js +4 -4
  500. package/dist/run/shared-world-shape.d.ts +3 -3
  501. package/dist/run/shared-world-shape.js +16 -16
  502. package/dist/run/stats.d.ts +17 -11
  503. package/dist/run/stats.js +124 -66
  504. package/dist/run/status.d.ts +21 -32
  505. package/dist/run/status.js +34 -33
  506. package/dist/run/stored-runs.js +2 -1
  507. package/dist/run/stream-shape.js +1 -1
  508. package/dist/run/streams.d.ts +29 -22
  509. package/dist/run/study-provenance.d.ts +47 -0
  510. package/dist/run/study-provenance.js +63 -0
  511. package/dist/run/study-result.d.ts +16 -0
  512. package/dist/run/study-result.js +9 -0
  513. package/dist/run/terminal-contract.d.ts +5 -5
  514. package/dist/run/terminal-contract.js +4 -4
  515. package/dist/run/text.d.ts +2 -0
  516. package/dist/run/text.js +4 -0
  517. package/dist/run/transient-comms-secrets.d.ts +5 -0
  518. package/dist/run/transient-comms-secrets.js +12 -0
  519. package/dist/run-lab.d.ts +40 -38
  520. package/dist/run-lab.js +42 -40
  521. package/dist/study/convert.d.ts +33 -0
  522. package/dist/study/convert.js +432 -0
  523. package/dist/study/field-paths.d.ts +12 -0
  524. package/dist/study/field-paths.js +126 -0
  525. package/dist/study/files.d.ts +26 -0
  526. package/dist/study/files.js +43 -0
  527. package/dist/study/migrate.d.ts +48 -0
  528. package/dist/study/migrate.js +408 -0
  529. package/dist/study/owned-files.d.ts +38 -0
  530. package/dist/study/owned-files.js +182 -0
  531. package/dist/subject/clone.d.ts +1 -1
  532. package/dist/subject/desktop-cli.d.ts +2 -2
  533. package/dist/subject/desktop-cli.js +3 -3
  534. package/dist/subject/local-tree-archive.d.ts +1 -1
  535. package/dist/subject/local-tree-archive.js +5 -5
  536. package/dist/subject/local-tree.d.ts +3 -3
  537. package/dist/subject/local-tree.js +1 -1
  538. package/dist/subject/node-bootstrap.d.ts +1 -1
  539. package/dist/subject/node-bootstrap.js +4 -4
  540. package/dist/subject/runtime.js +10 -11
  541. package/dist/subject/serve.d.ts +1 -1
  542. package/dist/subject/serve.js +4 -4
  543. package/dist/subject/state.d.ts +1 -1
  544. package/dist/subject/steps.d.ts +8 -8
  545. package/dist/subject/steps.js +7 -7
  546. package/dist/substrates/command-failure.d.ts +3 -3
  547. package/dist/substrates/command-failure.js +3 -3
  548. package/dist/substrates/detached.d.ts +6 -6
  549. package/dist/substrates/detached.js +7 -7
  550. package/dist/substrates/e2b/cdp-probe.d.ts +11 -11
  551. package/dist/substrates/e2b/cdp-probe.js +15 -18
  552. package/dist/substrates/e2b/desktop-browser.d.ts +5 -5
  553. package/dist/substrates/e2b/desktop-browser.js +12 -12
  554. package/dist/substrates/e2b/desktop-cdp.d.ts +15 -15
  555. package/dist/substrates/e2b/desktop-cdp.js +11 -11
  556. package/dist/substrates/e2b/desktop-executor.d.ts +1 -1
  557. package/dist/substrates/e2b/desktop-executor.js +1 -1
  558. package/dist/substrates/e2b/desktop-geometry.d.ts +6 -6
  559. package/dist/substrates/e2b/desktop-geometry.js +9 -9
  560. package/dist/substrates/e2b/desktop-media.d.ts +1 -1
  561. package/dist/substrates/e2b/desktop-media.js +3 -3
  562. package/dist/substrates/e2b/desktop-screenshot-cleanup.d.ts +3 -3
  563. package/dist/substrates/e2b/desktop-screenshot-cleanup.js +3 -3
  564. package/dist/substrates/e2b/sandbox.d.ts +1 -1
  565. package/dist/substrates/e2b/sandbox.js +2 -2
  566. package/dist/substrates/e2b/sdk.d.ts +11 -11
  567. package/dist/substrates/e2b/sdk.js +8 -8
  568. package/dist/substrates/local/runtime-host.d.ts +2 -0
  569. package/dist/substrates/local/runtime-host.js +6 -0
  570. package/dist/tui/actions.d.ts +8 -6
  571. package/dist/tui/actions.js +31 -22
  572. package/dist/tui/contract.d.ts +16 -16
  573. package/dist/tui/contract.js +10 -10
  574. package/dist/tui/launch.d.ts +4 -4
  575. package/dist/tui/launch.js +18 -19
  576. package/dist/tui/project.js +5 -5
  577. package/dist/tui-app.js +83 -83
  578. package/dist/verify/actor.d.ts +14 -14
  579. package/dist/verify/actor.js +45 -45
  580. package/dist/verify/artifacts.d.ts +3 -3
  581. package/dist/verify/artifacts.js +6 -6
  582. package/dist/verify/context-growth.d.ts +9 -0
  583. package/dist/verify/context-growth.js +62 -0
  584. package/dist/verify/costs.d.ts +7 -7
  585. package/dist/verify/costs.js +9 -9
  586. package/dist/verify/liveness.d.ts +1 -1
  587. package/dist/verify/liveness.js +4 -1
  588. package/dist/verify/rerun.d.ts +1 -1
  589. package/dist/verify/rerun.js +1 -1
  590. package/dist/verify/shared-world-concurrent.d.ts +2 -2
  591. package/dist/verify/shared-world-concurrent.js +79 -76
  592. package/dist/verify/shared-world.d.ts +2 -2
  593. package/dist/verify/shared-world.js +18 -18
  594. package/dist/verify/subject.d.ts +4 -4
  595. package/dist/verify/subject.js +18 -18
  596. package/dist/verify/verify.js +98 -49
  597. package/docs/README.md +26 -33
  598. package/docs/architecture/actor-contract.md +105 -98
  599. package/docs/architecture/desktop-sessions.md +14 -14
  600. package/docs/architecture/external-public-shared-world.md +66 -59
  601. package/docs/architecture/github-feedback-loop.md +1 -4
  602. package/docs/architecture/guest-desktop.md +2 -2
  603. package/docs/architecture/observer.md +37 -37
  604. package/docs/architecture/restricted-codex-analysis.md +70 -30
  605. package/docs/architecture/serve.md +34 -37
  606. package/docs/architecture/state-driven-executor.md +55 -59
  607. package/docs/architecture/task-protocol-support.md +7 -9
  608. package/docs/architecture/{terminal-product-lane.md → terminal-product-route.md} +83 -115
  609. package/docs/contracts/README.md +24 -0
  610. package/docs/contracts/adapter-admission.md +3 -3
  611. package/docs/contracts/adapter-fixtures.md +2 -5
  612. package/docs/contracts/core.md +1 -3
  613. package/docs/contracts/errors.md +62 -0
  614. package/docs/contracts/feedback.md +8 -9
  615. package/docs/contracts/policy.md +7 -12
  616. package/docs/contracts/run-bundle.md +54 -51
  617. package/docs/contracts/schemas.md +505 -390
  618. package/docs/contracts/study-analysis.md +26 -2
  619. package/docs/contracts/study-costs.md +11 -7
  620. package/docs/decisions/0001-run-bundle-is-the-source-of-truth.md +1 -1
  621. package/docs/decisions/0002-observer-is-one-self-contained-file.md +2 -2
  622. package/docs/decisions/0003-contained-paths-and-cleanup-authority.md +3 -3
  623. package/docs/decisions/0004-participant-desktops-stay-in-the-route.md +2 -1
  624. package/docs/principles/actor-fidelity.md +4 -4
  625. package/docs/principles/engineering.md +3 -3
  626. package/docs/principles/invariants-and-defaults.md +38 -38
  627. package/docs/principles/self-driving-harness.md +1 -5
  628. package/docs/principles/three-roles.md +1 -1
  629. package/docs/product/automatic-analysis.md +8 -7
  630. package/examples/participant/README.md +5 -5
  631. package/examples/participant/run.mjs +11 -10
  632. package/examples/scorer/README.md +3 -3
  633. package/examples/scorer/run.mjs +11 -12
  634. package/package.json +16 -17
  635. package/skills/humanish/SKILL.md +63 -60
  636. package/skills/humanish/agents/openai.yaml +1 -1
  637. package/AGENTS.md +0 -99
  638. package/CONTRIBUTING.md +0 -148
  639. package/dist/actors/codex/qualified-versions.d.ts +0 -45
  640. package/dist/actors/codex/qualified-versions.js +0 -87
  641. package/dist/cli/commands/lab.d.ts +0 -3
  642. package/dist/cli/commands/lab.js +0 -193
  643. package/dist/deprecated.d.ts +0 -90
  644. package/dist/deprecated.js +0 -106
  645. package/dist/lab/bag-overrides.d.ts +0 -18
  646. package/dist/lab/bag-overrides.js +0 -121
  647. package/dist/observer/static.d.ts +0 -39
  648. package/dist/observer/static.js +0 -369
  649. package/dist/routes/computer-use/legacy-lane-spec.d.ts +0 -62
  650. package/dist/routes/computer-use/legacy-lane-spec.js +0 -39
  651. package/docs/architecture/comms-inbox.md +0 -122
  652. package/docs/architecture/desktop-recording.md +0 -80
  653. package/docs/architecture/local-browser-runtime.md +0 -178
  654. package/docs/architecture/observer-review.md +0 -144
  655. package/docs/architecture/participant-media.md +0 -90
  656. package/docs/architecture/project-layout.md +0 -62
  657. package/docs/architecture/real-email-receiving.md +0 -136
  658. package/docs/assets/humanish-drawdb-hero.png +0 -0
  659. package/docs/assets/humanish-observer-hero.png +0 -0
  660. package/docs/goals/current.md +0 -207
  661. package/docs/product/lobby-trivia-3player-external-public.md +0 -77
  662. package/docs/product/open-source-install-experience.md +0 -240
  663. package/docs/ramp/README.md +0 -294
  664. package/docs/release/open-source-readiness.md +0 -222
  665. package/docs/release/public-readiness-standard.md +0 -210
  666. package/docs/roadmap/world-class-open-source-v0.md +0 -311
  667. /package/dist/routes/computer-use/{fanout-lanes.d.ts → fanout-records.d.ts} +0 -0
  668. /package/dist/routes/shared-world/{seat-records.d.ts → bundle-records.d.ts} +0 -0
@@ -1,96 +1,46 @@
1
- // The typed homes on RunLabOptions and the one place they meet the route hook bags. runLab calls
2
- // normalizeRunLabOptions first: it refuses an option the route cannot honor, or a new option set
3
- // together with the old field it replaces, and otherwise maps each new option into the bag the
4
- // route reads today. Old fields pass through untouched, so they keep their exact behavior.
1
+ // The typed homes on RunLabOptions. runLab calls normalizeRunLabOptions first: it refuses an option
2
+ // the route cannot honor and otherwise passes the typed options to the route, with env copied and
3
+ // onEvent turned into the emitter. The package's runLab refuses the removed bags
4
+ // (removedOptionRefusal).
5
5
  import path from "node:path";
6
- import { CUA_ACTOR_LAB_SCHEMA } from "../routes/computer-use/types.js";
7
- import { SCRIPTED_BROWSER_LAB_SCHEMA } from "../routes/scripted/types.js";
8
- import { CONCURRENT_SHARED_WORLD_LAB_SCHEMA } from "../routes/shared-world/types.js";
9
- import { TERMINAL_PRODUCT_LAB_SCHEMA, } from "../routes/terminal/types.js";
10
6
  import { isLocalBrowserLab } from "../substrates/local/runtime-config.js";
11
- import { defaultSharedWorldPhaseSink, defaultSubjectPhaseSink } from "../subject/steps.js";
12
- import { HOOK_MEMBERS, withHookOverrides } from "./bag-overrides.js";
13
7
  import { resolveLabDryRun } from "./plan.js";
14
- import { knownSecretValues, labEventEmitter, participantOf, phaseEvent, planEvent, } from "./run-lab-events.js";
8
+ import { knownSecretValues, labEventEmitter } from "./run-lab-events.js";
15
9
  import { rosterOf } from "./parse/actors.js";
16
- const conflict = (home, old) => ({
17
- ok: false,
18
- code: "HUMANISH_LAB_OPTION_CONFLICT",
19
- message: `RunLabOptions.${home} and ${old} are both set. ${old} is the older form of ${home}; set only ${home}.`,
20
- });
10
+ import { studyResultIdentity } from "../run/study-result.js";
21
11
  const unsupported = (option, route, reason) => ({
22
12
  ok: false,
23
- code: "HUMANISH_LAB_OPTION_UNSUPPORTED",
13
+ code: "HUMANISH_STUDY_OPTION_UNSUPPORTED",
24
14
  message: `RunLabOptions.${option} is not supported on the ${route} route: ${reason}`,
25
15
  });
26
- /**
27
- * Whether a caller's bag sets `key`, from its property descriptors: a data property counts when its
28
- * value is defined, an accessor counts without being called. Nothing the caller defined runs.
29
- */
30
- function hasMember(bag, key) {
31
- for (let source = bag ?? null; source !== null && source !== Object.prototype; source = Object.getPrototypeOf(source)) {
32
- const descriptor = Object.getOwnPropertyDescriptor(source, key);
33
- if (descriptor !== undefined)
34
- return "value" in descriptor ? descriptor.value !== undefined : true;
35
- }
36
- return false;
37
- }
38
- /**
39
- * Every old field the options set that has a new home, and whether its home is set too. Presence
40
- * comes from property descriptors (hasMember), so no getter of the caller's runs.
41
- */
42
- function oldFieldsInUse(options) {
43
- const pairs = [
44
- ["env", "cuaHooks", "env"],
45
- ["env", "scriptedHooks", "env"],
46
- ["env", "terminalHooks", "env"],
47
- ["env", "sharedWorldHooks", "env"],
48
- ["scorer", "cuaHooks", "score"],
49
- ["scorer", "cuaHooks", "deriveFeedback"],
50
- ["scorer", "cuaHooks", "deriveArtifacts"],
51
- ["scorer", "sharedWorldHooks", "score"],
52
- ["scorer", "sharedWorldHooks", "deriveFeedback"],
53
- ["scorer", "sharedWorldHooks", "deriveArtifacts"],
54
- ["scorer", "terminalHooks", "score"],
55
- ["scorer", "terminalHooks", "deriveFeedback"],
56
- ["prepareDesktop", "cuaHooks", "prepareDesktop"],
57
- ["prepareDesktop", "scriptedHooks", "prepareDesktop"],
58
- ["prepareDesktop", "sharedWorldHooks", "prepareDesktop"],
59
- ["onEvent", "cuaHooks", "onPreflight"],
60
- ["onEvent", "cuaHooks", "onPhase"],
61
- ["onEvent", "sharedWorldHooks", "onPhase"],
62
- ["onEvent", "automaticAnalysis", "onStart"],
63
- ["onStream", "cuaHooks", "onRuntimeStreamReady"],
64
- ["onStream", "cuaHooks", "onRuntimeStreamEnded"],
65
- ["onStream", "sharedWorldHooks", "onRuntimeStreamReady"],
66
- ["onStream", "sharedWorldHooks", "onRuntimeStreamEnded"],
67
- ["analysisSignal", "automaticAnalysis.deps", "signal"],
68
- ["createProvider", "cuaHooks", "buildProvider"],
69
- ["inProcess", "cuaHooks", "buildExecutor"],
70
- ["rerun.participantIds", "rerun", "laneIds"],
71
- ];
72
- const home = (name) => name === "rerun.participantIds"
73
- ? options.rerun?.participantIds !== undefined
74
- : options[name] !== undefined;
75
- const bagOf = (name) => name === "automaticAnalysis.deps"
76
- ? options.automaticAnalysis?.deps
77
- : options[name];
78
- return pairs
79
- .filter(([, bag, member]) => hasMember(bagOf(bag), member))
80
- .map(([name, bag, member]) => ({ home: name, old: `${bag}.${member}`, clash: home(name) }));
81
- }
82
- /** Old fields removed in the next minor with no replacement. They warn, and they never clash. */
83
- function retiredFieldsInUse(options) {
84
- return hasMember(options.cuaHooks, "createDesktopLane") ? ["cuaHooks.createDesktopLane"] : [];
85
- }
86
- const warned = new Set();
87
- /** One DeprecationWarning per old field per process. The bags' other test seams never warn. */
88
- function warnDeprecated(home, old) {
89
- if (warned.has(old))
90
- return;
91
- warned.add(old);
92
- const replacement = home === undefined ? "It has no replacement." : `Use RunLabOptions.${home}.`;
93
- process.emitWarning(`RunLabOptions.${old} is deprecated and is removed in the next minor. ${replacement}`, { type: "DeprecationWarning", code: "HUMANISH_RUN_LAB_OPTION_DEPRECATED" });
16
+ // Fields RunLabOptions no longer has, and where each one's job went.
17
+ const REMOVED_OPTIONS = {
18
+ cuaHooks: "Use scorer, createProvider, inProcess, prepareDesktop, env, onEvent and onStream.",
19
+ scriptedHooks: "Use prepareDesktop and env.",
20
+ terminalHooks: "Use scorer and env.",
21
+ sharedWorldHooks: "Use scorer, prepareDesktop, env, onEvent and onStream.",
22
+ automaticAnalysis: "Use onEvent (analysis-started, analysis-finished) and analysisSignal.",
23
+ lab: "The humanish CLI sets it.",
24
+ scorerProvenance: "The humanish CLI sets it.",
25
+ };
26
+ /** The refusal for a field a JavaScript caller passed that RunLabOptions no longer has. */
27
+ export function removedOptionRefusal(options) {
28
+ // rerun.laneIds, the older name of rerun.participantIds, would otherwise be ignored, so the rerun
29
+ // would select every failed participant instead of the ones the caller named.
30
+ if (options.rerun !== undefined && Reflect.get(options.rerun, "laneIds") !== undefined)
31
+ return {
32
+ ok: false,
33
+ code: "HUMANISH_STUDY_OPTION_UNSUPPORTED",
34
+ message: 'RunLabOptions.rerun.laneIds was removed. Use rerun.participantIds. See docs/contracts/schemas.md, "Library options".',
35
+ };
36
+ const field = Object.keys(REMOVED_OPTIONS).find((key) => Reflect.get(options, key) !== undefined);
37
+ if (field === undefined)
38
+ return undefined;
39
+ return {
40
+ ok: false,
41
+ code: "HUMANISH_STUDY_OPTION_UNSUPPORTED",
42
+ message: `RunLabOptions.${field} was removed. ${REMOVED_OPTIONS[field]} See docs/contracts/schemas.md, "Library options".`,
43
+ };
94
44
  }
95
45
  /** Why the route cannot honor an option it was given, or undefined when it can. */
96
46
  function unsupportedOption(config, route, options) {
@@ -113,11 +63,8 @@ function unsupportedOption(config, route, options) {
113
63
  if (prepareDesktop !== undefined) {
114
64
  if (isLocalBrowserLab(config))
115
65
  return unsupported("prepareDesktop", route, "a local VM study has no E2B desktop.");
116
- // The run is in process when either executor home is set: inProcess or the older
117
- // cuaHooks.buildExecutor. Either way no desktop exists to prepare.
118
- if (inProcess !== undefined ||
119
- hasMember(options.cuaHooks, "buildExecutor") ||
120
- source === "local-app")
66
+ // An in-process run has no desktop to prepare.
67
+ if (inProcess !== undefined || source === "local-app")
121
68
  return unsupported("prepareDesktop", route, "an in-process run has no desktop.");
122
69
  }
123
70
  return undefined;
@@ -133,200 +80,25 @@ function unsupportedOption(config, route, options) {
133
80
  : "this route has no E2B desktop to prepare.");
134
81
  }
135
82
  /**
136
- * Refuse what the route cannot honor, then map the new options into the old bags. Nothing here
137
- * touches the filesystem, so a refusal leaves no run directory, receipt or sandbox.
83
+ * Refuse what the route cannot honor, copy env, and build the emitter onEvent receives through.
84
+ * Nothing here touches the filesystem, so a refusal leaves no run directory, receipt or sandbox.
138
85
  */
139
86
  export function normalizeRunLabOptions(config, route, options) {
140
- const inUse = oldFieldsInUse(options);
141
- const clash = inUse.find((field) => field.clash);
142
- if (clash)
143
- return conflict(clash.home, clash.old);
144
87
  const refused = unsupportedOption(config, route, options);
145
88
  if (refused)
146
89
  return refused;
147
- for (const { home, old } of inUse)
148
- warnDeprecated(home, old);
149
- for (const old of retiredFieldsInUse(options))
150
- warnDeprecated(undefined, old);
151
90
  const warnings = [];
152
- const { env, scorer, prepareDesktop, onEvent, onStream, analysisSignal, createProvider, inProcess, ...legacy } = options;
91
+ const { env, onEvent, ...forwarded } = options;
153
92
  // The route gets this copy, so it is the env a warning is scrubbed against, whatever the caller
154
93
  // does to its own object afterwards.
155
94
  const forwardedEnv = env === undefined ? undefined : { ...env };
156
95
  const emit = labEventEmitter(onEvent, warnings, () => knownSecretValues(config, options, forwardedEnv));
157
- const normalized = { ...legacy };
158
- const participantIds = options.rerun?.participantIds;
159
- if (options.rerun !== undefined && participantIds !== undefined) {
160
- const { participantIds: _ids, ...rerun } = options.rerun;
161
- normalized.rerun = { ...rerun, laneIds: participantIds };
162
- }
163
- const analysis = withMapped(legacy.automaticAnalysis, HOOK_MEMBERS.analysis, {
164
- ...(analysisSignal === undefined
165
- ? {}
166
- : { deps: { ...legacy.automaticAnalysis?.deps, signal: analysisSignal } }),
167
- ...(emit === undefined
168
- ? {}
169
- : {
170
- onStart: () => {
171
- emit({ type: "analysis-started" });
172
- return () => emit({ type: "analysis-finished" });
173
- },
174
- }),
175
- });
176
- if (analysis !== undefined)
177
- normalized.automaticAnalysis = analysis;
178
- const envHome = forwardedEnv === undefined ? {} : { env: forwardedEnv };
179
- const scoring = scorer === undefined ? {} : scorerHooks(scorer);
180
- switch (route) {
181
- case "computer-use": {
182
- const hooks = withMapped(legacy.cuaHooks, HOOK_MEMBERS.cua, {
183
- ...envHome,
184
- ...scoring,
185
- ...computerUseHooks(config, {
186
- prepareDesktop,
187
- onStream,
188
- createProvider,
189
- inProcess,
190
- legacyInProcess: hasMember(legacy.cuaHooks, "buildExecutor"),
191
- }, emit),
192
- });
193
- if (hooks !== undefined)
194
- normalized.cuaHooks = hooks;
195
- break;
196
- }
197
- case "shared-world": {
198
- const hooks = withMapped(legacy.sharedWorldHooks, HOOK_MEMBERS.sharedWorld, {
199
- ...envHome,
200
- ...scoring,
201
- ...sharedWorldHooks({ prepareDesktop, onStream }, emit),
202
- });
203
- if (hooks !== undefined)
204
- normalized.sharedWorldHooks = hooks;
205
- break;
206
- }
207
- case "terminal": {
208
- const hooks = withMapped(legacy.terminalHooks, HOOK_MEMBERS.terminal, {
209
- ...envHome,
210
- ...(scorer?.score === undefined ? {} : { score: scorer.score }),
211
- ...(scorer?.deriveFeedback === undefined
212
- ? {}
213
- : { deriveFeedback: scorer.deriveFeedback }),
214
- });
215
- if (hooks !== undefined)
216
- normalized.terminalHooks = hooks;
217
- break;
218
- }
219
- case "scripted": {
220
- const hooks = withMapped(legacy.scriptedHooks, HOOK_MEMBERS.scripted, {
221
- ...envHome,
222
- ...(prepareDesktop === undefined
223
- ? {}
224
- : {
225
- prepareDesktop: (desktop) => prepareDesktop(desktop, { kind: "subject" }),
226
- }),
227
- });
228
- if (hooks !== undefined)
229
- normalized.scriptedHooks = hooks;
230
- break;
231
- }
232
- case "preview":
233
- break;
234
- }
235
- return { ok: true, options: normalized, warnings };
236
- }
237
- /** A caller's bag with new options mapped into it. With nothing to map, it is the same object. */
238
- function withMapped(bag, declared, mapped) {
239
- if (Object.keys(mapped).length === 0)
240
- return bag;
241
- return withHookOverrides(bag, declared, mapped);
242
- }
243
- export function scorerHooks(scorer) {
244
- return {
245
- ...(scorer.score === undefined ? {} : { score: scorer.score }),
246
- ...(scorer.deriveFeedback === undefined ? {} : { deriveFeedback: scorer.deriveFeedback }),
247
- ...(scorer.deriveArtifacts === undefined ? {} : { deriveArtifacts: scorer.deriveArtifacts }),
248
- };
249
- }
250
- /** The route awaits what these return, so onStream keeps the old hooks' barrier and errors. */
251
- function streamHooks(onStream) {
252
- return {
253
- onRuntimeStreamReady: (stream) => onStream({
254
- type: "ready",
255
- participantId: stream.laneId,
256
- sandboxId: stream.sandboxId,
257
- simId: stream.simId,
258
- streamId: stream.streamId,
259
- url: stream.url,
260
- }),
261
- onRuntimeStreamEnded: (stream) => onStream({
262
- type: "ended",
263
- participantId: stream.laneId,
264
- simId: stream.simId,
265
- streamId: stream.streamId,
266
- }),
267
- };
268
- }
269
- function computerUseHooks(config, homes, emit) {
270
- const { prepareDesktop, onStream, createProvider, inProcess, legacyInProcess } = homes;
271
- // A local VM study and an in-process run start no E2B stream, and the local study refuses a
272
- // stream hook outright, so onStream is left unset there: it is never called.
273
- const streams = !isLocalBrowserLab(config) && inProcess === undefined && !legacyInProcess;
274
- return {
275
- ...(prepareDesktop === undefined
276
- ? {}
277
- : {
278
- prepareDesktop: (desktop, participant) => prepareDesktop(desktop, {
279
- kind: "participant",
280
- participant: participantOf(participant),
281
- }),
282
- }),
283
- ...(createProvider === undefined
284
- ? {}
285
- : {
286
- buildProvider: ({ config: lab, lane: participant, laneCount, executor }) => createProvider({
287
- config: lab,
288
- participant: participantOf({ ...participant, laneCount }),
289
- executor,
290
- }),
291
- }),
292
- ...(inProcess === undefined
293
- ? {}
294
- : {
295
- buildExecutor: ({ config: lab, appUrl }) => inProcess.executor({ config: lab, appUrl }),
296
- }),
297
- ...(onStream !== undefined && streams ? streamHooks(onStream) : {}),
298
- ...(emit === undefined
299
- ? {}
300
- : {
301
- onPreflight: (plan) => emit(planEvent(plan)),
302
- onPhase: (event, participant) => {
303
- defaultSubjectPhaseSink(event, participant);
304
- emit(phaseEvent(event, { kind: "participant", participant: participantOf(participant) }));
305
- },
306
- }),
307
- };
308
- }
309
- function sharedWorldHooks(homes, emit) {
310
- const { prepareDesktop, onStream } = homes;
311
- return {
312
- ...(prepareDesktop === undefined
313
- ? {}
314
- : {
315
- // The provisioned plane prepares the subject sandbox with no participant, then each one.
316
- prepareDesktop: (desktop, participant) => prepareDesktop(desktop, participant === undefined
317
- ? { kind: "subject" }
318
- : { kind: "participant", participant: participantOf(participant) }),
319
- }),
320
- ...(onStream === undefined ? {} : streamHooks(onStream)),
321
- ...(emit === undefined
322
- ? {}
323
- : {
324
- onPhase: (event) => {
325
- defaultSharedWorldPhaseSink(event);
326
- emit(phaseEvent(event, { kind: "subject" }));
327
- },
328
- }),
329
- };
96
+ // Every route reads its typed options directly, and onEvent reaches it as `emit`. unsupportedOption
97
+ // already refused an option no route reads; the preview route reads no env.
98
+ const normalized = { ...forwarded };
99
+ if (route !== "preview" && forwardedEnv !== undefined)
100
+ normalized.env = forwardedEnv;
101
+ return { ok: true, options: normalized, warnings, emit };
330
102
  }
331
103
  /** A refusal in the route's own result envelope, before any run exists. */
332
104
  export function optionRefusalOutcome(config, route, options, refusal) {
@@ -335,20 +107,24 @@ export function optionRefusalOutcome(config, route, options, refusal) {
335
107
  const actor = config.actors[0]?.type ?? "";
336
108
  const dryRun = resolveLabDryRun(config, options.dryRun, true) ?? true;
337
109
  const runId = options.runId ?? "not-created";
338
- const common = { ok: false, cwd, labId: config.id, actor, dryRun, runId, warnings: [], error };
110
+ const common = { ok: false, cwd, actor, dryRun, runId, warnings: [], error };
339
111
  switch (route) {
340
112
  case "preview":
341
113
  return {
342
114
  route: "preview",
343
- backend: "synthetic",
344
- result: { schema: "humanish.run-result.v1", ok: false, cwd, warnings: [], error },
115
+ result: {
116
+ ...studyResultIdentity("preview", config.id),
117
+ ok: false,
118
+ cwd,
119
+ warnings: [],
120
+ error,
121
+ },
345
122
  };
346
123
  case "computer-use":
347
124
  return {
348
125
  route: "computer-use",
349
- backend: "cua",
350
126
  result: {
351
- schema: CUA_ACTOR_LAB_SCHEMA,
127
+ ...studyResultIdentity("computer-use", config.id),
352
128
  ...common,
353
129
  ok: false,
354
130
  appUrl: config.subject.appUrl ?? config.subject.serve?.url ?? "",
@@ -358,9 +134,8 @@ export function optionRefusalOutcome(config, route, options, refusal) {
358
134
  case "scripted":
359
135
  return {
360
136
  route: "scripted",
361
- backend: "scripted",
362
137
  result: {
363
- schema: SCRIPTED_BROWSER_LAB_SCHEMA,
138
+ ...studyResultIdentity("scripted", config.id),
364
139
  ...common,
365
140
  ok: false,
366
141
  appUrl: config.subject.appUrl ?? "",
@@ -370,9 +145,8 @@ export function optionRefusalOutcome(config, route, options, refusal) {
370
145
  case "terminal":
371
146
  return {
372
147
  route: "terminal",
373
- backend: "terminal",
374
148
  result: {
375
- schema: TERMINAL_PRODUCT_LAB_SCHEMA,
149
+ ...studyResultIdentity("terminal", config.id),
376
150
  ...common,
377
151
  ok: false,
378
152
  product: config.subject.product?.name ?? "",
@@ -382,9 +156,8 @@ export function optionRefusalOutcome(config, route, options, refusal) {
382
156
  const participantCount = rosterOf(config.actors[0])?.length ?? 0;
383
157
  return {
384
158
  route: "shared-world",
385
- backend: "concurrent-shared-world",
386
159
  result: {
387
- schema: CONCURRENT_SHARED_WORLD_LAB_SCHEMA,
160
+ ...studyResultIdentity("shared-world", config.id),
388
161
  ...common,
389
162
  ok: false,
390
163
  topology: "shared-world",
@@ -1,10 +1,10 @@
1
1
  import { type LocalRuntimeStatus } from "../substrates/local/runtime.js";
2
2
  import { type KeyResolutionDeps } from "../keys/key-resolution.js";
3
- export declare const LAB_SUMMARY_SCHEMA = "humanish.lab-summary.v1";
3
+ export declare const STUDY_SUMMARY_SCHEMA = "humanish.study-summary.v1";
4
4
  export interface LabCaps {
5
- /** Per-lane blast-radius budget. */
5
+ /** Per-participant blast-radius budget. */
6
6
  laneUsd?: number;
7
- /** Shared study budget across every lane. */
7
+ /** Shared study budget across every participant. */
8
8
  studyUsd?: number;
9
9
  }
10
10
  export interface LabSummary {
@@ -20,8 +20,9 @@ export interface LabSummary {
20
20
  model: string;
21
21
  maxCostUsd: number | null;
22
22
  };
23
- schema: typeof LAB_SUMMARY_SCHEMA;
24
- labId: string;
23
+ schema: typeof STUDY_SUMMARY_SCHEMA;
24
+ /** The study's `id`. */
25
+ studyId: string;
25
26
  title?: string;
26
27
  description?: string;
27
28
  /** "clone drawdb-io/drawdb", "app-url http://127.0.0.1:3000/", "this-repo". */
@@ -31,11 +32,11 @@ export interface LabSummary {
31
32
  /** The model that will actually run, override or default. */
32
33
  model?: string;
33
34
  /**
34
- * The reasoning effort that will actually run, override or default — and "per-lane" when the
35
- * roster declares more than one, because a single value would be a lie about half the lanes.
35
+ * The reasoning effort that will actually run, override or default, and `"per-lane"` when the
36
+ * roster declares more than one, because a single value would be a lie about half the participants.
36
37
  *
37
38
  * Shown because it was a silent constant: unreachable from a lab, so every run took the provider
38
- * default. A study variable you cannot see is one nobody chose (#497).
39
+ * default. A study variable you cannot see is one nobody chose.
39
40
  */
40
41
  reasoningEffort?: string;
41
42
  caps: LabCaps;
@@ -45,6 +46,11 @@ export interface LabSummary {
45
46
  */
46
47
  keysReady?: boolean;
47
48
  missingKeys?: string[];
49
+ /**
50
+ * The planner's refusal message when a live key check finds the lab will not plan, as
51
+ * `humanish lab run` would report it. `keysReady` is then unset: a refused plan lists no keys.
52
+ */
53
+ planRefusal?: string;
48
54
  }
49
55
  export interface ReadLabSummaryOptions {
50
56
  /** Skip the key probe (it touches vendor stores); the screen then shows no keys line. */
@@ -54,7 +60,7 @@ export interface ReadLabSummaryOptions {
54
60
  keyDeps?: KeyResolutionDeps;
55
61
  }
56
62
  /**
57
- * Describe one lab. Returns null when the manifest cannot be resolved — the caller already knows
63
+ * Describe one lab. Returns null when the manifest cannot be resolved: the caller already knows
58
64
  * the lab exists from the listing, so this failing means the file changed underneath them.
59
65
  */
60
66
  export declare function readLabSummary(cwd: string, lab: string, options?: ReadLabSummaryOptions): Promise<LabSummary | null>;
@@ -1,16 +1,17 @@
1
1
  import { isLocalBrowserLab } from "../substrates/local/runtime-config.js";
2
2
  import { localRuntimeStatus } from "../substrates/local/runtime.js";
3
- // What a lab IS, for the surface that has to describe it before you spend money (#455).
3
+ // What a lab is, for the surface that has to describe it before you spend money.
4
4
  //
5
- // The run index and run detail answer questions about runs. This answers a question about the LAB
6
- // itself — what it drives, who is in it, which model, and what it is allowed to spend — which is
5
+ // The run index and run detail answer questions about runs. This answers a question about the lab
6
+ // itself (what it drives, who is in it, which model, and what it is allowed to spend), which is
7
7
  // what a stakeholder reads on the screen where they decide whether to press Start.
8
8
  //
9
9
  // Resolved analysis defaults are shown independently of declared participant caps. A cap that is not
10
10
  // declared is not "unlimited" and not "$0"; it is a line the screen does not draw.
11
11
  import { resolveLabDryRun } from "./plan.js";
12
12
  import { routeOf } from "./plan.js";
13
- import { labKeyRequirements, localCodexParticipantCheck } from "./doctor.js";
13
+ import { localCodexParticipantCheck, planCliRun } from "./doctor.js";
14
+ import { requiredKeys, requiredSubjectEnv } from "./requirements.js";
14
15
  import { automaticAnalysisBudget } from "../analysis/automatic-config.js";
15
16
  import { DEFAULT_OPENAI_CU_MODEL, DEFAULT_OPENAI_CU_REASONING_EFFORT, } from "../actors/computer-use/openai-provider.js";
16
17
  import { inspectLabManifest } from "./discover.js";
@@ -18,10 +19,10 @@ import { isComputerUseComposition } from "./routing.js";
18
19
  import { probeKeySources } from "../keys/key-resolution.js";
19
20
  import { receivingRequiredKey } from "../comms/setup.js";
20
21
  import { rosterOf } from "./parse/actors.js";
21
- export const LAB_SUMMARY_SCHEMA = "humanish.lab-summary.v1";
22
+ export const STUDY_SUMMARY_SCHEMA = "humanish.study-summary.v1";
22
23
  /**
23
- * The effort every lane will run at, or "per-lane" when they differ. A lane that declares nothing
24
- * inherits the actor's, and an actor that declares nothing gets the provider default — which is
24
+ * The effort every participant will run at, or `"per-lane"` when they differ. A participant that declares nothing
25
+ * inherits the actor's, and an actor that declares nothing gets the provider default, which is
25
26
  * reported as the resolved value, exactly as `model` reports its default rather than hiding it.
26
27
  */
27
28
  function reasoningEffortOf(config) {
@@ -46,7 +47,7 @@ function subjectOf(config) {
46
47
  return `${subject.source} ${subject.appUrl}`;
47
48
  return subject.source;
48
49
  }
49
- /** How many participants, and who — collapsed when they are all the same persona. */
50
+ /** How many participants, and who; collapsed when they are all the same persona. */
50
51
  function participantsOf(config) {
51
52
  const actors = config.actors;
52
53
  const actor = actors?.[0];
@@ -60,7 +61,7 @@ function participantsOf(config) {
60
61
  const unique = [...new Set(personas)];
61
62
  if (unique.length === 0)
62
63
  return `${count} participant${count === 1 ? "" : "s"}`;
63
- // Several lanes of ONE persona reads as "3 × skeptical-power-user"; genuinely different people
64
+ // Several participants of one persona reads as "3 × skeptical-power-user"; genuinely different people
64
65
  // are named, because which personas are in a study is the study's design.
65
66
  return unique.length === 1 ? `${count} × ${unique[0]}` : unique.join(" · ");
66
67
  }
@@ -75,7 +76,7 @@ function capsOf(config) {
75
76
  };
76
77
  }
77
78
  /**
78
- * Describe one lab. Returns null when the manifest cannot be resolved — the caller already knows
79
+ * Describe one lab. Returns null when the manifest cannot be resolved: the caller already knows
79
80
  * the lab exists from the listing, so this failing means the file changed underneath them.
80
81
  */
81
82
  export async function readLabSummary(cwd, lab, options = {}) {
@@ -87,9 +88,14 @@ export async function readLabSummary(cwd, lab, options = {}) {
87
88
  const route = routeOf(inspected.config);
88
89
  let keysReady;
89
90
  let missingKeys;
90
- if (options.checkKeys === true) {
91
- const dryRun = resolveLabDryRun(inspected.config, undefined, true) === true;
92
- const subjectKeys = dryRun ? [] : (inspected.config.subject.env ?? []);
91
+ const dryRun = resolveLabDryRun(inspected.config, undefined, true) === true;
92
+ // A live key check reads the plan's requirements. A lab the planner refuses has none to check,
93
+ // so the summary reports the refusal in place of its keys.
94
+ const planned = options.checkKeys === true && !dryRun ? await planCliRun(inspected.config, cwd) : undefined;
95
+ const planRefusal = planned?.ok === false ? planned.refusal.message : undefined;
96
+ if (options.checkKeys === true && planned?.ok !== false) {
97
+ const requirements = planned?.planned.plan.requirements ?? [];
98
+ const subjectKeys = requiredSubjectEnv(requirements);
93
99
  const email = inspected.config.comms?.email;
94
100
  const receivingKey = !dryRun && email?.kind === "real"
95
101
  ? await receivingRequiredKey(cwd, email.connection)
@@ -109,9 +115,9 @@ export async function readLabSummary(cwd, lab, options = {}) {
109
115
  ...(options.keyDeps === undefined ? {} : { deps: options.keyDeps }),
110
116
  }).catch(() => []);
111
117
  const present = new Set(probes.filter((probe) => probe.source !== null).map((probe) => probe.name));
112
- const required = labKeyRequirements(inspected.config, route, dryRun, (name) => present.has(name));
118
+ const required = requiredKeys(requirements, (name) => present.has(name));
113
119
  const missing = [
114
- ...new Set([...required.keys, ...subjectKeys, ...(receivingKey ? [receivingKey] : [])]),
120
+ ...new Set([...required, ...subjectKeys, ...(receivingKey ? [receivingKey] : [])]),
115
121
  ].filter((name) => !present.has(name));
116
122
  if (receivingKey === null)
117
123
  missing.push("email connection");
@@ -148,13 +154,13 @@ export async function readLabSummary(cwd, lab, options = {}) {
148
154
  },
149
155
  }
150
156
  : {}),
151
- schema: LAB_SUMMARY_SCHEMA,
157
+ schema: STUDY_SUMMARY_SCHEMA,
152
158
  ...(inspected.config.comms?.email?.kind === "real"
153
159
  ? {
154
160
  communications: `Real email · ${inspected.config.comms.email.connection} · fresh inbox per participant · hosted processing · local review only`,
155
161
  }
156
162
  : {}),
157
- labId: String(config.id ?? lab),
163
+ studyId: String(config.id ?? lab),
158
164
  ...(typeof config.title === "string" ? { title: config.title } : {}),
159
165
  ...(typeof config.description === "string" ? { description: config.description.trim() } : {}),
160
166
  ...(subject === undefined ? {} : { subject }),
@@ -164,5 +170,6 @@ export async function readLabSummary(cwd, lab, options = {}) {
164
170
  caps: capsOf(inspected.config),
165
171
  ...(keysReady === undefined ? {} : { keysReady }),
166
172
  ...(missingKeys === undefined ? {} : { missingKeys }),
173
+ ...(planRefusal === undefined ? {} : { planRefusal }),
167
174
  };
168
175
  }