humanish 0.107.0 → 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 (521) hide show
  1. package/ARCHITECTURE.md +22 -17
  2. package/CHANGELOG.md +14 -0
  3. package/CONTEXT.md +51 -44
  4. package/README.md +145 -172
  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-ui.js +1 -1
  14. package/dist/actors/codex/codex-admission.d.ts +91 -0
  15. package/dist/actors/codex/codex-admission.js +150 -0
  16. package/dist/actors/codex/restricted-executable.d.ts +4 -4
  17. package/dist/actors/codex/restricted-executable.js +8 -8
  18. package/dist/actors/codex/restricted-launch.d.ts +2 -1
  19. package/dist/actors/codex/restricted-launch.js +1 -1
  20. package/dist/actors/codex/restricted-participant.js +8 -6
  21. package/dist/actors/codex/restricted-policy.d.ts +2 -2
  22. package/dist/actors/codex/restricted-policy.js +2 -2
  23. package/dist/actors/codex/restricted-session.d.ts +2 -2
  24. package/dist/actors/codex/restricted-session.js +10 -5
  25. package/dist/actors/computer-use/actor.d.ts +16 -16
  26. package/dist/actors/computer-use/actor.js +2 -2
  27. package/dist/actors/computer-use/admission-limit.d.ts +1 -1
  28. package/dist/actors/computer-use/admission-limit.js +1 -1
  29. package/dist/actors/computer-use/loop/actions.d.ts +3 -3
  30. package/dist/actors/computer-use/loop/actions.js +10 -10
  31. package/dist/actors/computer-use/loop/backstop.d.ts +3 -3
  32. package/dist/actors/computer-use/loop/backstop.js +14 -12
  33. package/dist/actors/computer-use/loop/ending.d.ts +5 -5
  34. package/dist/actors/computer-use/loop/ending.js +7 -7
  35. package/dist/actors/computer-use/loop/observation.d.ts +2 -2
  36. package/dist/actors/computer-use/loop/observation.js +9 -9
  37. package/dist/actors/computer-use/loop/provider-call.d.ts +1 -1
  38. package/dist/actors/computer-use/loop/provider-call.js +1 -1
  39. package/dist/actors/computer-use/loop/session.js +3 -3
  40. package/dist/actors/computer-use/loop/spend.d.ts +1 -1
  41. package/dist/actors/computer-use/loop/spend.js +1 -1
  42. package/dist/actors/computer-use/loop/trace.js +9 -8
  43. package/dist/actors/computer-use/loop/types.d.ts +25 -23
  44. package/dist/actors/computer-use/loop/usage.js +2 -2
  45. package/dist/actors/computer-use/openai-context.d.ts +37 -0
  46. package/dist/actors/computer-use/openai-context.js +214 -0
  47. package/dist/actors/computer-use/openai-provider.d.ts +11 -8
  48. package/dist/actors/computer-use/openai-provider.js +45 -34
  49. package/dist/actors/computer-use/openai-requests.d.ts +36 -10
  50. package/dist/actors/computer-use/openai-requests.js +82 -15
  51. package/dist/actors/computer-use/openai-wire.d.ts +19 -7
  52. package/dist/actors/computer-use/openai-wire.js +36 -34
  53. package/dist/actors/contract.d.ts +78 -43
  54. package/dist/actors/contract.js +29 -23
  55. package/dist/actors/local-agent/claude-session.d.ts +1 -1
  56. package/dist/actors/local-agent/claude-session.js +10 -9
  57. package/dist/actors/local-agent/cli.d.ts +8 -6
  58. package/dist/actors/local-agent/cli.js +24 -28
  59. package/dist/actors/local-agent/readiness.d.ts +2 -2
  60. package/dist/actors/local-agent/readiness.js +4 -4
  61. package/dist/actors/reasoning-effort.js +6 -6
  62. package/dist/actors/registry.d.ts +10 -10
  63. package/dist/actors/registry.js +18 -17
  64. package/dist/actors/scripted-browser/actor.d.ts +8 -8
  65. package/dist/actors/scripted-browser/actor.js +16 -16
  66. package/dist/actors/scripted-browser/browser-command.js +1 -1
  67. package/dist/actors/scripted-browser/steps.js +1 -1
  68. package/dist/actors/scripted-browser/types.d.ts +1 -1
  69. package/dist/actors/stop-conditions.d.ts +1 -1
  70. package/dist/analysis/codex-config.d.ts +6 -2
  71. package/dist/analysis/codex-config.js +22 -14
  72. package/dist/analysis/service.js +5 -5
  73. package/dist/cli/commands/analyze.js +19 -16
  74. package/dist/cli/commands/codex.js +9 -9
  75. package/dist/cli/commands/comms.js +54 -33
  76. package/dist/cli/commands/feedback.js +20 -21
  77. package/dist/cli/commands/lab-format.d.ts +5 -4
  78. package/dist/cli/commands/lab-format.js +35 -23
  79. package/dist/cli/commands/lab-route-computer-use.js +6 -7
  80. package/dist/cli/commands/lab-route-preview.js +4 -3
  81. package/dist/cli/commands/lab-route-shared-world.js +3 -3
  82. package/dist/cli/commands/lab-run.js +10 -11
  83. package/dist/cli/commands/lab-scorer.d.ts +2 -2
  84. package/dist/cli/commands/lab-scorer.js +1 -1
  85. package/dist/cli/commands/migrate.d.ts +4 -0
  86. package/dist/cli/commands/migrate.js +65 -0
  87. package/dist/cli/commands/observe.js +147 -108
  88. package/dist/cli/commands/run-command.d.ts +10 -0
  89. package/dist/cli/commands/run-command.js +85 -0
  90. package/dist/cli/commands/runs.js +137 -138
  91. package/dist/cli/commands/setup.d.ts +2 -2
  92. package/dist/cli/commands/setup.js +26 -21
  93. package/dist/cli/commands/study.d.ts +3 -0
  94. package/dist/cli/commands/study.js +182 -0
  95. package/dist/cli/commands/tui.d.ts +4 -4
  96. package/dist/cli/commands/tui.js +21 -21
  97. package/dist/cli/commands/watch.js +60 -75
  98. package/dist/cli/deprecations.d.ts +18 -0
  99. package/dist/cli/deprecations.js +48 -0
  100. package/dist/cli/doctor.d.ts +15 -5
  101. package/dist/cli/doctor.js +103 -48
  102. package/dist/cli/first-run-path.d.ts +12 -10
  103. package/dist/cli/first-run-path.js +30 -28
  104. package/dist/cli/io.d.ts +41 -6
  105. package/dist/cli/io.js +97 -22
  106. package/dist/cli/observer-follow.d.ts +2 -2
  107. package/dist/cli/observer-follow.js +5 -6
  108. package/dist/cli/orientation.d.ts +6 -3
  109. package/dist/cli/orientation.js +43 -39
  110. package/dist/cli/product-sentence.d.ts +6 -0
  111. package/dist/cli/product-sentence.js +6 -0
  112. package/dist/cli/program.d.ts +6 -1
  113. package/dist/cli/program.js +109 -40
  114. package/dist/cli/telemetry.d.ts +15 -15
  115. package/dist/cli/telemetry.js +48 -40
  116. package/dist/cli.js +1 -1
  117. package/dist/comms/capture-surface.d.ts +13 -12
  118. package/dist/comms/capture-surface.js +23 -22
  119. package/dist/comms/catch-host.d.ts +7 -7
  120. package/dist/comms/catch-host.js +14 -14
  121. package/dist/comms/email-catch.d.ts +3 -3
  122. package/dist/comms/email-catch.js +8 -8
  123. package/dist/comms/external-evidence.js +2 -2
  124. package/dist/comms/extract.js +2 -2
  125. package/dist/comms/fake-inbox.d.ts +2 -2
  126. package/dist/comms/fake-inbox.js +2 -2
  127. package/dist/comms/receiving-render.d.ts +1 -1
  128. package/dist/comms/receiving-render.js +2 -2
  129. package/dist/comms/sandbox-catch-script.d.ts +6 -6
  130. package/dist/comms/sandbox-catch-script.js +6 -6
  131. package/dist/comms/sandbox-catch.d.ts +36 -37
  132. package/dist/comms/sandbox-catch.js +34 -35
  133. package/dist/comms/setup.js +42 -8
  134. package/dist/comms/thread-evidence.d.ts +1 -1
  135. package/dist/comms/thread-evidence.js +6 -6
  136. package/dist/comms/types.d.ts +6 -6
  137. package/dist/comms/types.js +3 -3
  138. package/dist/evidence/frame-signature.d.ts +1 -1
  139. package/dist/evidence/frame-signature.js +4 -4
  140. package/dist/evidence/redaction.d.ts +3 -3
  141. package/dist/evidence/redaction.js +4 -4
  142. package/dist/feedback/draft.js +36 -78
  143. package/dist/feedback/export-bundle.js +1 -1
  144. package/dist/feedback/export.d.ts +5 -1
  145. package/dist/feedback/export.js +7 -8
  146. package/dist/feedback/feedback.d.ts +2 -2
  147. package/dist/feedback/feedback.js +21 -3
  148. package/dist/guest/chromium-text.js +2 -2
  149. package/dist/guest/desktop-native.d.ts +1 -1
  150. package/dist/guest/runtime.js +1 -1
  151. package/dist/index.d.ts +12 -10
  152. package/dist/index.js +8 -6
  153. package/dist/keys/key-resolution.d.ts +5 -5
  154. package/dist/keys/key-resolution.js +23 -23
  155. package/dist/lab/adapter-extension.d.ts +7 -7
  156. package/dist/lab/adapter-extension.js +13 -36
  157. package/dist/lab/adapter-scorer-loader.d.ts +7 -7
  158. package/dist/lab/adapter-scorer-loader.js +32 -32
  159. package/dist/lab/composition-rules.js +42 -42
  160. package/dist/lab/config.js +65 -25
  161. package/dist/lab/deprecated-fields.d.ts +10 -0
  162. package/dist/lab/deprecated-fields.js +24 -0
  163. package/dist/lab/device-presets.d.ts +8 -8
  164. package/dist/lab/device-presets.js +11 -11
  165. package/dist/lab/discover.d.ts +13 -9
  166. package/dist/lab/discover.js +117 -57
  167. package/dist/lab/doctor.d.ts +10 -3
  168. package/dist/lab/doctor.js +47 -9
  169. package/dist/lab/init-templates.js +147 -147
  170. package/dist/lab/init.d.ts +1 -1
  171. package/dist/lab/init.js +41 -9
  172. package/dist/lab/keys.d.ts +2 -0
  173. package/dist/lab/keys.js +42 -8
  174. package/dist/lab/lab-deps.d.ts +7 -12
  175. package/dist/lab/parse/actors.js +9 -9
  176. package/dist/lab/parse/comms.js +5 -5
  177. package/dist/lab/parse/execution.js +13 -13
  178. package/dist/lab/parse/study-v3.d.ts +23 -0
  179. package/dist/lab/parse/study-v3.js +259 -0
  180. package/dist/lab/parse/subject-state.d.ts +7 -7
  181. package/dist/lab/parse/subject-state.js +16 -16
  182. package/dist/lab/parse/subject.js +28 -28
  183. package/dist/lab/parse/values.d.ts +1 -1
  184. package/dist/lab/parse/values.js +3 -3
  185. package/dist/lab/persona-resolve.d.ts +4 -4
  186. package/dist/lab/persona-resolve.js +4 -4
  187. package/dist/lab/plan-participants.d.ts +2 -2
  188. package/dist/lab/plan-types.d.ts +4 -4
  189. package/dist/lab/plan.d.ts +1 -7
  190. package/dist/lab/plan.js +10 -41
  191. package/dist/lab/preflight-probes.js +11 -11
  192. package/dist/lab/preflight-result.d.ts +2 -1
  193. package/dist/lab/preflight-result.js +5 -4
  194. package/dist/lab/preflight.d.ts +7 -5
  195. package/dist/lab/preflight.js +5 -5
  196. package/dist/lab/routing.d.ts +31 -25
  197. package/dist/lab/routing.js +60 -29
  198. package/dist/lab/run-lab-events.d.ts +0 -3
  199. package/dist/lab/run-lab-events.js +0 -6
  200. package/dist/lab/run-lab-homes.d.ts +22 -10
  201. package/dist/lab/run-lab-homes.js +5 -1
  202. package/dist/lab/run-lab-options.d.ts +1 -1
  203. package/dist/lab/run-lab-options.js +16 -13
  204. package/dist/lab/summary.d.ts +7 -6
  205. package/dist/lab/summary.js +10 -10
  206. package/dist/lab/tasks.d.ts +15 -15
  207. package/dist/lab/tasks.js +14 -14
  208. package/dist/lab/types.d.ts +101 -95
  209. package/dist/lab/types.js +2 -0
  210. package/dist/lab/validation.d.ts +13 -13
  211. package/dist/lab/validation.js +44 -42
  212. package/dist/lab/warnings.d.ts +10 -0
  213. package/dist/lab/warnings.js +61 -33
  214. package/dist/library-aliases.d.ts +56 -0
  215. package/dist/library-aliases.js +22 -0
  216. package/dist/observer/artifact.d.ts +1 -1
  217. package/dist/observer/artifact.js +6 -6
  218. package/dist/observer/data.d.ts +6 -6
  219. package/dist/observer/data.js +5 -4
  220. package/dist/observer/exposure.d.ts +1 -1
  221. package/dist/observer/exposure.js +11 -11
  222. package/dist/observer/http.js +1 -1
  223. package/dist/observer/library.d.ts +1 -1
  224. package/dist/observer/library.js +4 -2
  225. package/dist/observer/listen.js +5 -4
  226. package/dist/observer/render.d.ts +1 -1
  227. package/dist/observer/render.js +10 -5
  228. package/dist/observer/run-routes.d.ts +3 -3
  229. package/dist/observer/run-routes.js +1 -1
  230. package/dist/observer/serve.js +7 -3
  231. package/dist/observer/tunnel.js +1 -1
  232. package/dist/observer-app.html +4 -4
  233. package/dist/routes/computer-use/bundle-parts.d.ts +9 -9
  234. package/dist/routes/computer-use/bundle-parts.js +15 -15
  235. package/dist/routes/computer-use/bundle.js +3 -3
  236. package/dist/routes/computer-use/e2b-desktop/comms.d.ts +1 -1
  237. package/dist/routes/computer-use/e2b-desktop/comms.js +14 -14
  238. package/dist/routes/computer-use/e2b-desktop/desktop.js +4 -4
  239. package/dist/routes/computer-use/e2b-desktop/fidelity.d.ts +4 -3
  240. package/dist/routes/computer-use/e2b-desktop/fidelity.js +11 -10
  241. package/dist/routes/computer-use/e2b-desktop/prepare.js +7 -7
  242. package/dist/routes/computer-use/e2b-desktop/start.js +9 -8
  243. package/dist/routes/computer-use/e2b-desktop/teardown.js +5 -4
  244. package/dist/routes/computer-use/external-comms.d.ts +1 -1
  245. package/dist/routes/computer-use/external-comms.js +1 -1
  246. package/dist/routes/computer-use/fanout-bundle.js +18 -18
  247. package/dist/routes/computer-use/fanout-records.js +10 -11
  248. package/dist/routes/computer-use/live-flush.d.ts +1 -1
  249. package/dist/routes/computer-use/live-flush.js +6 -6
  250. package/dist/routes/computer-use/live-phase.d.ts +4 -2
  251. package/dist/routes/computer-use/live-phase.js +6 -6
  252. package/dist/routes/computer-use/local-vm.js +1 -1
  253. package/dist/routes/computer-use/participant-desktop.d.ts +4 -4
  254. package/dist/routes/computer-use/participant-desktop.js +4 -4
  255. package/dist/routes/computer-use/participant-execution.d.ts +4 -4
  256. package/dist/routes/computer-use/participant-execution.js +9 -9
  257. package/dist/routes/computer-use/participant-model.d.ts +6 -0
  258. package/dist/routes/computer-use/participant-model.js +31 -13
  259. package/dist/routes/computer-use/participant-prompt.d.ts +11 -11
  260. package/dist/routes/computer-use/participant-prompt.js +6 -6
  261. package/dist/routes/computer-use/participant-runs.d.ts +7 -7
  262. package/dist/routes/computer-use/participant-runs.js +13 -13
  263. package/dist/routes/computer-use/plan.js +22 -22
  264. package/dist/routes/computer-use/preflight.js +21 -21
  265. package/dist/routes/computer-use/rerun-selection.js +1 -1
  266. package/dist/routes/computer-use/result.js +11 -11
  267. package/dist/routes/computer-use/route.d.ts +2 -1
  268. package/dist/routes/computer-use/route.js +15 -14
  269. package/dist/routes/computer-use/self-report.d.ts +7 -7
  270. package/dist/routes/computer-use/self-report.js +31 -31
  271. package/dist/routes/computer-use/setup.d.ts +1 -1
  272. package/dist/routes/computer-use/setup.js +17 -18
  273. package/dist/routes/computer-use/single-bundle.d.ts +7 -7
  274. package/dist/routes/computer-use/single-bundle.js +28 -30
  275. package/dist/routes/computer-use/subject-projection.d.ts +1 -1
  276. package/dist/routes/computer-use/subject-projection.js +6 -6
  277. package/dist/routes/computer-use/types.d.ts +40 -42
  278. package/dist/routes/computer-use/types.js +10 -10
  279. package/dist/routes/preview.d.ts +8 -2
  280. package/dist/routes/preview.js +8 -4
  281. package/dist/routes/scripted/bundle.d.ts +2 -2
  282. package/dist/routes/scripted/bundle.js +13 -12
  283. package/dist/routes/scripted/plan.d.ts +1 -1
  284. package/dist/routes/scripted/plan.js +9 -9
  285. package/dist/routes/scripted/result.js +5 -5
  286. package/dist/routes/scripted/route.js +5 -6
  287. package/dist/routes/scripted/scenario.js +2 -2
  288. package/dist/routes/scripted/setup.js +7 -7
  289. package/dist/routes/scripted/subject.js +1 -1
  290. package/dist/routes/scripted/surface-records.js +3 -3
  291. package/dist/routes/scripted/types.d.ts +3 -5
  292. package/dist/routes/scripted/types.js +1 -1
  293. package/dist/routes/shared-world/bundle-records.js +9 -8
  294. package/dist/routes/shared-world/bundle.d.ts +5 -5
  295. package/dist/routes/shared-world/bundle.js +40 -38
  296. package/dist/routes/shared-world/checkpoints.d.ts +1 -1
  297. package/dist/routes/shared-world/checkpoints.js +1 -1
  298. package/dist/routes/shared-world/comms.d.ts +5 -5
  299. package/dist/routes/shared-world/comms.js +14 -14
  300. package/dist/routes/shared-world/external-public.d.ts +4 -3
  301. package/dist/routes/shared-world/external-public.js +16 -12
  302. package/dist/routes/shared-world/handoff.d.ts +7 -6
  303. package/dist/routes/shared-world/handoff.js +65 -57
  304. package/dist/routes/shared-world/lobby-code.d.ts +2 -2
  305. package/dist/routes/shared-world/lobby-code.js +9 -9
  306. package/dist/routes/shared-world/participant-specs.d.ts +7 -6
  307. package/dist/routes/shared-world/participant-specs.js +31 -24
  308. package/dist/routes/shared-world/plan.js +7 -7
  309. package/dist/routes/shared-world/provenance.d.ts +2 -2
  310. package/dist/routes/shared-world/provenance.js +2 -2
  311. package/dist/routes/shared-world/provisioned.js +14 -13
  312. package/dist/routes/shared-world/result.js +20 -21
  313. package/dist/routes/shared-world/route.js +23 -22
  314. package/dist/routes/shared-world/setup.d.ts +3 -3
  315. package/dist/routes/shared-world/setup.js +4 -4
  316. package/dist/routes/shared-world/types.d.ts +30 -28
  317. package/dist/routes/shared-world/types.js +4 -4
  318. package/dist/routes/terminal/adapter.d.ts +3 -3
  319. package/dist/routes/terminal/adapter.js +5 -5
  320. package/dist/routes/terminal/bundle.d.ts +3 -3
  321. package/dist/routes/terminal/bundle.js +22 -21
  322. package/dist/routes/terminal/credentials.d.ts +4 -4
  323. package/dist/routes/terminal/credentials.js +7 -7
  324. package/dist/routes/terminal/dry-run.js +4 -4
  325. package/dist/routes/terminal/encoding.js +2 -2
  326. package/dist/routes/terminal/ledger.d.ts +3 -3
  327. package/dist/routes/terminal/ledger.js +14 -14
  328. package/dist/routes/terminal/live-finish.js +3 -3
  329. package/dist/routes/terminal/live-sandbox.js +12 -13
  330. package/dist/routes/terminal/persona.js +1 -1
  331. package/dist/routes/terminal/plan.js +11 -11
  332. package/dist/routes/terminal/recorder.js +2 -2
  333. package/dist/routes/terminal/result.js +8 -8
  334. package/dist/routes/terminal/route.js +6 -7
  335. package/dist/routes/terminal/sandbox.d.ts +1 -1
  336. package/dist/routes/terminal/sandbox.js +1 -1
  337. package/dist/routes/terminal/session.js +8 -7
  338. package/dist/routes/terminal/token-usage.d.ts +1 -1
  339. package/dist/routes/terminal/token-usage.js +7 -8
  340. package/dist/routes/terminal/trace.d.ts +2 -2
  341. package/dist/routes/terminal/trace.js +2 -2
  342. package/dist/routes/terminal/types.d.ts +26 -28
  343. package/dist/routes/terminal/types.js +3 -3
  344. package/dist/run/bundle-shape.js +3 -3
  345. package/dist/run/bundle.d.ts +46 -46
  346. package/dist/run/bundle.js +2 -1
  347. package/dist/run/cost-summary.js +3 -3
  348. package/dist/run/costs.js +7 -1
  349. package/dist/run/detail.d.ts +6 -6
  350. package/dist/run/detail.js +4 -4
  351. package/dist/run/dry-run-inputs.js +1 -1
  352. package/dist/run/dry-run.js +18 -18
  353. package/dist/run/judge.d.ts +19 -13
  354. package/dist/run/judge.js +18 -8
  355. package/dist/run/paths.d.ts +1 -1
  356. package/dist/run/paths.js +1 -1
  357. package/dist/run/pricing.d.ts +11 -6
  358. package/dist/run/pricing.js +20 -13
  359. package/dist/run/projection.d.ts +14 -14
  360. package/dist/run/projection.js +15 -15
  361. package/dist/run/reclaim.js +2 -2
  362. package/dist/run/results.d.ts +5 -5
  363. package/dist/run/run-index.d.ts +8 -6
  364. package/dist/run/run-index.js +15 -16
  365. package/dist/run/run-not-found.d.ts +5 -0
  366. package/dist/run/run-not-found.js +15 -0
  367. package/dist/run/run.d.ts +5 -4
  368. package/dist/run/run.js +1 -1
  369. package/dist/run/sandbox-receipts.d.ts +2 -2
  370. package/dist/run/sandbox-receipts.js +3 -3
  371. package/dist/run/shared-world-evidence.d.ts +36 -35
  372. package/dist/run/shared-world-evidence.js +4 -4
  373. package/dist/run/shared-world-shape.d.ts +1 -1
  374. package/dist/run/shared-world-shape.js +6 -6
  375. package/dist/run/stats.d.ts +12 -6
  376. package/dist/run/stats.js +116 -58
  377. package/dist/run/status.d.ts +8 -29
  378. package/dist/run/status.js +5 -27
  379. package/dist/run/stored-runs.js +2 -1
  380. package/dist/run/stream-shape.js +1 -1
  381. package/dist/run/streams.d.ts +6 -6
  382. package/dist/run/study-provenance.d.ts +47 -0
  383. package/dist/run/study-provenance.js +63 -0
  384. package/dist/run/study-result.d.ts +16 -0
  385. package/dist/run/study-result.js +9 -0
  386. package/dist/run/text.d.ts +2 -0
  387. package/dist/run/text.js +4 -0
  388. package/dist/run-lab.d.ts +7 -7
  389. package/dist/run-lab.js +1 -3
  390. package/dist/study/convert.d.ts +33 -0
  391. package/dist/study/convert.js +432 -0
  392. package/dist/study/field-paths.d.ts +12 -0
  393. package/dist/study/field-paths.js +126 -0
  394. package/dist/study/files.d.ts +26 -0
  395. package/dist/study/files.js +43 -0
  396. package/dist/study/migrate.d.ts +48 -0
  397. package/dist/study/migrate.js +408 -0
  398. package/dist/study/owned-files.d.ts +38 -0
  399. package/dist/study/owned-files.js +182 -0
  400. package/dist/subject/clone.d.ts +1 -1
  401. package/dist/subject/desktop-cli.d.ts +1 -1
  402. package/dist/subject/desktop-cli.js +2 -2
  403. package/dist/subject/local-tree-archive.js +1 -1
  404. package/dist/subject/local-tree.d.ts +1 -1
  405. package/dist/subject/node-bootstrap.js +1 -1
  406. package/dist/subject/runtime.js +8 -9
  407. package/dist/subject/serve.d.ts +1 -1
  408. package/dist/subject/serve.js +3 -3
  409. package/dist/subject/state.d.ts +1 -1
  410. package/dist/subject/steps.d.ts +5 -5
  411. package/dist/subject/steps.js +4 -4
  412. package/dist/substrates/command-failure.d.ts +3 -3
  413. package/dist/substrates/command-failure.js +3 -3
  414. package/dist/substrates/detached.d.ts +6 -6
  415. package/dist/substrates/detached.js +7 -7
  416. package/dist/substrates/e2b/cdp-probe.d.ts +9 -9
  417. package/dist/substrates/e2b/cdp-probe.js +14 -17
  418. package/dist/substrates/e2b/desktop-browser.d.ts +2 -2
  419. package/dist/substrates/e2b/desktop-browser.js +8 -8
  420. package/dist/substrates/e2b/desktop-cdp.d.ts +9 -9
  421. package/dist/substrates/e2b/desktop-cdp.js +8 -8
  422. package/dist/substrates/e2b/desktop-executor.d.ts +1 -1
  423. package/dist/substrates/e2b/desktop-executor.js +1 -1
  424. package/dist/substrates/e2b/desktop-geometry.d.ts +3 -3
  425. package/dist/substrates/e2b/desktop-geometry.js +7 -7
  426. package/dist/substrates/e2b/desktop-media.d.ts +1 -1
  427. package/dist/substrates/e2b/desktop-media.js +1 -1
  428. package/dist/substrates/e2b/desktop-screenshot-cleanup.d.ts +3 -3
  429. package/dist/substrates/e2b/desktop-screenshot-cleanup.js +3 -3
  430. package/dist/substrates/e2b/sandbox.d.ts +1 -1
  431. package/dist/substrates/e2b/sandbox.js +1 -1
  432. package/dist/substrates/e2b/sdk.d.ts +11 -11
  433. package/dist/substrates/e2b/sdk.js +6 -6
  434. package/dist/tui/actions.d.ts +1 -1
  435. package/dist/tui/actions.js +13 -13
  436. package/dist/tui/contract.d.ts +16 -16
  437. package/dist/tui/contract.js +10 -10
  438. package/dist/tui/launch.d.ts +4 -4
  439. package/dist/tui/launch.js +18 -19
  440. package/dist/tui/project.js +5 -5
  441. package/dist/tui-app.js +82 -82
  442. package/dist/verify/actor.d.ts +8 -8
  443. package/dist/verify/actor.js +36 -36
  444. package/dist/verify/artifacts.d.ts +2 -2
  445. package/dist/verify/artifacts.js +3 -3
  446. package/dist/verify/context-growth.d.ts +9 -0
  447. package/dist/verify/context-growth.js +62 -0
  448. package/dist/verify/costs.d.ts +6 -6
  449. package/dist/verify/costs.js +8 -8
  450. package/dist/verify/shared-world-concurrent.d.ts +2 -2
  451. package/dist/verify/shared-world-concurrent.js +79 -76
  452. package/dist/verify/shared-world.d.ts +2 -2
  453. package/dist/verify/shared-world.js +16 -16
  454. package/dist/verify/subject.d.ts +4 -4
  455. package/dist/verify/subject.js +18 -18
  456. package/dist/verify/verify.js +92 -43
  457. package/docs/README.md +25 -32
  458. package/docs/architecture/actor-contract.md +56 -87
  459. package/docs/architecture/desktop-sessions.md +7 -7
  460. package/docs/architecture/external-public-shared-world.md +61 -59
  461. package/docs/architecture/github-feedback-loop.md +1 -4
  462. package/docs/architecture/guest-desktop.md +2 -2
  463. package/docs/architecture/observer.md +34 -34
  464. package/docs/architecture/restricted-codex-analysis.md +34 -28
  465. package/docs/architecture/serve.md +34 -37
  466. package/docs/architecture/state-driven-executor.md +55 -58
  467. package/docs/architecture/task-protocol-support.md +5 -5
  468. package/docs/architecture/terminal-product-route.md +67 -107
  469. package/docs/contracts/README.md +24 -0
  470. package/docs/contracts/adapter-admission.md +3 -3
  471. package/docs/contracts/adapter-fixtures.md +2 -5
  472. package/docs/contracts/core.md +1 -3
  473. package/docs/contracts/errors.md +62 -0
  474. package/docs/contracts/feedback.md +8 -9
  475. package/docs/contracts/policy.md +7 -12
  476. package/docs/contracts/run-bundle.md +45 -44
  477. package/docs/contracts/schemas.md +421 -362
  478. package/docs/contracts/study-analysis.md +3 -3
  479. package/docs/contracts/study-costs.md +11 -7
  480. package/docs/decisions/0001-run-bundle-is-the-source-of-truth.md +1 -1
  481. package/docs/decisions/0002-observer-is-one-self-contained-file.md +2 -2
  482. package/docs/decisions/0003-contained-paths-and-cleanup-authority.md +3 -3
  483. package/docs/principles/actor-fidelity.md +4 -4
  484. package/docs/principles/engineering.md +3 -3
  485. package/docs/principles/invariants-and-defaults.md +38 -38
  486. package/docs/principles/self-driving-harness.md +1 -5
  487. package/docs/principles/three-roles.md +1 -1
  488. package/docs/product/automatic-analysis.md +7 -7
  489. package/examples/participant/README.md +5 -5
  490. package/examples/participant/run.mjs +11 -10
  491. package/examples/scorer/README.md +3 -3
  492. package/examples/scorer/run.mjs +11 -12
  493. package/package.json +16 -17
  494. package/skills/humanish/SKILL.md +60 -58
  495. package/skills/humanish/agents/openai.yaml +1 -1
  496. package/AGENTS.md +0 -99
  497. package/CONTRIBUTING.md +0 -148
  498. package/dist/actors/codex/qualified-versions.d.ts +0 -72
  499. package/dist/actors/codex/qualified-versions.js +0 -132
  500. package/dist/cli/commands/lab.d.ts +0 -3
  501. package/dist/cli/commands/lab.js +0 -199
  502. package/dist/cli/renamed-options.d.ts +0 -11
  503. package/dist/cli/renamed-options.js +0 -18
  504. package/dist/observer/static.d.ts +0 -39
  505. package/dist/observer/static.js +0 -369
  506. package/docs/architecture/comms-inbox.md +0 -122
  507. package/docs/architecture/desktop-recording.md +0 -80
  508. package/docs/architecture/local-browser-runtime.md +0 -178
  509. package/docs/architecture/observer-review.md +0 -144
  510. package/docs/architecture/participant-media.md +0 -90
  511. package/docs/architecture/project-layout.md +0 -62
  512. package/docs/architecture/real-email-receiving.md +0 -136
  513. package/docs/assets/humanish-drawdb-hero.png +0 -0
  514. package/docs/assets/humanish-observer-hero.png +0 -0
  515. package/docs/goals/current.md +0 -207
  516. package/docs/product/lobby-trivia-3player-external-public.md +0 -77
  517. package/docs/product/open-source-install-experience.md +0 -240
  518. package/docs/ramp/README.md +0 -295
  519. package/docs/release/open-source-readiness.md +0 -222
  520. package/docs/release/public-readiness-standard.md +0 -210
  521. package/docs/roadmap/world-class-open-source-v0.md +0 -311
@@ -1,12 +1,12 @@
1
1
  import { selfReportedBlocker } from "../../run/judge.js";
2
- // "can't" followed by a PERCEPTION verb describes what the screen showed, not an inability to
2
+ // "can't" followed by a perception verb describes what the screen showed, not an inability to
3
3
  // proceed: "the canvas truncates it so you can't even read the whole thing", "I can't tell from
4
4
  // the screen whether the rename is persisted", "so I could not read its full description". Five
5
5
  // of five completed live runs on 2026-09-01 (two on drawDB, three on the planted benchmark app)
6
6
  // were refused as "not a credible pass" on exactly these sentences, every one a defect report
7
- // written AFTER the participant reached the goal. The more precisely a participant describes a
8
- // display defect, the more likely the scan was to refuse the run — the incentive inversion #453
9
- // fixed for resolved arcs, back in a new shape. "could not complete", "could not connect",
7
+ // written after the participant reached the goal. The more precisely a participant describes a
8
+ // display defect, the more likely the scan was to refuse the run: the incentive inversion the
9
+ // resolved-arc rule fixed, back in a new shape. "could not complete", "could not connect",
10
10
  // "unable to get focus" still count: those name an inability to act.
11
11
  const PERCEPTION_AFTER_MODAL = /\b(can'?t|cannot|could ?not|couldn'?t|unable to|wasn'?t able to)\s+(even\s+|quite\s+|really\s+|fully\s+)?(read|see|tell|view|make out|verify|confirm|be sure|be certain|judge|know)\b/g;
12
12
  function hasBlockerLanguage(text) {
@@ -15,17 +15,17 @@ function hasBlockerLanguage(text) {
15
15
  /\berror[:.]/.test(text) ||
16
16
  /what would you like me to do|please tell me|need (the )?(task|credentials|instructions)/.test(text));
17
17
  }
18
- /** The friction scan (inclusive): does the narrative report ANY blocker-shaped language,
18
+ /** The friction scan (inclusive): does the narrative report any blocker-shaped language,
19
19
  * resolved or not? Feeds the participants `reportedFriction` tally and feedback candidates. */
20
- // Report-shaped language: what a participant writes when it finished AND has something to say.
20
+ // Report-shaped language: what a participant writes when it finished and has something to say.
21
21
  // Every one of the day's eleven drawDB reports (2026-09-01) opened a section "What confused me"
22
22
  // or "Accessibility defects:"; none contained a blocker word, so none became a feedback candidate
23
23
  // and a participant that had just replicated a keyboard-accessibility defect three times drafted "Live
24
- // study completed without a participant-reported finding". Friction is the INCLUSIVE scan; a
24
+ // study completed without a participant-reported finding". Friction is the inclusive scan; a
25
25
  // false positive here adds a candidate a person then reads, which is the cheap direction.
26
26
  const REPORTED_DEFECT_LANGUAGE = /\b(defects?|bugs?|accessibilit(y|ies)|inaccessible|not (keyboard|screen.?reader)[- ]?accessible|confus(ed|ing)|hesitat(ed|ion)|unexpected(ly)?|unclear|hard to (find|tell|see|read|reach)|no (visible )?focus|overlap(ped|ping|s)?|truncat(ed|es|ion)|cut off|did nothing|nothing happened|no effect)\b/;
27
- // The friction scan's own negations (#614). "Nothing was confusing", "no defects", "not unclear"
28
- // are what a participant writes when it has NOTHING to report, and until 2026-09-03 each of them
27
+ // The friction scan's own negations. "Nothing was confusing", "no defects", "not unclear"
28
+ // are what a participant writes when it has nothing to report, and until 2026-09-03 each of them
29
29
  // counted as reported friction and became a feedback candidate whose "actual" was a sentence
30
30
  // reporting no problem. Only the report-shaped adjectives are negatable here: "no visible focus",
31
31
  // "not keyboard-accessible" and "did nothing" are defects and stay.
@@ -80,25 +80,25 @@ function interimMessageReportsFriction(message) {
80
80
  });
81
81
  }
82
82
  /** The verdict scan (strict): like the friction scan, but resolved-arc segments are stripped
83
- * first — failure narration the participant itself reports as overcome is friction on the
84
- * road, not a blocker at the destination (#453). */
83
+ * first: failure narration the participant itself reports as overcome counts as friction and
84
+ * never as a blocker. */
85
85
  function completionReasonBlocksVerdict(reason) {
86
- // Perception phrases are stripped for the VERDICT only: "I could not read the full description"
86
+ // Perception phrases are stripped for the verdict only: "I could not read the full description"
87
87
  // is friction worth a tally count and a feedback candidate (the friction scan above keeps it),
88
88
  // and it is not a reason to refuse the pass.
89
89
  return hasBlockerLanguage(stripResolvedArcSegments(stripQuotedSpans(stripNegatedNonBlockerPhrases(reason.toLowerCase()))).replace(PERCEPTION_AFTER_MODAL, ""));
90
90
  }
91
91
  // A failure segment counts as a resolved arc when the recovery is self-reported either in the
92
- // SAME segment ("the import failed but then went through") or — the common report shape — in the
93
- // immediately FOLLOWING segment as a retry/alternative that succeeded ("my first import failed
92
+ // same segment ("the import failed but then went through") or, in the common report shape, in the
93
+ // immediately following segment as a retry/alternative that succeeded ("my first import failed
94
94
  // with a parser error. A simpler SQL import succeeded."). The lookahead demands the retry flavor
95
95
  // on purpose: unrelated praise ("Separately, the search box worked") must never launder an
96
96
  // unresolved failure. "Login failed so I gave up" has no recovery anywhere and stays a blocker.
97
- // (#453 — the run-1 false negative: a defect report after demonstrated success failed the participant,
97
+ // (Without this, a defect report after demonstrated success failed the participant:
98
98
  // an incentive inversion against exactly the participant behavior a study wants most.)
99
99
  const RESOLUTION_TERMS = /\b(succeed(?:ed|s)?|success(?:ful|fully)?|worked|works around|then worked|now works?|resolved|fixed|recovered|got it working|went through)\b/;
100
100
  const RETRY_RESOLUTION = /\b(simpler|simplified|retry(?:ing)?|retried|second (?:attempt|try)|another (?:attempt|try|approach)|different (?:approach|way|route)|instead|then|eventually|after that)\b[^.!?\n]{0,80}\b(succeed(?:ed|s)?|success(?:ful|fully)?|worked|went through|completed|passed)\b/;
101
- /** Drop sentence/bullet segments whose failure language is part of a self-reported RESOLVED arc. */
101
+ /** Drop sentence/bullet segments whose failure language is part of a self-reported resolved arc. */
102
102
  function stripResolvedArcSegments(text) {
103
103
  const segments = text.split(/(?<=[.!?])\s+|\n+/);
104
104
  return segments
@@ -112,15 +112,15 @@ function stripResolvedArcSegments(text) {
112
112
  })
113
113
  .join(" ");
114
114
  }
115
- // Negations that DESCRIBE a defect rather than deny one. Kept out of every clause drop below.
115
+ // Negations that describe a defect rather than deny one. Kept out of every clause drop below.
116
116
  const DEFECT_SHAPED_NEGATION = /\bno\s+(?:visible\s+)?focus\b|\bno\s+(?:keyboard|screen.?reader)[- ]?(?:access|path|route|way|alternative|equivalent)|\bnot\s+(?:keyboard|screen.?reader)[- ]?accessible\b|\bno\s+(?:effect|feedback|response)\b|\b(?:did|does)\s+nothing\b|\bnothing\s+happened\b/;
117
117
  function stripNegatedNonBlockerPhrases(text) {
118
118
  return (text
119
- // FIRST, before the narrower rules eat the "no blockers" and leave "encountered ... error"
119
+ // First, before the narrower rules eat the "no blockers" and leave "encountered ... error"
120
120
  // behind: "I encountered no blockers or unclear error output." refused a clean passing run on
121
121
  // 2026-09-01. A verb of encounter followed by "no" negates the whole clause, so drop the clause.
122
- // ... unless the clause names a DEFECT: "the delete control had no visible focus" is a
123
- // finding, and the verb it happens to use must not decide whether it counts (#622).
122
+ // ... unless the clause names a defect: "the delete control had no visible focus" is a
123
+ // finding, and the verb it happens to use must not decide whether it counts.
124
124
  .replace(/\b(?:encountered|hit|saw|found|met|had|got|ran into)\s+no\s+[^.!?\n]*/g, (clause) => (DEFECT_SHAPED_NEGATION.test(clause) ? clause : " "))
125
125
  .replace(/\bno\s+(?:real\s+|remaining\s+|actual\s+)?(?:blocker|blockers|blocking issue|blocking issues|error|errors|failure|failures)\s+(?:was\s+|were\s+)?(?:encountered|observed|found|hit|seen|reported|detected)\b/g, "")
126
126
  .replace(/\bwithout\s+(?:a\s+|any\s+)?(?:real\s+|remaining\s+|actual\s+)?(?:blocker|blockers|blocking issue|blocking issues|error|errors|failure|failures)\b/g, "")
@@ -134,9 +134,9 @@ function stripNegatedNonBlockerPhrases(text) {
134
134
  }
135
135
  /**
136
136
  * Remove double-quoted spans and markdown blockquote lines before the blocker scan, so a persona
137
- * that faithfully QUOTES the subject app's own copy (e.g. a banner reading "cannot be undone") is
138
- * not misread as the actor reporting its OWN blocker. Only double quotes (straight and smart) and
139
- * `>` blockquotes are stripped — never single quotes, which would mangle contractions like `can't`.
137
+ * that faithfully quotes the subject app's own copy (e.g. a banner reading "cannot be undone") is
138
+ * not misread as the actor reporting its own blocker. Only double quotes (straight and smart) and
139
+ * `>` blockquotes are stripped, never single quotes, which would mangle contractions like `can't`.
140
140
  */
141
141
  function stripQuotedSpans(text) {
142
142
  return text
@@ -148,15 +148,15 @@ function traceHasStopWhenMatch(session) {
148
148
  return session.trace.items.some((item) => item.kind === "notice" &&
149
149
  item.status === "matched" &&
150
150
  // A dwell window that ended the session (then: stop) is the same class of harness-owned,
151
- // structured completion as a matched stopWhen (#510).
151
+ // structured completion as a matched stopWhen.
152
152
  (item.title.startsWith("stopWhen matched") || item.title === "dwell window complete"));
153
153
  }
154
154
  /**
155
- * A goal_satisfied participant counts as a self-reported blocker ONLY when its final narrative contradicts
156
- * the goal AND the run's own stop predicate did NOT fire. A matched stopWhen is independent,
157
- * structured completion evidence, so it overrides a text scan of the free-form narrative — which can
158
- * otherwise trip on the subject app's OWN quoted copy (e.g. a relayed "cannot be undone" banner).
159
- * Resolved-arc segments never block the verdict (#453). Returns the offending reason, or undefined
155
+ * A goal_satisfied participant counts as a self-reported blocker only when its final narrative contradicts
156
+ * the goal and the run's own stop predicate did not fire. A matched stopWhen is independent,
157
+ * structured completion evidence, so it overrides a text scan of the free-form narrative, which can
158
+ * otherwise trip on the subject app's own quoted copy (e.g. a relayed "cannot be undone" banner).
159
+ * Resolved-arc segments never block the verdict. Returns the offending reason, or undefined
160
160
  * when the participant is a clean pass. Exported for testing.
161
161
  */
162
162
  export function resolveSelfReportedBlocker(session) {
@@ -187,10 +187,10 @@ export function sessionEnding(session) {
187
187
  };
188
188
  }
189
189
  /**
190
- * Friction is independent of how a completed session ended (#657). Read the participant's
190
+ * Friction is independent of how a completed session ended. Read the participant's
191
191
  * redacted messages, including earlier reports, rather than the harness-owned reason that
192
192
  * stopWhen/dwell writes. Reasoning, observations, and notices are not participant reports.
193
- * Resolved arcs still count (#453); quoted copy and negated reports still do not. This read
193
+ * Resolved arcs still count; quoted copy and negated reports still do not. This read
194
194
  * never changes the verdict. Exported for testing.
195
195
  */
196
196
  export function resolveSelfReportedFriction(session) {
@@ -106,7 +106,7 @@ export declare function admitCuaRun(plan: ComputerUsePlan, input: ComputerUseRun
106
106
  result: CuaActorLabResult;
107
107
  };
108
108
  descriptor: CuaActorDescriptor;
109
- runSession: (options: import("../../actors/computer-use/actor.js").CuaActorSessionOptions) => Promise<import("../../index.js").CuaLoopResult>;
109
+ runSession: (options: import("../../actors/computer-use/actor.js").CuaActorSessionOptions) => Promise<import("../../index.js").ComputerUseLoopResult>;
110
110
  externalCommsConfig: LabCommsExternal | undefined;
111
111
  externalCommsEmail: LabCommsEmail | undefined;
112
112
  participantRuns: DesktopParticipantRun[];
@@ -17,13 +17,14 @@ import { e2bRequestTimeoutMs } from "../../substrates/e2b/lifetime.js";
17
17
  import { liveCuaRejection } from "./preflight.js";
18
18
  import { cuaDescriptorOf, declaredAppUrl, plannedAppUrl } from "./plan.js";
19
19
  import { trackRuntimeStreams } from "./live-flush.js";
20
- import { participantOf, phaseEvent, planEvent } from "../../lab/run-lab-events.js";
20
+ import { phaseEvent, planEvent } from "../../lab/run-lab-events.js";
21
21
  import { defaultSubjectPhaseSink } from "../../subject/steps.js";
22
22
  import {} from "./bundle.js";
23
23
  import { packRunLocalTree } from "./local-tree-pack.js";
24
24
  import { projectParticipantSubjects, subjectProvenanceArg } from "./subject-projection.js";
25
- import { CUA_ACTOR_LAB_SCHEMA, participantSubjectEnv, } from "./types.js";
25
+ import { participantSubjectEnv, } from "./types.js";
26
26
  import { labPersonaIds } from "../../lab/persona-resolve.js";
27
+ import { studyResultIdentity } from "../../run/study-result.js";
27
28
  /** The physical project, bound before any caller hook runs. */
28
29
  async function bindProject(cwd) {
29
30
  // Capture the physical project before reading or invoking any caller hook. A supported
@@ -43,10 +44,9 @@ export async function refuseCuaLab(options, refusal) {
43
44
  if (refusal.stage === "after-personas")
44
45
  await compileParticipantPersonas(projectRoot, labPersonaIds(config));
45
46
  return {
46
- schema: CUA_ACTOR_LAB_SCHEMA,
47
+ ...studyResultIdentity("computer-use", config.id),
47
48
  ok: false,
48
49
  cwd: projectRoot.physicalPath,
49
- labId: config.id,
50
50
  actor: refusal.actor ?? config.actors[0]?.type ?? "",
51
51
  appUrl: declaredAppUrl(config),
52
52
  dryRun,
@@ -74,10 +74,9 @@ export async function admitCuaRun(plan, input, config) {
74
74
  const appUrl = plannedAppUrl(subject);
75
75
  const subjectEnvNames = [...participantSubjectEnv(subject)];
76
76
  const fail = (code, message, actorLabel) => ({
77
- schema: CUA_ACTOR_LAB_SCHEMA,
77
+ ...studyResultIdentity("computer-use", plan.labId),
78
78
  ok: false,
79
79
  cwd,
80
- labId: plan.labId,
81
80
  actor: actorLabel ?? plan.actor,
82
81
  appUrl,
83
82
  dryRun,
@@ -96,7 +95,7 @@ export async function admitCuaRun(plan, input, config) {
96
95
  if (config.subject.source === "app-url" &&
97
96
  config.execution?.target === "local" &&
98
97
  input.localVm === undefined)
99
- return refuse("HUMANISH_CUA_LAB_LOCAL_DESKTOP_MISSING", "An app-url lab with execution.target: local needs a local desktop. runLab starts one; a direct route call or an in-process executor does not.");
98
+ return refuse("HUMANISH_COMPUTER_USE_LOCAL_DESKTOP_MISSING", "An app-url lab with execution.target: local needs a local desktop. runLab starts one; a direct route call or an in-process executor does not.");
100
99
  const descriptor = cuaDescriptorOf(plan.actor);
101
100
  const baseRunSession = seams.runSession ?? descriptor.runSession;
102
101
  // A local VM study's sessions abort on its signal.
@@ -104,11 +103,11 @@ export async function admitCuaRun(plan, input, config) {
104
103
  const runSession = localVmSignal === undefined
105
104
  ? baseRunSession
106
105
  : (options) => baseRunSession({ ...options, signal: localVmSignal });
107
- // Adopter-hosted comms plane on the app-url route (#380): humanish provisions no subject here,
108
- // so it cannot host a catch — the OPERATOR runs one, and humanish still does every other part
106
+ // Adopter-hosted comms plane on the app-url route: humanish provisions no subject here,
107
+ // so it cannot host a catch. The operator runs one, and humanish still does every other part
109
108
  // of the funnel: tells each persona its address and inbox URL, drains the catch over HTTP after
110
109
  // the participants, and writes the same digest-only evidence. Declaring `external` previously did
111
- // nothing on this route (and, per #387, on every other) while its docs said otherwise.
110
+ // nothing on this route (or on any other) while its docs said otherwise.
112
111
  const comms = plan.residual.comms;
113
112
  const externalCommsConfig = subject.kind !== "clone" && subject.kind !== "local-tree" && !inProcess
114
113
  ? comms?.email?.external
@@ -120,7 +119,7 @@ export async function admitCuaRun(plan, input, config) {
120
119
  }
121
120
  const { participantRuns, participantPlan, rerunLineage } = participants;
122
121
  const participantCount = participantRuns.length;
123
- // Pre-flight plan: BEFORE any sandbox or provider call (dry-run AND live). onEvent gets it for
122
+ // Pre-flight plan: before any sandbox or provider call (dry-run and live). onEvent gets it for
124
123
  // every N; the stderr table prints for fan-out (N>1) so single-participant runs stay as quiet as they
125
124
  // always were.
126
125
  if (participantCount > 1) {
@@ -141,7 +140,7 @@ export async function admitCuaRun(plan, input, config) {
141
140
  sanitizeParticipantRuns(participantRuns, scrubKnownValues);
142
141
  const redactRepoLabel = plan.residual.policies?.redactRepos ?? subjectEnvNames.includes("GITHUB_TOKEN");
143
142
  const publicRepo = subject.kind === "clone" ? (redactRepoLabel ? "repo-01" : subject.repo) : undefined;
144
- // Key-gating is route-aware: the in-process route uses the caller's OWN model + executor, and
143
+ // Key-gating is route-aware: the in-process route uses the caller's own model + executor, and
145
144
  // the local-agent route uses a CLI the operator has already signed in to.
146
145
  if (!dryRun && !inProcess) {
147
146
  const rejection = await liveCuaRejection({
@@ -154,8 +153,8 @@ export async function admitCuaRun(plan, input, config) {
154
153
  if (rejection)
155
154
  return refuse(rejection.code, rejection.message, descriptor.id);
156
155
  }
157
- // Pack the working tree ONCE per run, on the host, BEFORE any sandbox or provider call: every
158
- // fan-out participant below uploads this SAME archive, so one archiveSha256 describes every
156
+ // Pack the working tree once per run, on the host, before any sandbox or provider call: every
157
+ // fan-out participant below uploads this same archive, so one archiveSha256 describes every
159
158
  // participant's digest. Dry-run packs nothing (no fs side effects; the contract bundle carries no
160
159
  // archiveSha256). A packing failure fails the run closed here, before any sandbox is
161
160
  // created and before the run directory exists.
@@ -168,7 +167,7 @@ export async function admitCuaRun(plan, input, config) {
168
167
  localTreeArchiveBuffer = packed.buffer;
169
168
  }
170
169
  catch (error) {
171
- return refuse("HUMANISH_CUA_LAB_SUBJECT_INVALID", `local-tree packing failed: ${redactText(scrubKnownValues(toErrorMessage(error)))}`, descriptor.id);
170
+ return refuse("HUMANISH_COMPUTER_USE_SUBJECT_INVALID", `local-tree packing failed: ${redactText(scrubKnownValues(toErrorMessage(error)))}`, descriptor.id);
172
171
  }
173
172
  }
174
173
  return {
@@ -229,7 +228,7 @@ export async function startCuaRun(plan, input, admitted, scope) {
229
228
  humanishSource: "present",
230
229
  packageName: "humanish",
231
230
  });
232
- // Live-trace flush seam (#441): runLabParticipants fills it when a live run has an in-progress bundle
231
+ // Live-trace flush seam: runLabParticipants fills it when a live run has an in-progress bundle
233
232
  // to grow; participants call it through deps.onTrace. It exists before deps so deps can reference it as
234
233
  // a stable indirection.
235
234
  const liveTrace = {};
@@ -334,7 +333,7 @@ function cuaParticipantDeps(plan, input, admitted, run) {
334
333
  redactScreenshots,
335
334
  scrubKnownValues,
336
335
  runSession,
337
- // The study-level ledger exists once per RUN, shared by every participant (#299). Dry runs never
336
+ // The study-level ledger exists once per run, shared by every participant. Dry runs never
338
337
  // spend, so they carry none.
339
338
  ...(dryRun || plan.caps.maxTotalUsd === undefined
340
339
  ? {}
@@ -374,7 +373,7 @@ function subjectPhaseReporter(input) {
374
373
  const sink = input.deps?.subjectPhaseSink ?? defaultSubjectPhaseSink;
375
374
  return (event, participant) => {
376
375
  sink(event, participant);
377
- input.emit?.(phaseEvent(event, { kind: "participant", participant: participantOf(participant) }));
376
+ input.emit?.(phaseEvent(event, { kind: "participant", participant }));
378
377
  };
379
378
  }
380
379
  function makeCuaRunId() {
@@ -49,15 +49,15 @@ export declare function buildSingleParticipantBundle(args: {
49
49
  /**
50
50
  * Capture-time screenshot policy ("blurred" when policies.redactScreenshots, else "raw").
51
51
  * When a session ran, its trace's `redaction.screenshots` is the evidence-of-record and
52
- * wins; this fallback keeps labels honest for frames written before a mid-session failure
53
- * (no trace exists to testify then). Defaults to "raw" — the engine default.
52
+ * wins; this fallback labels the frames written before a mid-session failure
53
+ * (no trace exists to testify then). Defaults to "raw", the engine default.
54
54
  */
55
55
  captureRedaction?: "raw" | "blurred";
56
56
  session?: CuaLoopResult;
57
57
  sessionError?: string;
58
58
  /**
59
- * The route's own credibility read of a goal_satisfied session (#476). The actor's status is
60
- * evidence of what it CLAIMED; whether the harness counts the claim is decided by the route
59
+ * The route's own credibility read of a goal_satisfied session. The actor's status is
60
+ * evidence of what it claimed; whether the harness counts the claim is decided by the route
61
61
  * (zero engagement, a final message that describes a blocker). The review has to say the same
62
62
  * thing the participant's exit code says, or the durable bundle reports a participant reaching the
63
63
  * goal on a run the harness refused to count.
@@ -72,9 +72,9 @@ export declare function buildSingleParticipantBundle(args: {
72
72
  * + digests only, never values or command text), including the subject's state story. */
73
73
  subjectProvenance?: CuaSubjectProvenanceArg;
74
74
  /**
75
- * Entry kind for the non-clone subject.declared event (invariant 5 — declare what the subject
76
- * WAS). "local-app": an already-running LOCAL dev server driven in-process, un-pinnable —
77
- * declared honestly as caller-provisioned/unpinned with no E2B. Absent: a plain app-url entry.
75
+ * Entry kind for the non-clone subject.declared event, which declares what the subject
76
+ * was. "local-app": an already-running local dev server driven in-process, un-pinnable, and
77
+ * declared as caller-provisioned/unpinned with no E2B. Absent: a plain app-url entry.
78
78
  */
79
79
  entryKind?: "local-app";
80
80
  /** The custom E2B desktop template (image) this participant launched on, when configured (provenance). */
@@ -24,7 +24,7 @@ function browserPlace(args) {
24
24
  return "in a hosted desktop browser";
25
25
  }
26
26
  }
27
- /** Run-level cost ESTIMATE (advisory; omitted when nothing was priced and no sandbox ran). */
27
+ /** Run-level cost estimate (advisory; omitted when nothing was priced and no sandbox ran). */
28
28
  function runCost(args) {
29
29
  return buildRunCostSummary({
30
30
  participants: args.session
@@ -52,15 +52,15 @@ function participantView(args, publicAppUrl) {
52
52
  ? "Live computer-use session is running; stream auth URL is available only through the attached Observer server."
53
53
  : (args.session?.reason ??
54
54
  args.sessionError ??
55
- "Contract bundle only: dry-run produced the evidence shape without launching a desktop or spending provider tokens.");
55
+ "Dry run: the evidence shape was written without launching a desktop or spending provider tokens.");
56
56
  const lastScreenshot = args.screenshots[args.screenshots.length - 1];
57
57
  const desktopGeometry = args.desktopRoute === false
58
58
  ? undefined
59
59
  : (args.desktopGeometry ?? {
60
60
  screen: { requested: { width: args.resolution[0], height: args.resolution[1] } },
61
61
  });
62
- // Honest labels (invariant 6: claims match mechanism): every screenshot label names the
63
- // run's ACTUAL mode. The session trace is the evidence-of-record; the capture policy covers
62
+ // Claims match mechanism: every screenshot label names the
63
+ // run's actual mode. The session trace is the evidence-of-record; the capture policy covers
64
64
  // frames written before a mid-session failure produced a trace.
65
65
  const traceScreenshotMode = args.session?.trace.redaction.screenshots;
66
66
  const screenshotMode = traceScreenshotMode === "raw" || traceScreenshotMode === "blurred"
@@ -92,7 +92,7 @@ function singleSimulation(args, view) {
92
92
  ? `Computer-use actor (${args.actorId}) is driving the subject app ${browserPlace(args)}.`
93
93
  : args.sessionError !== undefined
94
94
  ? `Computer-use lab failed before a terminal session verdict: ${args.sessionError}`
95
- : `Contract participant for the computer-use actor (${args.actorId}) against ${publicAppUrl}.`,
95
+ : `Computer-use actor (${args.actorId}) against ${publicAppUrl}; no session ran.`,
96
96
  startedAt: args.run.createdAt,
97
97
  updatedAt: args.run.createdAt,
98
98
  });
@@ -107,13 +107,13 @@ function singleStream(args, view) {
107
107
  ...(args.surface === undefined ? {} : { surface: args.surface }),
108
108
  ...(args.caseGroup === undefined ? {} : { caseGroup: args.caseGroup }),
109
109
  kind: "browser",
110
- label: `CUA browser — ${args.labId}`,
110
+ label: `${args.participantId ?? "lane-01"} · browser`,
111
111
  status,
112
112
  transport: "snapshot",
113
113
  updatedAt: args.run.createdAt,
114
114
  embed: lastScreenshot
115
- ? { kind: "screenshot", url: lastScreenshot, title: `CUA desktop (${screenshotMode})` }
116
- : { kind: "placeholder", title: "CUA desktop" },
115
+ ? { kind: "screenshot", url: lastScreenshot, title: `Desktop (${screenshotMode})` }
116
+ : { kind: "placeholder", title: "Desktop" },
117
117
  ...(desktopGeometry?.viewport === undefined
118
118
  ? {}
119
119
  : {
@@ -172,7 +172,7 @@ function singleEvents(args, view) {
172
172
  at: args.run.createdAt,
173
173
  level: "info",
174
174
  type: "cua-lab.subject.provenance",
175
- // HONEST WORDING: claim "cloned/packed and served" only when it actually happened.
175
+ // Claim "cloned/packed and served" only when it actually happened.
176
176
  message: `${subjectProvenanceMessage(args.subjectProvenance, publicAppUrl, args.dryRun, args.session !== undefined)} (subject env names: ${args.subjectProvenance.envNames.length > 0 ? args.subjectProvenance.envNames.join(", ") : "none"}; values never persisted); state: ${describeSubjectState(args.subjectProvenance.state, args.dryRun)}.`,
177
177
  })
178
178
  : participantEvent(SINGLE, {
@@ -180,13 +180,13 @@ function singleEvents(args, view) {
180
180
  at: args.run.createdAt,
181
181
  level: "info",
182
182
  type: "cua-lab.subject.declared",
183
- // Invariant 5: declare what the subject WAS, including the ABSENCE of a pin. A
184
- // local-app / in-process subject is an already-running LOCAL dev server the caller
185
- // provisioned; it cannot be commit-pinned, so its provenance is honestly UNPINNED and
183
+ // Declare what the subject was, including the absence of a pin. A
184
+ // local-app / in-process subject is an already-running local dev server the caller
185
+ // provisioned; it cannot be commit-pinned, so its provenance is unpinned and
186
186
  // no E2B desktop was created. A plain app-url entry runs inside the desktop sandbox, or,
187
187
  // on the local VM, reaches the host's loopback from the VM's browser.
188
188
  message: args.entryKind === "local-app"
189
- ? `Subject app declared at ${publicAppUrl} (already-running LOCAL dev server driven in-process; NO clone, NO E2B desktop). Provenance: caller-provisioned and UNPINNED — a running dev server cannot be commit-pinned.`
189
+ ? `Subject app declared at ${publicAppUrl}: a running local dev server driven in this process, with no clone and no E2B desktop. Provenance: provided by the caller and unpinned, because a running dev server has no commit to pin.`
190
190
  : runnerSubstrate(args) === "local-desktop"
191
191
  ? `Subject app declared at ${publicAppUrl} (the host's loopback, opened from a browser on a local VM).`
192
192
  : `Subject app declared at ${publicAppUrl} (loopback inside the desktop sandbox).`,
@@ -220,12 +220,12 @@ function singleEvents(args, view) {
220
220
  at: args.run.createdAt,
221
221
  level: "info",
222
222
  type: "cua-lab.contract.ready",
223
- message: "Dry-run contract bundle ready; switch scenario.mode to live for a real desktop session.",
223
+ message: "Dry-run bundle ready; switch scenario.mode to live for a real desktop session.",
224
224
  }),
225
225
  ];
226
226
  const record = (event) => events.push(participantEvent(SINGLE, event));
227
227
  // Persisted phase trail (real boot timing, not just a coarse provenance sentence): one
228
- // RunEvent per COMPLETED phase boundary (started events never persist here; they carry no
228
+ // RunEvent per completed phase boundary (started events never persist here; they carry no
229
229
  // durationMs). ok:false phases warn rather than error, since the failing phase's own thrown
230
230
  // error already becomes the terminal cua-lab.session.error event above.
231
231
  let phaseEventSeq = 3;
@@ -251,17 +251,15 @@ function singleEvents(args, view) {
251
251
  }
252
252
  function singleReview(args, view, stream) {
253
253
  const { reason } = view;
254
- // A funnel with a denominator of one is still the funnel — and its absence stays honest: no
254
+ // A funnel with a denominator of one is still the funnel, and its absence stays recorded: no
255
255
  // declared protocol (or a dry run) means no `tasks` field, never an empty one.
256
256
  const singleRunTasks = args.inProgress !== true && args.session?.trace.taskFunnel !== undefined
257
257
  ? aggregateTaskFunnels([args.session.trace.taskFunnel])
258
258
  : undefined;
259
- // What happened to the participant, as the route judged it — the same rule the fan-out roll-up
260
- // applies (participantStatusForOutcome). Before #476 this read the actor's own status, so a
261
- // run the route refused as "not a credible pass" was written up as verdict pass, 1/1 reached
262
- // the goal, and every projection of the bundle (Observer tally, `runs`, the status index)
263
- // repeated it. Found on a real drawDB run whose participant wrote "Blocked after partial
264
- // completion".
259
+ // What happened to the participant, as the route judged it: the same rule the fan-out roll-up
260
+ // applies (participantStatus in src/run/judge.ts). Reading the actor's own status instead would write up
261
+ // a run the route refused as "not a credible pass" as verdict pass, 1/1 reached the goal, and
262
+ // every projection of the bundle (Observer tally, `runs`, the status index) would repeat it.
265
263
  const participantStatus = args.session === undefined
266
264
  ? undefined
267
265
  : participantStatusFor(args.session.status, args.credibility);
@@ -286,7 +284,7 @@ function singleReview(args, view, stream) {
286
284
  ? []
287
285
  : args.inProgress === true
288
286
  ? ["Live desktop session is still running."]
289
- : ["Live desktop session not yet run (dry-run contract only)."],
287
+ : ["Live desktop session not yet run (dry run only)."],
290
288
  }, [stream]);
291
289
  return review;
292
290
  }
@@ -314,14 +312,14 @@ export function buildSingleParticipantBundle(args) {
314
312
  persona: {
315
313
  id: args.persona.id,
316
314
  name: `Computer-use operator (${args.persona.id})`,
317
- source: `lab:${args.labId}`,
315
+ source: `study:${args.labId}`,
318
316
  sourceDigest: args.persona.promptDigest,
319
317
  },
320
318
  scenario: {
321
319
  id: `cua-${args.labId}`,
322
320
  title: args.labTitle ?? `Computer-use lab: ${args.labId}`,
323
321
  goal: redactText(args.mission),
324
- source: `lab:${args.labId}`,
322
+ source: `study:${args.labId}`,
325
323
  sourceDigest: args.persona.promptDigest,
326
324
  },
327
325
  lifecycle: [
@@ -337,7 +335,7 @@ export function buildSingleParticipantBundle(args) {
337
335
  redaction: {
338
336
  status: "passed",
339
337
  notes: traceScreenshotMode === "raw"
340
- ? "Typed text recorded as length only and reasoning/messages pass through text redaction. Screenshots are FULL-FIDELITY (raw), retained for local use — NOT redacted for publishing; set policies.redactScreenshots: true to blur a share-as-is bundle."
338
+ ? "Typed text is recorded as its length only, and reasoning and messages pass through text redaction. Screenshots are unblurred and kept for local use; they are not redacted for publishing. Set policies.redactScreenshots: true to blur screenshots in a bundle you plan to share."
341
339
  : traceScreenshotMode === "blurred"
342
340
  ? "Typed text recorded as length only and reasoning/messages pass through text redaction. Screenshots are blurred at capture (policies.redactScreenshots: true) for a share-as-is bundle."
343
341
  : args.screenshots.length > 0
@@ -346,8 +344,8 @@ export function buildSingleParticipantBundle(args) {
346
344
  },
347
345
  artifacts: bundleArtifacts(),
348
346
  review,
349
- // What the participant reported, when it reported anything (#392). Dry-run and in-progress
350
- // bundles carry none — there is no participant yet to quote.
347
+ // What the participant reported, when it reported anything. Dry-run and in-progress
348
+ // bundles carry none: there is no participant yet to quote.
351
349
  feedbackCandidates: args.dryRun || args.inProgress === true
352
350
  ? []
353
351
  : participantFeedbackCandidates({
@@ -378,8 +376,8 @@ export function buildSingleParticipantBundle(args) {
378
376
  ...(args.providerResources === undefined || args.providerResources.length === 0
379
377
  ? {}
380
378
  : { providerResources: args.providerResources }),
381
- // Structured subject provenance (invariant 5): code pin + state story. Uniform and
382
- // honest on app-url bundles too — the caller minted the URL, its state is the caller's.
379
+ // Structured subject provenance: code pin + state story. Uniform, and
380
+ // stated on app-url bundles too: the caller minted the URL, its state is the caller's.
383
381
  // CuaSubjectProvenanceArg's two variants (clone, local-tree) are already RunSubjectProvenance-
384
382
  // shaped, so no reconstruction is needed beyond the app-url fallback.
385
383
  subject: args.subjectProvenance ?? { source: "app-url", state: { provenance: "undeclared" } },
@@ -18,7 +18,7 @@ export declare function projectParticipantSubjects(args: {
18
18
  }): CuaSubjectProjection[];
19
19
  /**
20
20
  * Resolve the bundle's state marker from the declaration and what actually ran.
21
- * Precedence: external declared → "unpinned" (seed records, if any, stay attached — a
21
+ * Precedence: external declared → "unpinned" (seed records, if any, stay attached; a
22
22
  * migrated external DB is still unpinned overall); else seed declared → "seeded" only when
23
23
  * every declared step executed ok on a live run, otherwise "declared-not-run" (dry-run
24
24
  * contract bundles and failed live provisioning); no declaration → "undeclared".
@@ -36,7 +36,7 @@ export function projectParticipantSubjects(args) {
36
36
  }
37
37
  /**
38
38
  * Resolve the bundle's state marker from the declaration and what actually ran.
39
- * Precedence: external declared → "unpinned" (seed records, if any, stay attached — a
39
+ * Precedence: external declared → "unpinned" (seed records, if any, stay attached; a
40
40
  * migrated external DB is still unpinned overall); else seed declared → "seeded" only when
41
41
  * every declared step executed ok on a live run, otherwise "declared-not-run" (dry-run
42
42
  * contract bundles and failed live provisioning); no declaration → "undeclared".
@@ -48,8 +48,8 @@ export function resolveSubjectState(args) {
48
48
  }
49
49
  const declaredSeed = declared.seed ?? [];
50
50
  const external = declared.external ?? [];
51
- // Dry-run: nothing executes (no sandbox) — record the DECLARED recipe: name, phase, and
52
- // command digest only, with NO execution fields.
51
+ // Dry-run: nothing executes (no sandbox), so record the declared recipe: name, phase, and
52
+ // command digest only, with no execution fields.
53
53
  const seed = args.dryRun
54
54
  ? declaredSeed.map((step) => ({
55
55
  name: step.name,
@@ -74,8 +74,8 @@ export function resolveSubjectState(args) {
74
74
  ...(external.length > 0 ? { externalEnvNames: external } : {}),
75
75
  };
76
76
  }
77
- /** Build the per-participant subject projection (invariant 5). Local-tree participants all share
78
- * ONE host-packed archive, so every participant's projection carries the identical archiveSha256/
77
+ /** Build the per-participant subject projection. Local-tree participants all share
78
+ * one host-packed archive, so every participant's projection carries the identical archiveSha256/
79
79
  * commit/dirty (no divergence is possible, unlike the clone route's per-participant
80
80
  * in-sandbox commit). */
81
81
  function participantSubjectProjection(args) {
@@ -144,7 +144,7 @@ export function aggregateCuaSubject(args) {
144
144
  const unanimous = !dryRun && commits.length === participantCount && new Set(commits).size === 1;
145
145
  const warnings = !dryRun && participantCount > 1 && new Set(commits).size > 1
146
146
  ? [
147
- "Fan-out participants resolved DIVERGENT subject commits, so the top-level subject.commit is omitted; see each participant's provenance in result.lanes for its pinned commit.",
147
+ "Participants resolved different subject commits, so the top-level subject.commit is omitted; each participant's provenance in result.lanes has its pinned commit.",
148
148
  ]
149
149
  : [];
150
150
  return {