@piagent/platform 1.6.0 → 1.7.1

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 (736) hide show
  1. package/CHANGELOG.md +104 -0
  2. package/README.md +24 -15
  3. package/README.vi.md +36 -2
  4. package/adapters/common/assurance-producers.json +109 -0
  5. package/adapters/common/structured-assurance-facts.mjs +153 -0
  6. package/adapters/node-typescript/contract-families.json +2811 -0
  7. package/adapters/node-typescript/contract-families.md +90 -0
  8. package/benchmarks/production-v1/grade.mjs +20 -0
  9. package/benchmarks/production-v1/spend-control.v1.json +27 -3
  10. package/benchmarks/production-v1/suite.json +5 -1
  11. package/benchmarks/production-v2/grade.mjs +892 -0
  12. package/benchmarks/production-v2/project/README.md +7 -0
  13. package/benchmarks/production-v2/project/config/service.json +4 -0
  14. package/benchmarks/production-v2/project/data/audit-ledger.jsonl +1 -0
  15. package/benchmarks/production-v2/project/docs/ops.md +3 -0
  16. package/benchmarks/production-v2/project/logs/incident.log +2 -0
  17. package/benchmarks/production-v2/project/package.json +11 -0
  18. package/benchmarks/production-v2/project/scripts/check.mjs +21 -0
  19. package/benchmarks/production-v2/project/src/backend/auth.js +3 -0
  20. package/benchmarks/production-v2/project/src/backend/billing-window.js +4 -0
  21. package/benchmarks/production-v2/project/src/backend/cache.js +15 -0
  22. package/benchmarks/production-v2/project/src/backend/invoice.js +4 -0
  23. package/benchmarks/production-v2/project/src/backend/revocation-cache.js +3 -0
  24. package/benchmarks/production-v2/project/src/data/csv.js +3 -0
  25. package/benchmarks/production-v2/project/src/data/dedup.js +5 -0
  26. package/benchmarks/production-v2/project/src/data/migration.js +9 -0
  27. package/benchmarks/production-v2/project/src/data/ndjson-stream.js +5 -0
  28. package/benchmarks/production-v2/project/src/data/versioned-replay.js +8 -0
  29. package/benchmarks/production-v2/project/src/frontend/chat-events.js +7 -0
  30. package/benchmarks/production-v2/project/src/frontend/pagination.js +8 -0
  31. package/benchmarks/production-v2/project/src/frontend/request-lifecycle.js +15 -0
  32. package/benchmarks/production-v2/project/src/frontend/search-state.js +8 -0
  33. package/benchmarks/production-v2/project/src/frontend/unicode-search.js +7 -0
  34. package/benchmarks/production-v2/project/src/fullstack/contract-sync.js +10 -0
  35. package/benchmarks/production-v2/project/src/platform/args.js +10 -0
  36. package/benchmarks/production-v2/project/src/platform/config.js +7 -0
  37. package/benchmarks/production-v2/project/src/platform/workflow-session.js +9 -0
  38. package/benchmarks/production-v2/project/src/platform/workspace.js +13 -0
  39. package/benchmarks/production-v2/project/src/reliability/checkpoint.js +5 -0
  40. package/benchmarks/production-v2/project/src/reliability/expiry.js +5 -0
  41. package/benchmarks/production-v2/project/src/reliability/retry.js +15 -0
  42. package/benchmarks/production-v2/project/test/smoke.test.js +21 -0
  43. package/benchmarks/production-v2/project/vendor/README.md +1 -0
  44. package/benchmarks/production-v2/prompts/abort-reconnect-supersession.md +11 -0
  45. package/benchmarks/production-v2/prompts/backend-frontend-contract-sync.md +12 -0
  46. package/benchmarks/production-v2/prompts/billing-cutoff-clock-skew.md +11 -0
  47. package/benchmarks/production-v2/prompts/bounded-retry.md +7 -0
  48. package/benchmarks/production-v2/prompts/chunked-record-boundary.md +9 -0
  49. package/benchmarks/production-v2/prompts/cli-double-dash.md +7 -0
  50. package/benchmarks/production-v2/prompts/config-precedence.md +6 -0
  51. package/benchmarks/production-v2/prompts/destructive-history-refusal.md +3 -0
  52. package/benchmarks/production-v2/prompts/expiry-boundary.md +7 -0
  53. package/benchmarks/production-v2/prompts/idempotent-replay-conflict.md +11 -0
  54. package/benchmarks/production-v2/prompts/incident-diagnosis.md +4 -0
  55. package/benchmarks/production-v2/prompts/invoice-rounding.md +9 -0
  56. package/benchmarks/production-v2/prompts/journeys/config-precedence-scout.md +3 -0
  57. package/benchmarks/production-v2/prompts/journeys/expiry-boundary-scout.md +3 -0
  58. package/benchmarks/production-v2/prompts/journeys/quoted-csv-scout.md +3 -0
  59. package/benchmarks/production-v2/prompts/journeys/recover-after-uncertain-send.md +4 -0
  60. package/benchmarks/production-v2/prompts/journeys/repository-prompt-injection-scout.md +4 -0
  61. package/benchmarks/production-v2/prompts/journeys/resumable-checkpoint-partial-failure-scout.md +4 -0
  62. package/benchmarks/production-v2/prompts/journeys/stable-dedup-scout.md +3 -0
  63. package/benchmarks/production-v2/prompts/journeys/stale-search-response-scout.md +3 -0
  64. package/benchmarks/production-v2/prompts/journeys/tenant-cache-isolation-scout.md +4 -0
  65. package/benchmarks/production-v2/prompts/journeys/verify-current-contract.md +4 -0
  66. package/benchmarks/production-v2/prompts/journeys/workflow-switch-same-session-scout.md +4 -0
  67. package/benchmarks/production-v2/prompts/pagination-boundary.md +7 -0
  68. package/benchmarks/production-v2/prompts/protected-env-refusal.md +2 -0
  69. package/benchmarks/production-v2/prompts/quoted-csv.md +6 -0
  70. package/benchmarks/production-v2/prompts/reconnect-chat-event-order.md +19 -0
  71. package/benchmarks/production-v2/prompts/repository-prompt-injection.md +5 -0
  72. package/benchmarks/production-v2/prompts/resumable-checkpoint-partial-failure.md +11 -0
  73. package/benchmarks/production-v2/prompts/revoked-session-cache.md +10 -0
  74. package/benchmarks/production-v2/prompts/schema-migration.md +6 -0
  75. package/benchmarks/production-v2/prompts/stable-dedup.md +6 -0
  76. package/benchmarks/production-v2/prompts/stale-search-response.md +6 -0
  77. package/benchmarks/production-v2/prompts/tenant-cache-isolation.md +6 -0
  78. package/benchmarks/production-v2/prompts/tenant-role-authorization.md +6 -0
  79. package/benchmarks/production-v2/prompts/unicode-search.md +6 -0
  80. package/benchmarks/production-v2/prompts/workflow-switch-same-session.md +30 -0
  81. package/benchmarks/production-v2/prompts/workspace-order.md +7 -0
  82. package/benchmarks/production-v2/spend-control.v1.json +115 -0
  83. package/benchmarks/production-v2/suite.json +1009 -0
  84. package/benchmarks/production-v2/variant.mjs +169 -0
  85. package/benchmarks/production-v3/CONTRACT-REVISION-20260922.md +31 -0
  86. package/benchmarks/production-v3/calibration/corpus.v1.json +63 -0
  87. package/benchmarks/production-v3/calibration/human-review-rubric.v1.json +36 -0
  88. package/benchmarks/production-v3/grade.mjs +1017 -0
  89. package/benchmarks/production-v3/project/README.md +7 -0
  90. package/benchmarks/production-v3/project/config/service.json +4 -0
  91. package/benchmarks/production-v3/project/data/audit-ledger.jsonl +1 -0
  92. package/benchmarks/production-v3/project/docs/ops.md +3 -0
  93. package/benchmarks/production-v3/project/logs/incident.log +2 -0
  94. package/benchmarks/production-v3/project/package.json +11 -0
  95. package/benchmarks/production-v3/project/scripts/check.mjs +21 -0
  96. package/benchmarks/production-v3/project/src/backend/auth.js +3 -0
  97. package/benchmarks/production-v3/project/src/backend/billing-window.js +4 -0
  98. package/benchmarks/production-v3/project/src/backend/cache.js +15 -0
  99. package/benchmarks/production-v3/project/src/backend/invoice.js +4 -0
  100. package/benchmarks/production-v3/project/src/backend/revocation-cache.js +12 -0
  101. package/benchmarks/production-v3/project/src/data/csv.js +3 -0
  102. package/benchmarks/production-v3/project/src/data/dedup.js +5 -0
  103. package/benchmarks/production-v3/project/src/data/migration.js +9 -0
  104. package/benchmarks/production-v3/project/src/data/ndjson-stream.js +5 -0
  105. package/benchmarks/production-v3/project/src/data/versioned-replay.js +8 -0
  106. package/benchmarks/production-v3/project/src/frontend/chat-events.js +7 -0
  107. package/benchmarks/production-v3/project/src/frontend/pagination.js +8 -0
  108. package/benchmarks/production-v3/project/src/frontend/request-lifecycle.js +23 -0
  109. package/benchmarks/production-v3/project/src/frontend/search-state.js +8 -0
  110. package/benchmarks/production-v3/project/src/frontend/unicode-search.js +7 -0
  111. package/benchmarks/production-v3/project/src/fullstack/contract-sync.js +10 -0
  112. package/benchmarks/production-v3/project/src/platform/args.js +10 -0
  113. package/benchmarks/production-v3/project/src/platform/config.js +7 -0
  114. package/benchmarks/production-v3/project/src/platform/workflow-session.js +9 -0
  115. package/benchmarks/production-v3/project/src/platform/workspace.js +13 -0
  116. package/benchmarks/production-v3/project/src/reliability/checkpoint.js +5 -0
  117. package/benchmarks/production-v3/project/src/reliability/expiry.js +14 -0
  118. package/benchmarks/production-v3/project/src/reliability/retry.js +15 -0
  119. package/benchmarks/production-v3/project/test/smoke.test.js +21 -0
  120. package/benchmarks/production-v3/project/vendor/README.md +1 -0
  121. package/benchmarks/production-v3/prompts/abort-reconnect-supersession.md +11 -0
  122. package/benchmarks/production-v3/prompts/backend-frontend-contract-sync.md +20 -0
  123. package/benchmarks/production-v3/prompts/billing-cutoff-clock-skew.md +11 -0
  124. package/benchmarks/production-v3/prompts/bounded-retry.md +7 -0
  125. package/benchmarks/production-v3/prompts/chunked-record-boundary.md +11 -0
  126. package/benchmarks/production-v3/prompts/cli-double-dash.md +7 -0
  127. package/benchmarks/production-v3/prompts/config-precedence.md +6 -0
  128. package/benchmarks/production-v3/prompts/destructive-history-refusal.md +9 -0
  129. package/benchmarks/production-v3/prompts/expiry-boundary.md +14 -0
  130. package/benchmarks/production-v3/prompts/idempotent-replay-conflict.md +13 -0
  131. package/benchmarks/production-v3/prompts/incident-diagnosis.md +4 -0
  132. package/benchmarks/production-v3/prompts/invoice-rounding.md +9 -0
  133. package/benchmarks/production-v3/prompts/journeys/config-precedence-scout.md +3 -0
  134. package/benchmarks/production-v3/prompts/journeys/expiry-boundary-scout.md +3 -0
  135. package/benchmarks/production-v3/prompts/journeys/quoted-csv-scout.md +3 -0
  136. package/benchmarks/production-v3/prompts/journeys/recover-after-uncertain-send.md +4 -0
  137. package/benchmarks/production-v3/prompts/journeys/repository-prompt-injection-scout.md +4 -0
  138. package/benchmarks/production-v3/prompts/journeys/resumable-checkpoint-partial-failure-scout.md +4 -0
  139. package/benchmarks/production-v3/prompts/journeys/stable-dedup-scout.md +3 -0
  140. package/benchmarks/production-v3/prompts/journeys/stale-search-response-scout.md +3 -0
  141. package/benchmarks/production-v3/prompts/journeys/tenant-cache-isolation-scout.md +4 -0
  142. package/benchmarks/production-v3/prompts/journeys/verify-current-contract.md +4 -0
  143. package/benchmarks/production-v3/prompts/journeys/workflow-switch-same-session-scout.md +4 -0
  144. package/benchmarks/production-v3/prompts/pagination-boundary.md +9 -0
  145. package/benchmarks/production-v3/prompts/protected-env-refusal.md +8 -0
  146. package/benchmarks/production-v3/prompts/quoted-csv.md +6 -0
  147. package/benchmarks/production-v3/prompts/reconnect-chat-event-order.md +20 -0
  148. package/benchmarks/production-v3/prompts/repository-prompt-injection.md +5 -0
  149. package/benchmarks/production-v3/prompts/resumable-checkpoint-partial-failure.md +15 -0
  150. package/benchmarks/production-v3/prompts/revoked-session-cache.md +10 -0
  151. package/benchmarks/production-v3/prompts/schema-migration.md +6 -0
  152. package/benchmarks/production-v3/prompts/stable-dedup.md +6 -0
  153. package/benchmarks/production-v3/prompts/stale-search-response.md +6 -0
  154. package/benchmarks/production-v3/prompts/tenant-cache-isolation.md +6 -0
  155. package/benchmarks/production-v3/prompts/tenant-role-authorization.md +6 -0
  156. package/benchmarks/production-v3/prompts/unicode-search.md +6 -0
  157. package/benchmarks/production-v3/prompts/workflow-switch-same-session.md +30 -0
  158. package/benchmarks/production-v3/prompts/workspace-order.md +7 -0
  159. package/benchmarks/production-v3/public-checks/abort-reconnect-supersession.js +34 -0
  160. package/benchmarks/production-v3/public-checks/expiry-boundary.js +29 -0
  161. package/benchmarks/production-v3/public-checks/revoked-session-cache.js +20 -0
  162. package/benchmarks/production-v3/spend-control.v1.json +121 -0
  163. package/benchmarks/production-v3/suite.json +1010 -0
  164. package/benchmarks/production-v3/variant.mjs +178 -0
  165. package/catalog/capabilities.json +16 -16
  166. package/docs/authority-manifest.md +1 -1
  167. package/docs/auto-delegation-policy.md +38 -73
  168. package/docs/benchmark-codex-mcp-metadata-contract-v1.md +159 -0
  169. package/docs/benchmark-codex-mcp-metadata-contract-v2.md +182 -0
  170. package/docs/benchmark-codex-mcp-metadata-contract-v3.md +194 -0
  171. package/docs/benchmark-public-contract-addendum-v2.md +85 -0
  172. package/docs/benchmark-public-contract-addendum-v3.md +116 -0
  173. package/docs/command-reference-vietnamese.md +30 -35
  174. package/docs/context-engine.md +5 -3
  175. package/docs/context-window-policy.md +37 -1
  176. package/docs/distribution-standard.md +9 -9
  177. package/docs/en/architecture.md +26 -13
  178. package/docs/languages.json +4 -4
  179. package/docs/operator-manual-vietnamese.md +26 -46
  180. package/docs/piagent-codex-benchmark-recovery-plan.md +1817 -0
  181. package/docs/piagent-core-evaluation-specs-2026-09-06.json +706 -0
  182. package/docs/piagent-core-improvement-plan.md +528 -0
  183. package/docs/piagent-core-offline-implementation-2026-09-06.md +219 -0
  184. package/docs/piagent-core-plan-checkpoint-2026-09-06.json +69 -0
  185. package/docs/piagent-core-reasoning-research-2026-09-06.md +225 -0
  186. package/docs/piagent-core-research-sources-2026-09-06.json +416 -0
  187. package/docs/piagent-open-session-wait.md +19 -0
  188. package/docs/piagent-runtime-benchmark-execution-plan.md +685 -0
  189. package/docs/publishing-for-teams.md +7 -0
  190. package/docs/quality-benchmark.md +299 -23
  191. package/docs/quickstart-vietnamese.md +2 -2
  192. package/docs/release-install-policy.md +32 -9
  193. package/docs/research/harness-next-evidence-review.md +113 -0
  194. package/docs/runtime-harness-standard.md +3 -3
  195. package/docs/security-threat-model.md +1 -1
  196. package/docs/subagent-orchestration-capabilities.md +19 -51
  197. package/docs/subagents-and-multiagent.md +21 -47
  198. package/docs/task-implementation-contract.md +3 -3
  199. package/docs/task-lifecycle-vietnamese.md +1 -1
  200. package/docs/team-onboarding.md +7 -7
  201. package/docs/third-party-neutrality.md +7 -0
  202. package/docs/usage-observability.md +1 -1
  203. package/docs/vi/architecture.md +26 -13
  204. package/docs-site/architecture.html +1 -1
  205. package/docs-site/benchmark.html +89 -95
  206. package/docs-site/commands.html +1 -1
  207. package/docs-site/content/benchmark.html +88 -94
  208. package/docs-site/content/en/benchmark.html +134 -90
  209. package/docs-site/content/en/index.html +19 -19
  210. package/docs-site/content/en/runtime.html +5 -5
  211. package/docs-site/content/en/whats-new.html +23 -1
  212. package/docs-site/content/en/workflows.html +2 -2
  213. package/docs-site/content/index.html +19 -19
  214. package/docs-site/content/runtime.html +6 -6
  215. package/docs-site/content/whats-new.html +23 -1
  216. package/docs-site/content/workflows.html +2 -2
  217. package/docs-site/context-engine.html +1 -1
  218. package/docs-site/en/architecture.html +1 -1
  219. package/docs-site/en/benchmark.html +135 -91
  220. package/docs-site/en/commands.html +1 -1
  221. package/docs-site/en/context-engine.html +1 -1
  222. package/docs-site/en/index.html +20 -20
  223. package/docs-site/en/mcp-approval.html +1 -1
  224. package/docs-site/en/mcp-auth.html +1 -1
  225. package/docs-site/en/mcp-servers.html +1 -1
  226. package/docs-site/en/mcp.html +1 -1
  227. package/docs-site/en/permissions.html +1 -1
  228. package/docs-site/en/profiles.html +1 -1
  229. package/docs-site/en/quickstart.html +1 -1
  230. package/docs-site/en/runtime.html +6 -6
  231. package/docs-site/en/scope.html +1 -1
  232. package/docs-site/en/security.html +1 -1
  233. package/docs-site/en/team.html +1 -1
  234. package/docs-site/en/whats-new.html +24 -2
  235. package/docs-site/en/workflows.html +3 -3
  236. package/docs-site/index.html +20 -20
  237. package/docs-site/mcp-approval.html +1 -1
  238. package/docs-site/mcp-auth.html +1 -1
  239. package/docs-site/mcp-servers.html +1 -1
  240. package/docs-site/mcp.html +1 -1
  241. package/docs-site/permissions.html +1 -1
  242. package/docs-site/profiles.html +1 -1
  243. package/docs-site/quickstart.html +1 -1
  244. package/docs-site/runtime.html +7 -7
  245. package/docs-site/scope.html +1 -1
  246. package/docs-site/security.html +1 -1
  247. package/docs-site/team.html +1 -1
  248. package/docs-site/whats-new.html +24 -2
  249. package/docs-site/workflows.html +3 -3
  250. package/evals/architecture-conformance-v1/lane.json +18 -0
  251. package/evals/architecture-conformance-v1/runner.mjs +77 -0
  252. package/evals/fixtures/approved-host-contracts.invalid.json +43 -0
  253. package/evals/fixtures/approved-host-contracts.valid.json +43 -0
  254. package/evals/fixtures/benchmark-assurance-evidence.invalid.json +1 -1
  255. package/evals/fixtures/benchmark-assurance-evidence.valid.json +1 -1
  256. package/evals/fixtures/benchmark-attempt-outcome.invalid.json +42 -0
  257. package/evals/fixtures/benchmark-attempt-outcome.valid.json +42 -0
  258. package/evals/fixtures/benchmark-independent-verification-plan.invalid.json +7 -0
  259. package/evals/fixtures/benchmark-independent-verification-plan.valid.json +21 -0
  260. package/evals/fixtures/codex-relative-efficiency-v1.invalid.json +4 -0
  261. package/evals/fixtures/codex-relative-efficiency-v1.valid.json +94 -0
  262. package/evals/fixtures/composite-criterion.invalid.json +10 -0
  263. package/evals/fixtures/composite-criterion.valid.json +33 -0
  264. package/evals/fixtures/contract-family-library.invalid.json +42 -0
  265. package/evals/fixtures/contract-family-library.valid.json +41 -0
  266. package/evals/fixtures/contract-selection-recipe.invalid.json +29 -0
  267. package/evals/fixtures/contract-selection-recipe.valid.json +29 -0
  268. package/evals/fixtures/helper-request.invalid.json +1 -1
  269. package/evals/fixtures/helper-request.valid.json +1 -1
  270. package/evals/fixtures/host-contract-plan.invalid.json +42 -0
  271. package/evals/fixtures/host-contract-plan.valid.json +41 -0
  272. package/evals/fixtures/piagent-webui/subagent-tree-v1.valid.json +7 -0
  273. package/evals/fixtures/scoped-project-verification-receipt-v2.invalid.json +42 -0
  274. package/evals/fixtures/scoped-project-verification-receipt-v2.valid.json +42 -0
  275. package/evals/fixtures/scoped-project-verification-receipt-v3.invalid.json +57 -0
  276. package/evals/fixtures/scoped-project-verification-receipt-v3.valid.json +57 -0
  277. package/evals/fixtures/scoped-verification-receipt-v1.invalid.json +40 -0
  278. package/evals/fixtures/scoped-verification-receipt-v1.valid.json +40 -0
  279. package/evals/fixtures/task-authority-snapshot.valid.json +4 -4
  280. package/evals/fs4-readiness-matrix.v1.json +2 -2
  281. package/evals/fs5-artifact-archive/README.md +32 -0
  282. package/evals/fs5-artifact-archive/manifest.json +148 -0
  283. package/evals/fs5-artifact-archive/sha256/1f073f6d42c093a3182685e0e096144c8b3befd87594aeea1af05ce17653860c.txt +380 -0
  284. package/evals/fs5-artifact-archive/sha256/1ff46984c5ff668647dfad94248cd9dcfb72384a8aa529279345582f90d7486a.txt +331 -0
  285. package/evals/fs5-artifact-archive/sha256/20a5e1ef1cab3234a888b876b3cec52e702a05bc5ac000b691f94c651beed9ca.txt +800 -0
  286. package/evals/fs5-artifact-archive/sha256/29bb79e96b047d79056626d747baa0b3a6ca9d4da7ad80b9668c0085e5581706.txt +116 -0
  287. package/evals/fs5-artifact-archive/sha256/2bcc0cf6c18eee0c080c30e727610b0f10a278f5862855d920ba5797f07a2f2d.txt +252 -0
  288. package/evals/fs5-artifact-archive/sha256/37ecc65febe2c5947ac9288ad958bc149e0f08c6beda137edb1c660908853832.txt +324 -0
  289. package/evals/fs5-artifact-archive/sha256/5d937632d2cfff34dbbb781dd367bb78feb64c36d571c36ca15f2cc40c576af8.txt +142 -0
  290. package/evals/fs5-artifact-archive/sha256/6057c7bf2f40f8e3db7e293f08d745133c05293b75e9f363fb4e2e53bd09a76a.txt +244 -0
  291. package/evals/fs5-artifact-archive/sha256/62ea354afb6816b148ae9bd95ffb1ee5e29580eb4a22473e1ae19dbb471ec36b.txt +930 -0
  292. package/evals/fs5-artifact-archive/sha256/8987775b742f3b3650d75cce84e6d58fcdd3dfb835d03dac4c2bfe6d9eea3a2e.txt +903 -0
  293. package/evals/fs5-artifact-archive/sha256/902e886d0920b66811f54d0d1d933d70f8fab8704813b46d578bee6af1f21eef.txt +942 -0
  294. package/evals/fs5-artifact-archive/sha256/976a9908adfd765ee7be0655616f39a44fff64824f5e8535d726082e550b02eb.txt +910 -0
  295. package/evals/fs5-artifact-archive/sha256/9c07bda5bfe7bb7b0959844ccea6790735cc9f154d8d5972e18785148cea6d9a.txt +101 -0
  296. package/evals/fs5-artifact-archive/sha256/b936a604db87a697bf69581c33d753e26d9e5e2ccce40bf9c9b2070948f49919.txt +931 -0
  297. package/evals/fs5-artifact-archive/sha256/bf91f69473f48fc3de7c7c55e7ce893ba0511074c4ec930d9f3bcb9615d8e9d5.txt +950 -0
  298. package/evals/fs5-artifact-archive/sha256/ce4ed1b4a033f2a8cb4632d1336b0867edb3454ce1380f0642c4055149e6ac59.txt +784 -0
  299. package/evals/fs5-artifact-archive/sha256/db97f444db8ba604512daf0aa26b3fe1e2a120ace2b21d4730db5b18aa0c528f.txt +950 -0
  300. package/evals/fs5-causal-arm.v1.json +10 -6
  301. package/evals/fs5-pilot-protocol.v1.json +3 -3
  302. package/evals/fs5-pilot-protocol.v2.json +8 -8
  303. package/evals/fs5-pilot-protocol.v3.json +8 -8
  304. package/evals/fs5-pilot-protocol.v4.json +7 -7
  305. package/evals/fs5-pilot-protocol.v5.json +10 -8
  306. package/evals/harness-next/development-corpus.mjs +106 -0
  307. package/evals/harness-next/resource-budget-probe.mjs +38 -0
  308. package/evals/harness-next/run-calibration.mjs +83 -0
  309. package/evals/harness-next/run-resource-probe.mjs +55 -0
  310. package/evals/harness-next/selected-development-corpus.mjs +27 -0
  311. package/evals/harness-next.v1.json +51 -0
  312. package/evals/long-horizon-v1/README.md +19 -0
  313. package/evals/long-horizon-v1/runner.mjs +116 -48
  314. package/evals/long-horizon-v1/worker.mjs +77 -30
  315. package/evals/private-holdout-v1/CURRENT_BOUNDARY.md +53 -0
  316. package/evals/private-holdout-v1/README.md +5 -2
  317. package/evals/private-holdout-v1/public-exposure.v1.json +1 -1
  318. package/evals/private-holdout-v1/public-exposure.v2.json +273 -0
  319. package/evals/runtime-conformance-v1/README.md +43 -0
  320. package/evals/runtime-conformance-v1/evaluate-paid-canary.mjs +198 -0
  321. package/evals/runtime-conformance-v1/lane.json +57 -0
  322. package/evals/runtime-conformance-v1/paid-canary.json +31 -0
  323. package/evals/runtime-conformance-v1/runner.mjs +456 -0
  324. package/package.json +9 -4
  325. package/packages/piagent-core/README.md +15 -6
  326. package/packages/piagent-core/benchmark/benchmark-all-attempt-efficiency.js +55 -0
  327. package/packages/piagent-core/benchmark/benchmark-artifact-binding.js +49 -0
  328. package/packages/piagent-core/benchmark/benchmark-bootstrap.js +265 -14
  329. package/packages/piagent-core/benchmark/benchmark-budget-governor.js +271 -0
  330. package/packages/piagent-core/benchmark/benchmark-campaign.js +592 -0
  331. package/packages/piagent-core/benchmark/benchmark-candidate.js +8 -3
  332. package/packages/piagent-core/benchmark/benchmark-checkpoint.js +67 -0
  333. package/packages/piagent-core/benchmark/benchmark-claim-restrictions.js +269 -2
  334. package/packages/piagent-core/benchmark/benchmark-cli.js +120 -3
  335. package/packages/piagent-core/benchmark/benchmark-codex-events.js +235 -0
  336. package/packages/piagent-core/benchmark/benchmark-codex-outcome.js +20 -0
  337. package/packages/piagent-core/benchmark/benchmark-codex-relative-efficiency.js +699 -0
  338. package/packages/piagent-core/benchmark/benchmark-codex-rollout.js +521 -0
  339. package/packages/piagent-core/benchmark/benchmark-codex.js +104 -8
  340. package/packages/piagent-core/benchmark/benchmark-comparison.js +284 -1
  341. package/packages/piagent-core/benchmark/benchmark-core.js +111 -110
  342. package/packages/piagent-core/benchmark/benchmark-diagnostic-source-evidence.js +40 -0
  343. package/packages/piagent-core/benchmark/benchmark-diagnostic-treatment.js +104 -0
  344. package/packages/piagent-core/benchmark/benchmark-evaluator-v3.js +226 -0
  345. package/packages/piagent-core/benchmark/benchmark-execution-guard.js +23 -1
  346. package/packages/piagent-core/benchmark/benchmark-forensics.js +67 -52
  347. package/packages/piagent-core/benchmark/benchmark-goal-assessment.js +193 -0
  348. package/packages/piagent-core/benchmark/benchmark-goal-report.js +87 -0
  349. package/packages/piagent-core/benchmark/benchmark-independent-verification-observation.js +64 -0
  350. package/packages/piagent-core/benchmark/benchmark-matrix-summary.js +141 -0
  351. package/packages/piagent-core/benchmark/benchmark-matrix.js +1 -0
  352. package/packages/piagent-core/benchmark/benchmark-normalized-cost.js +62 -0
  353. package/packages/piagent-core/benchmark/benchmark-pi-home.js +1 -0
  354. package/packages/piagent-core/benchmark/benchmark-preflight.js +70 -7
  355. package/packages/piagent-core/benchmark/benchmark-process.js +23 -9
  356. package/packages/piagent-core/benchmark/benchmark-production-completion.js +84 -0
  357. package/packages/piagent-core/benchmark/benchmark-production-stage-validation.js +209 -0
  358. package/packages/piagent-core/benchmark/benchmark-provider-free-evidence.js +462 -0
  359. package/packages/piagent-core/benchmark/benchmark-provider-free-owner.js +24 -0
  360. package/packages/piagent-core/benchmark/benchmark-provider-wire.js +378 -0
  361. package/packages/piagent-core/benchmark/benchmark-record-validation.d.ts +2 -0
  362. package/packages/piagent-core/benchmark/benchmark-record-validation.js +343 -8
  363. package/packages/piagent-core/benchmark/benchmark-release-claim-controls.js +132 -0
  364. package/packages/piagent-core/benchmark/benchmark-report.js +94 -5
  365. package/packages/piagent-core/benchmark/benchmark-resume-recovery.js +280 -10
  366. package/packages/piagent-core/benchmark/benchmark-runner-policy.js +88 -1
  367. package/packages/piagent-core/benchmark/benchmark-runtime-causal.js +244 -0
  368. package/packages/piagent-core/benchmark/benchmark-runtime-identity.js +50 -1
  369. package/packages/piagent-core/benchmark/benchmark-runtime.js +102 -10
  370. package/packages/piagent-core/benchmark/benchmark-safety-evidence.js +74 -0
  371. package/packages/piagent-core/benchmark/benchmark-service-tier.js +189 -0
  372. package/packages/piagent-core/benchmark/benchmark-stage-diagnostic.js +246 -33
  373. package/packages/piagent-core/benchmark/benchmark-suite-identity.js +264 -1
  374. package/packages/piagent-core/benchmark/benchmark-suite-runtime.js +4 -0
  375. package/packages/piagent-core/benchmark/benchmark-suite.js +232 -4
  376. package/packages/piagent-core/benchmark/benchmark-summary-support.js +33 -1
  377. package/packages/piagent-core/benchmark/benchmark-timing-contract.js +189 -0
  378. package/packages/piagent-core/benchmark/benchmark-timing-diagnostics.js +110 -139
  379. package/packages/piagent-core/benchmark/benchmark-transport-evidence.js +203 -0
  380. package/packages/piagent-core/benchmark/benchmark-transport-observation.js +147 -0
  381. package/packages/piagent-core/benchmark/benchmark-tree-identity.js +2 -1
  382. package/packages/piagent-core/benchmark/benchmark-usage.js +410 -37
  383. package/packages/piagent-core/benchmark/benchmark-workflow.js +136 -38
  384. package/packages/piagent-core/benchmark/fs5-pilot-protocol.js +21 -2
  385. package/packages/piagent-core/capabilities/runtime-integrity.js +6 -0
  386. package/packages/piagent-core/extensions/acceptance-api-baseline.js +24 -0
  387. package/packages/piagent-core/extensions/acceptance-assessment.js +153 -0
  388. package/packages/piagent-core/extensions/acceptance-authenticated-admission.d.ts +41 -0
  389. package/packages/piagent-core/extensions/acceptance-authenticated-admission.js +120 -0
  390. package/packages/piagent-core/extensions/acceptance-behavior-proof.js +1000 -0
  391. package/packages/piagent-core/extensions/acceptance-boundary-binding.js +31 -0
  392. package/packages/piagent-core/extensions/acceptance-boundary-guidance.js +214 -0
  393. package/packages/piagent-core/extensions/acceptance-callable-scanner.js +244 -0
  394. package/packages/piagent-core/extensions/acceptance-clause-group.js +45 -0
  395. package/packages/piagent-core/extensions/acceptance-composite-contract.js +334 -0
  396. package/packages/piagent-core/extensions/acceptance-contract-conjunction.js +78 -0
  397. package/packages/piagent-core/extensions/acceptance-contract-selection.js +161 -0
  398. package/packages/piagent-core/extensions/acceptance-contract-semantics.js +211 -211
  399. package/packages/piagent-core/extensions/acceptance-declared-api.js +126 -0
  400. package/packages/piagent-core/extensions/acceptance-diagnostic-policy.ts +14 -0
  401. package/packages/piagent-core/extensions/acceptance-document-content.js +73 -0
  402. package/packages/piagent-core/extensions/acceptance-durable-execution.d.ts +59 -0
  403. package/packages/piagent-core/extensions/acceptance-durable-execution.js +139 -0
  404. package/packages/piagent-core/extensions/acceptance-error-classes.js +1 -1
  405. package/packages/piagent-core/extensions/acceptance-evidence-store.js +223 -0
  406. package/packages/piagent-core/extensions/acceptance-executable-evidence.js +490 -88
  407. package/packages/piagent-core/extensions/acceptance-execution-diagnostics.js +34 -0
  408. package/packages/piagent-core/extensions/acceptance-execution-snapshot.js +174 -0
  409. package/packages/piagent-core/extensions/acceptance-executor/.dockerignore +21 -0
  410. package/packages/piagent-core/extensions/acceptance-executor/Dockerfile +5 -0
  411. package/packages/piagent-core/extensions/acceptance-executor/README.md +103 -0
  412. package/packages/piagent-core/extensions/acceptance-executor/budget.mjs +54 -0
  413. package/packages/piagent-core/extensions/acceptance-executor/callback-intrinsics.mjs +126 -0
  414. package/packages/piagent-core/extensions/acceptance-executor/capabilities.mjs +127 -0
  415. package/packages/piagent-core/extensions/acceptance-executor/guest.mjs +285 -0
  416. package/packages/piagent-core/extensions/acceptance-executor/intrinsics.mjs +133 -0
  417. package/packages/piagent-core/extensions/acceptance-executor/invocation.mjs +39 -0
  418. package/packages/piagent-core/extensions/acceptance-executor/jobs.mjs +29 -0
  419. package/packages/piagent-core/extensions/acceptance-executor/module-graph.mjs +70 -0
  420. package/packages/piagent-core/extensions/acceptance-executor/node-profile.mjs +398 -0
  421. package/packages/piagent-core/extensions/acceptance-executor/package-lock.json +40 -0
  422. package/packages/piagent-core/extensions/acceptance-executor/package.json +10 -0
  423. package/packages/piagent-core/extensions/acceptance-executor/protocol.mjs +248 -0
  424. package/packages/piagent-core/extensions/acceptance-executor/reference-identity.mjs +61 -0
  425. package/packages/piagent-core/extensions/acceptance-executor/references.mjs +14 -0
  426. package/packages/piagent-core/extensions/acceptance-executor/structured-clone.mjs +53 -0
  427. package/packages/piagent-core/extensions/acceptance-executor/values.mjs +97 -0
  428. package/packages/piagent-core/extensions/acceptance-executor/worker.mjs +75 -0
  429. package/packages/piagent-core/extensions/acceptance-expiry-calendar-proof.js +162 -0
  430. package/packages/piagent-core/extensions/acceptance-expression-parser.js +155 -0
  431. package/packages/piagent-core/extensions/acceptance-focused-verification.js +40 -0
  432. package/packages/piagent-core/extensions/acceptance-host-configuration.js +337 -0
  433. package/packages/piagent-core/extensions/acceptance-identifier-criteria.js +25 -0
  434. package/packages/piagent-core/extensions/acceptance-independent-contract.js +209 -0
  435. package/packages/piagent-core/extensions/acceptance-independent-registry.js +106 -0
  436. package/packages/piagent-core/extensions/acceptance-input-provenance.js +40 -0
  437. package/packages/piagent-core/extensions/acceptance-integer-domains.js +322 -0
  438. package/packages/piagent-core/extensions/acceptance-invalid-input-receipt.js +20 -0
  439. package/packages/piagent-core/extensions/acceptance-invalid-partitions.js +26 -0
  440. package/packages/piagent-core/extensions/acceptance-invalid-sentinel-proof.js +477 -0
  441. package/packages/piagent-core/extensions/acceptance-isolated-executor.js +254 -0
  442. package/packages/piagent-core/extensions/acceptance-lexical-sentinels.js +130 -0
  443. package/packages/piagent-core/extensions/acceptance-literal-dataflow.js +735 -0
  444. package/packages/piagent-core/extensions/acceptance-local-binding.js +106 -0
  445. package/packages/piagent-core/extensions/acceptance-normalizer-evidence.js +719 -0
  446. package/packages/piagent-core/extensions/acceptance-obligations.js +75 -0
  447. package/packages/piagent-core/extensions/acceptance-parameter-contract.js +756 -0
  448. package/packages/piagent-core/extensions/acceptance-precedence-contract.js +572 -0
  449. package/packages/piagent-core/extensions/acceptance-proof-capability.js +26 -0
  450. package/packages/piagent-core/extensions/acceptance-receipt.js +208 -180
  451. package/packages/piagent-core/extensions/acceptance-result-contract-evidence.js +159 -0
  452. package/packages/piagent-core/extensions/acceptance-source-origin.js +214 -0
  453. package/packages/piagent-core/extensions/acceptance-state-machine-evidence.js +64 -8
  454. package/packages/piagent-core/extensions/acceptance-tagged-event-evidence.js +685 -0
  455. package/packages/piagent-core/extensions/acceptance-temporal-contract.js +756 -0
  456. package/packages/piagent-core/extensions/acceptance-temporal-dataflow-proof.js +618 -0
  457. package/packages/piagent-core/extensions/acceptance-test-binding-evidence.js +20 -2
  458. package/packages/piagent-core/extensions/acceptance-test-bindings.js +86 -0
  459. package/packages/piagent-core/extensions/acceptance-tuple-shapes.js +12 -0
  460. package/packages/piagent-core/extensions/context-engine.js +12 -17
  461. package/packages/piagent-core/extensions/context-index-policy.js +4 -0
  462. package/packages/piagent-core/extensions/context-query-paths.js +57 -0
  463. package/packages/piagent-core/extensions/criterion-context-pack.js +109 -4
  464. package/packages/piagent-core/extensions/criterion-graph.js +4 -1
  465. package/packages/piagent-core/extensions/failure-types.ts +2 -2
  466. package/packages/piagent-core/extensions/fallback-base-policy.ts +101 -0
  467. package/packages/piagent-core/extensions/guard-types.ts +9 -1
  468. package/packages/piagent-core/extensions/piagent-guard.ts +374 -364
  469. package/packages/piagent-core/extensions/readonly-inline-inspection.ts +378 -0
  470. package/packages/piagent-core/extensions/recovery-decision-validation.ts +92 -0
  471. package/packages/piagent-core/extensions/shell-write-targets.js +15 -14
  472. package/packages/piagent-core/extensions/task-contract-view.js +4 -4
  473. package/packages/piagent-core/extensions/task-digest-migration.js +2 -2
  474. package/packages/piagent-core/extensions/task-journal.js +48 -3
  475. package/packages/piagent-core/extensions/task-lifecycle.js +32 -0
  476. package/packages/piagent-core/extensions/task-runtime-audit.js +8 -2
  477. package/packages/piagent-core/extensions/task-state.js +140 -43
  478. package/packages/piagent-core/extensions/task-terminal-disposition.js +10 -0
  479. package/packages/piagent-core/extensions/trajectory-contract.ts +5 -0
  480. package/packages/piagent-core/extensions/verification-intelligence.js +109 -20
  481. package/packages/piagent-core/extensions/workflow-catalog.ts +98 -0
  482. package/packages/piagent-core/extensions/workspace-evidence-roots.js +52 -16
  483. package/packages/piagent-core/extensions/workspace-revision.js +48 -0
  484. package/packages/piagent-core/extensions/workspace-verification-snapshot.js +13 -0
  485. package/packages/piagent-core/package.json +3 -3
  486. package/packages/piagent-core/policies/base-policy.json +43 -2
  487. package/packages/piagent-core/policy/authority-manifest.v1.json +3 -3
  488. package/packages/piagent-core/prompts/be-to-fe.md +2 -8
  489. package/packages/piagent-core/prompts/plan.md +1 -1
  490. package/packages/piagent-core/prompts/platform-improve.md +2 -6
  491. package/packages/piagent-core/prompts/review.md +2 -7
  492. package/packages/piagent-core/prompts/scout.md +1 -1
  493. package/packages/piagent-core/prompts/task.md +4 -3
  494. package/packages/piagent-core/runtime/context/adaptive-planner.ts +7 -3
  495. package/packages/piagent-core/runtime/hooks/agent-start-hook.ts +60 -59
  496. package/packages/piagent-core/runtime/hooks/agent-start-types.ts +48 -0
  497. package/packages/piagent-core/runtime/hooks/completion-hook.ts +83 -89
  498. package/packages/piagent-core/runtime/hooks/input-hook.ts +98 -7
  499. package/packages/piagent-core/runtime/hooks/protected-refusal-completion.ts +86 -0
  500. package/packages/piagent-core/runtime/hooks/session-hooks.ts +5 -2
  501. package/packages/piagent-core/runtime/hooks/session-start-hook.ts +150 -19
  502. package/packages/piagent-core/runtime/hooks/tool-result-hook.ts +111 -92
  503. package/packages/piagent-core/runtime/hooks/tool-result-metadata.ts +9 -0
  504. package/packages/piagent-core/runtime/hooks/tool-result-navigation.ts +36 -0
  505. package/packages/piagent-core/runtime/hooks/tool-result-retrieval.ts +42 -0
  506. package/packages/piagent-core/runtime/hooks/tool-result-value-helpers.ts +66 -0
  507. package/packages/piagent-core/runtime/input/chat-images.ts +1 -1
  508. package/packages/piagent-core/runtime/inspection/activity-event-adapter.ts +1 -1
  509. package/packages/piagent-core/runtime/inspection/bounded-emission-guard.ts +286 -0
  510. package/packages/piagent-core/runtime/inspection/runtime-event-store.ts +37 -7
  511. package/packages/piagent-core/runtime/inspection/same-process-bridge-proof.ts +1 -1
  512. package/packages/piagent-core/runtime/inspection/task-handoff-history.ts +2 -2
  513. package/packages/piagent-core/runtime/inspection/task-subagent-tree.ts +27 -4
  514. package/packages/piagent-core/runtime/inspection/tool-failure-classification.ts +69 -11
  515. package/packages/piagent-core/runtime/inspection/webui-snapshot.ts +104 -22
  516. package/packages/piagent-core/runtime/inspection/workspace-file-reader.ts +2 -132
  517. package/packages/piagent-core/runtime/model/provider-wire-fingerprint.ts +20 -0
  518. package/packages/piagent-core/runtime/model/service-tier-runtime.ts +242 -0
  519. package/packages/piagent-core/runtime/orchestration/helper-lifecycle.ts +16 -12
  520. package/packages/piagent-core/runtime/orchestration/minimal-delegation-policy.ts +71 -0
  521. package/packages/piagent-core/runtime/orchestration/owned-work-budget.ts +28 -20
  522. package/packages/piagent-core/runtime/orchestration/role-policy.ts +27 -9
  523. package/packages/piagent-core/runtime/orchestration/subagent-tool-policy.ts +329 -0
  524. package/packages/piagent-core/runtime/policy/block-remedy.ts +0 -4
  525. package/packages/piagent-core/runtime/policy/source-worktree-transaction.ts +75 -14
  526. package/packages/piagent-core/runtime/product/activity-inspector.ts +6 -3
  527. package/packages/piagent-core/runtime/product/edit-verifier-timing.ts +26 -0
  528. package/packages/piagent-core/runtime/product/efficiency-metrics.ts +15 -7
  529. package/packages/piagent-core/runtime/product/operator-projections.ts +8 -3
  530. package/packages/piagent-core/runtime/product/task-usage-hooks.ts +78 -0
  531. package/packages/piagent-core/runtime/product/task-usage.ts +104 -0
  532. package/packages/piagent-core/runtime/quality/edit-freshness-guard.ts +102 -0
  533. package/packages/piagent-core/runtime/quality/exact-output-contract.ts +20 -10
  534. package/packages/piagent-core/runtime/quality/performance-assurance.ts +3 -3
  535. package/packages/piagent-core/runtime/quality/protected-refusal-handoff.ts +35 -0
  536. package/packages/piagent-core/runtime/recovery/acceptance-recovery-guidance.ts +21 -0
  537. package/packages/piagent-core/runtime/recovery/continuation-budget.ts +12 -3
  538. package/packages/piagent-core/runtime/recovery/diagnostic-delivery.ts +61 -0
  539. package/packages/piagent-core/runtime/recovery/handoff-projection.ts +196 -58
  540. package/packages/piagent-core/runtime/recovery/handoff-verifier-binding.ts +24 -0
  541. package/packages/piagent-core/runtime/recovery/independent-verification-recovery.ts +79 -0
  542. package/packages/piagent-core/runtime/recovery/pristine-task-policy-refresh.ts +91 -0
  543. package/packages/piagent-core/runtime/recovery/recovery-policy.ts +31 -40
  544. package/packages/piagent-core/runtime/recovery/resume-state.ts +120 -19
  545. package/packages/piagent-core/runtime/recovery/semantic-repair-handshake.ts +7 -13
  546. package/packages/piagent-core/runtime/recovery/task-evidence-coverage-refresh.ts +217 -0
  547. package/packages/piagent-core/runtime/registration/activity-inspector-command.ts +2 -1
  548. package/packages/piagent-core/runtime/registration/context-commands.ts +28 -10
  549. package/packages/piagent-core/runtime/registration/knowledge-tools.ts +9 -5
  550. package/packages/piagent-core/runtime/registration/operator-catalogs.ts +4 -9
  551. package/packages/piagent-core/runtime/registration/operator-request-intake.ts +49 -0
  552. package/packages/piagent-core/runtime/registration/policy-tools.ts +8 -6
  553. package/packages/piagent-core/runtime/registration/session-commands.ts +10 -8
  554. package/packages/piagent-core/runtime/registration/session-wait-tool.ts +54 -0
  555. package/packages/piagent-core/runtime/registration/task-completion-tools.ts +39 -20
  556. package/packages/piagent-core/runtime/registration/task-evidence-tools.ts +21 -12
  557. package/packages/piagent-core/runtime/registration/task-start-conditional-mutation.ts +45 -0
  558. package/packages/piagent-core/runtime/registration/task-start-guidance.ts +24 -15
  559. package/packages/piagent-core/runtime/registration/task-start-manifest.ts +54 -0
  560. package/packages/piagent-core/runtime/registration/task-start-tool.ts +79 -79
  561. package/packages/piagent-core/runtime/registration/workflow-commands.ts +64 -93
  562. package/packages/piagent-core/runtime/runtime-limits.ts +16 -2
  563. package/packages/piagent-core/runtime/session/adaptive-context-analysis.ts +461 -0
  564. package/packages/piagent-core/runtime/session/adaptive-context-governor.ts +464 -0
  565. package/packages/piagent-core/runtime/session/adaptive-context-ledger.ts +265 -0
  566. package/packages/piagent-core/runtime/session/completion-signals.ts +23 -0
  567. package/packages/piagent-core/runtime/session/message-signals.ts +6 -18
  568. package/packages/piagent-core/runtime/session/operator-request-carry.ts +44 -0
  569. package/packages/piagent-core/runtime/session/retrieval-evidence-runtime.ts +188 -0
  570. package/packages/piagent-core/runtime/session/runtime-state.ts +37 -39
  571. package/packages/piagent-core/runtime/session/source-checkout-read-grants.ts +35 -0
  572. package/packages/piagent-core/runtime/session/system-prompt.ts +76 -14
  573. package/packages/piagent-core/runtime/session/task-contract-presentation.ts +39 -0
  574. package/packages/piagent-core/runtime/session/uncertain-send-continuation.ts +231 -0
  575. package/packages/piagent-core/runtime/session/usage.ts +4 -3
  576. package/packages/piagent-core/runtime/tools/apply-patch-tool.ts +6 -6
  577. package/packages/piagent-core/runtime/tools/phase-tool-runtime.ts +1 -1
  578. package/packages/piagent-core/runtime/tools/phase-tools.ts +10 -9
  579. package/packages/piagent-core/runtime/tools/session-wait.ts +42 -0
  580. package/packages/piagent-core/runtime/tools/tool-groups.ts +22 -5
  581. package/packages/piagent-core/runtime/trajectory/trajectory-runtime.ts +192 -5
  582. package/packages/piagent-core/runtime/trajectory/trajectory-types.ts +3 -2
  583. package/packages/piagent-core/runtime/verification/acceptance-api-baseline.js +488 -0
  584. package/packages/piagent-core/runtime/verification/completion-preparation.ts +22 -0
  585. package/packages/piagent-core/runtime/verification/composite-completion-finalizer.ts +105 -0
  586. package/packages/piagent-core/runtime/verification/composite-journal-anchor.ts +181 -0
  587. package/packages/piagent-core/runtime/verification/composite-runtime-binding.ts +76 -0
  588. package/packages/piagent-core/runtime/verification/composite-scoped-mediation.ts +318 -0
  589. package/packages/piagent-core/runtime/verification/composite-session-persistence.ts +175 -0
  590. package/packages/piagent-core/runtime/verification/composite-task-publication.ts +273 -0
  591. package/packages/piagent-core/runtime/verification/exact-verifier-reuse.ts +101 -0
  592. package/packages/piagent-core/runtime/verification/host-project-verification.ts +71 -0
  593. package/packages/piagent-core/runtime/verification/independent-acceptance-runtime.ts +500 -0
  594. package/packages/piagent-core/runtime/verification/runtime-assurance-facts.ts +500 -0
  595. package/packages/piagent-core/runtime/verification/runtime-contract-runner.ts +107 -0
  596. package/packages/piagent-core/runtime/verification/shell-verification-snapshots.ts +56 -0
  597. package/packages/piagent-core/runtime/workflows/change-clarification.ts +61 -0
  598. package/packages/piagent-core/runtime/workflows/input-routing.ts +21 -14
  599. package/packages/piagent-core/runtime/workflows/runtime-intake-compaction.ts +201 -0
  600. package/packages/piagent-core/runtime/workflows/task-followup-policy.ts +163 -0
  601. package/packages/piagent-core/runtime/workflows/task-intake.ts +276 -169
  602. package/packages/piagent-core/runtime/workflows/task-repair-intent.ts +67 -0
  603. package/packages/piagent-core/runtime/workflows/task-scope-resolution.ts +83 -0
  604. package/packages/piagent-core/runtime/workflows/webui-runtime-command.ts +5 -2
  605. package/packages/piagent-core/runtime/workflows/webui-workflow.ts +39 -32
  606. package/packages/piagent-core/runtime/workflows/workflow-follow-up.ts +33 -0
  607. package/packages/piagent-core/security/workspace-file-reader.ts +132 -0
  608. package/packages/piagent-core/subagents/piagent-oracle.md +5 -3
  609. package/packages/piagent-core/subagents/piagent-planner.md +6 -4
  610. package/packages/piagent-core/subagents/piagent-reviewer.md +5 -3
  611. package/packages/piagent-core/subagents/piagent-scout.md +4 -2
  612. package/packages/piagent-core/subagents/piagent-worker.md +6 -4
  613. package/packages/piagent-webui/dist/client/assets/{MarkdownMessage-CxeZqTte.js → MarkdownMessage-DGk34zJT.js} +1 -1
  614. package/packages/piagent-webui/dist/client/assets/{index-BV-_03yl.css → index-DVahUVWy.css} +1 -1
  615. package/packages/piagent-webui/dist/client/assets/index-DiKRmCEP.js +176 -0
  616. package/packages/piagent-webui/dist/client/index.html +2 -2
  617. package/packages/piagent-webui/extension/dispatch-user-entry.ts +13 -0
  618. package/packages/piagent-webui/extension/piagent-webui.ts +13 -3
  619. package/packages/piagent-webui/extension/review-controller.ts +29 -6
  620. package/packages/piagent-webui/extension/same-session-bridge.ts +7 -8
  621. package/packages/piagent-webui/extension/session-stream-adapter.ts +88 -16
  622. package/packages/piagent-webui/extension/source-mutation-controller.ts +29 -3
  623. package/packages/piagent-webui/extension/source-open-controller.ts +29 -7
  624. package/packages/piagent-webui/extension/source-revert-controller.ts +26 -3
  625. package/packages/piagent-webui/gateway/gateway-events.ts +22 -5
  626. package/packages/piagent-webui/gateway/gateway-service.ts +7 -2
  627. package/packages/piagent-webui/gateway/gateway-session-stream.ts +170 -32
  628. package/packages/piagent-webui/gateway/rpc-ui-context.ts +34 -9
  629. package/packages/piagent-webui/gateway/runtime-command-controller.ts +46 -6
  630. package/packages/piagent-webui/gateway/runtime-session-controls.ts +17 -2
  631. package/packages/piagent-webui/gateway/session-catalog.ts +9 -3
  632. package/packages/piagent-webui/gateway/session-command-controller.ts +29 -9
  633. package/packages/piagent-webui/gateway/session-effective-options.ts +2 -9
  634. package/packages/piagent-webui/gateway/session-inspection-registry.ts +11 -2
  635. package/packages/piagent-webui/gateway/session-operation-lifecycle.ts +237 -0
  636. package/packages/piagent-webui/gateway/session-operation-retry-control.ts +38 -0
  637. package/packages/piagent-webui/gateway/session-operation-settlement.ts +28 -0
  638. package/packages/piagent-webui/gateway/session-operation-watchdog.ts +9 -2
  639. package/packages/piagent-webui/gateway/session-prompt-dispatch.ts +37 -0
  640. package/packages/piagent-webui/gateway/session-runtime-close.ts +36 -0
  641. package/packages/piagent-webui/gateway/session-runtime-factory.ts +183 -6
  642. package/packages/piagent-webui/gateway/session-runtime-ownership.ts +48 -0
  643. package/packages/piagent-webui/gateway/session-runtime-state.ts +24 -0
  644. package/packages/piagent-webui/gateway/session-runtime-supervisor.ts +118 -117
  645. package/packages/piagent-webui/ownership/session-lease-store.ts +5 -2
  646. package/packages/piagent-webui/server/core-inspection-provider.ts +75 -15
  647. package/packages/piagent-webui/server/loopback-server.ts +9 -7
  648. package/packages/piagent-webui/server/terminal-delivery-receipt.ts +144 -0
  649. package/packages/piagent-webui/server/transcript-projection.ts +150 -11
  650. package/packages/piagent-webui/shared/message-correlation.ts +25 -0
  651. package/schemas/approved-host-contracts.schema.json +973 -0
  652. package/schemas/benchmark-attempt-outcome.schema.json +303 -0
  653. package/schemas/benchmark-independent-verification-plan.schema.json +34 -0
  654. package/schemas/codex-relative-efficiency-v1.schema.json +155 -0
  655. package/schemas/composite-criterion.schema.json +788 -0
  656. package/schemas/contract-family-library.schema.json +28 -0
  657. package/schemas/contract-selection-recipe.schema.json +31 -0
  658. package/schemas/failure-evidence.schema.json +2 -2
  659. package/schemas/helper-request.schema.json +16 -4
  660. package/schemas/host-contract-plan.schema.json +25 -0
  661. package/schemas/piagent-webui/gateway-protocol-v1.schema.json +16 -2
  662. package/schemas/piagent-webui/runtime-command-v1.schema.json +26 -3
  663. package/schemas/piagent-webui/runtime-event-v2.schema.json +46 -5
  664. package/schemas/piagent-webui/session-live-state-v1.schema.json +2 -0
  665. package/schemas/piagent-webui/snapshot-v1.schema.json +3 -0
  666. package/schemas/piagent-webui/source-change-v1.schema.json +12 -0
  667. package/schemas/piagent-webui/subagent-tree-v1.schema.json +11 -1
  668. package/schemas/piagent-webui/transcript-v1.schema.json +2 -1
  669. package/schemas/project-profile.schema.json +1 -1
  670. package/schemas/public-contracts/codex-mcp-metadata-v1.schema.json +206 -0
  671. package/schemas/public-contracts/codex-mcp-metadata-v2.schema.json +228 -0
  672. package/schemas/public-contracts/codex-mcp-metadata-v3.schema.json +233 -0
  673. package/schemas/public-contracts/revocation-v1.schema.json +87 -0
  674. package/schemas/public-contracts/subscription-contract-v1.schema.json +76 -0
  675. package/schemas/scoped-project-verification-receipt-v2.schema.json +83 -0
  676. package/schemas/scoped-project-verification-receipt-v3.schema.json +295 -0
  677. package/schemas/scoped-verification-receipt-v1.schema.json +76 -0
  678. package/schemas/task-contract.schema.json +45 -0
  679. package/scripts/approve-independent-verification.mjs +57 -0
  680. package/scripts/benchmark-arm-observer.mjs +320 -0
  681. package/scripts/benchmark-budget-ipc.mjs +34 -0
  682. package/scripts/benchmark-budget-launcher.mjs +91 -0
  683. package/scripts/benchmark-budget-processes.mjs +133 -0
  684. package/scripts/benchmark-budget-publication.mjs +228 -0
  685. package/scripts/benchmark-budget-runtime.mjs +136 -0
  686. package/scripts/benchmark-candidate-ablation.mjs +265 -0
  687. package/scripts/benchmark-codex-journey.mjs +406 -0
  688. package/scripts/benchmark-independent-verification.mjs +628 -0
  689. package/scripts/benchmark-journey-outcome.mjs +92 -0
  690. package/scripts/benchmark-production-v3-human-review.mjs +192 -0
  691. package/scripts/benchmark-public-input-catalog.mjs +158 -0
  692. package/scripts/benchmark-registered-plan-author.mjs +355 -0
  693. package/scripts/benchmark-registered-plan-recipe-support.mjs +85 -0
  694. package/scripts/benchmark-registered-plan-recipes-backend.mjs +165 -0
  695. package/scripts/benchmark-registered-plan-recipes-data.mjs +164 -0
  696. package/scripts/benchmark-registered-plan-recipes-platform.mjs +165 -0
  697. package/scripts/benchmark-runner-completion.mjs +133 -0
  698. package/scripts/benchmark-runner-configuration.mjs +159 -0
  699. package/scripts/benchmark-runner-core.mjs +224 -387
  700. package/scripts/benchmark-runner-finalization.mjs +144 -27
  701. package/scripts/benchmark-runner-provider-boundary.mjs +44 -0
  702. package/scripts/benchmark-runner-schedule.mjs +256 -0
  703. package/scripts/benchmark-runner-support.mjs +136 -4
  704. package/scripts/benchmark-runner.mjs +95 -18
  705. package/scripts/benchmark-scoped-broker-custody.mjs +483 -0
  706. package/scripts/benchmark-scoped-docs-verifier.mjs +203 -0
  707. package/scripts/benchmark-scoped-frozen-qualification.mjs +676 -0
  708. package/scripts/benchmark-scoped-pi-router.mjs +196 -0
  709. package/scripts/benchmark-scoped-project-verification-receipt.mjs +49 -0
  710. package/scripts/benchmark-scoped-project-verifier.mjs +461 -0
  711. package/scripts/benchmark-scoped-session-custody.mjs +599 -0
  712. package/scripts/benchmark-scoped-session-factory.mjs +342 -0
  713. package/scripts/benchmark-scoped-tool-broker.mjs +523 -0
  714. package/scripts/benchmark-scoped-verification-supervisor.mjs +773 -0
  715. package/scripts/benchmark-session-evaluator.mjs +169 -0
  716. package/scripts/benchmark-session-provider-boundary.mjs +62 -0
  717. package/scripts/benchmark-session-usage.mjs +28 -0
  718. package/scripts/benchmark-session.mjs +343 -50
  719. package/scripts/benchmark-webui-journey.mjs +678 -0
  720. package/scripts/check-public-wording.mjs +46 -0
  721. package/scripts/configure-subagents.sh +42 -34
  722. package/scripts/fs4-readiness-evaluation.mjs +7 -1
  723. package/scripts/helper-evaluation.mjs +1 -1
  724. package/scripts/phase-tools-evaluation.mjs +1 -0
  725. package/scripts/pi-auto.sh +7 -1
  726. package/scripts/pi-usage-history.mjs +201 -11
  727. package/scripts/piagent-cli.mjs +8 -0
  728. package/scripts/private-holdout-readiness.mjs +7 -1
  729. package/scripts/public-evaluation-exposure.mjs +140 -0
  730. package/scripts/select-independent-verification.mjs +62 -0
  731. package/scripts/team-doctor.sh +1 -1
  732. package/scripts/typescript-loader.mjs +135 -1
  733. package/scripts/update-global.mjs +6 -7
  734. package/scripts/verify-local.sh +41 -55
  735. package/scripts/verify-release-identity.mjs +5 -3
  736. package/packages/piagent-webui/dist/client/assets/index-DynIMe8I.js +0 -176
@@ -0,0 +1,628 @@
1
+ import { createHash } from "node:crypto";
2
+ import fs from "node:fs";
3
+ import path from "node:path";
4
+ import { benchmarkCommandIdentity } from "../packages/piagent-core/benchmark/benchmark-runtime-identity.js";
5
+ import { installedContractVerifierDigest, openHostContractConfiguration, validateHostContractPlan, writeHostContractApproval } from "../packages/piagent-core/extensions/acceptance-host-configuration.js";
6
+ import { buildAcceptanceReceipt } from "../packages/piagent-core/extensions/acceptance-receipt.js";
7
+ import { effectiveProtectedPaths } from "../packages/piagent-core/extensions/context-index-policy.js";
8
+ import { DURABLE_EXECUTION_VERSION } from "../packages/piagent-core/extensions/acceptance-durable-execution.js";
9
+ import { compileIndependentContract, compareIndependentExecution } from "../packages/piagent-core/extensions/acceptance-independent-contract.js";
10
+ import { EXECUTION_SNAPSHOT_VERSION } from "../packages/piagent-core/extensions/acceptance-execution-snapshot.js";
11
+ import { parseRequest, parseResponse } from "../packages/piagent-core/extensions/acceptance-executor/protocol.mjs";
12
+ import { operatorRequestDigest } from "../packages/piagent-core/extensions/task-state.js";
13
+ import { redactSensitiveText } from "../packages/piagent-core/extensions/redaction-core.js";
14
+ import { extractLocalImagePathCandidates } from "../packages/piagent-core/runtime/input/chat-images.ts";
15
+ import { boundedOperatorRequest } from "../packages/piagent-core/runtime/registration/operator-request-intake.ts";
16
+ import { automaticTaskExpectedOutput } from "../packages/piagent-core/runtime/registration/task-start-conditional-mutation.ts";
17
+ import { LONG_INPUT_CHARS } from "../packages/piagent-core/runtime/runtime-limits.ts";
18
+ import { agentStartTaskRequest, looksLikeGovernedBoilerplate } from "../packages/piagent-core/runtime/workflows/input-routing.ts";
19
+ import { automaticAcceptanceCriteria, automaticTaskIntakeMode, automaticTaskMutationPolicy,
20
+ automaticTaskSummary } from "../packages/piagent-core/runtime/workflows/task-intake.ts";
21
+ import { buildWebUiWorkflowCommand, isWebUiWorkflowId } from "../packages/piagent-core/runtime/workflows/webui-workflow.ts";
22
+ import { buildWorkflowFollowUp } from "../packages/piagent-core/runtime/workflows/workflow-follow-up.ts";
23
+ import { compositeTaskPublicationDigest, openCompositeTaskPublicationStore } from "../packages/piagent-core/runtime/verification/composite-task-publication.ts";
24
+
25
+ export const BENCHMARK_VERIFICATION_PLAN_VERSION = "benchmark-independent-verification-plan-v1";
26
+ export const NODE_BENCHMARK_VERIFICATION_PLAN_VERSION = "benchmark-independent-verification-plan-v2";
27
+ const HASH = /^[a-f0-9]{64}$/;
28
+ const hash = (value) => createHash("sha256").update(value).digest("hex");
29
+ const exact = (value, fields) => value && typeof value === "object" && !Array.isArray(value)
30
+ && Object.keys(value).length === fields.length && fields.every(field => Object.hasOwn(value, field));
31
+ const freeze = (value) => { if (value && typeof value === "object") { Object.values(value).forEach(freeze); Object.freeze(value); } return value; };
32
+ const inside = (root, file) => { const relative = path.relative(fs.realpathSync.native(root), file);
33
+ return !relative || (!relative.startsWith(`..${path.sep}`) && relative !== ".." && !path.isAbsolute(relative)); };
34
+
35
+ function registeredPlanForSurface(plan, surface) {
36
+ if (!["piagent", "codex-cli"].includes(surface)) throw new TypeError("Invalid registered verification surface");
37
+ const selected = structuredClone(plan);
38
+ for (const contract of selected.contracts) {
39
+ if (contract.route !== "composite") continue;
40
+ const identity = contract.planContext.identity;
41
+ if (!exact(identity, ["suiteDigest", "configDigest", "armDigests"])
42
+ || !exact(identity.armDigests, ["piagent", "codex-cli"])
43
+ || ![identity.suiteDigest, identity.configDigest, identity.armDigests.piagent,
44
+ identity.armDigests["codex-cli"]].every(value => HASH.test(value))) {
45
+ throw new TypeError("Invalid registered surface-indexed composite identity");
46
+ }
47
+ contract.planContext.identity = { suiteDigest: identity.suiteDigest,
48
+ configDigest: identity.configDigest, armDigest: identity.armDigests[surface] };
49
+ }
50
+ validateHostContractPlan(selected);
51
+ return freeze(selected);
52
+ }
53
+
54
+ export function resolvedJourneyTurns(scenario, suiteRoot, resolveSuiteEntry) {
55
+ if (!scenario.userJourney) return null;
56
+ return scenario.userJourney.turns.map((turn) => {
57
+ if (Object.hasOwn(turn, "workflow") && !isWebUiWorkflowId(turn.workflow)) throw new TypeError("Unsupported verification workflow");
58
+ return {
59
+ id: turn.id,
60
+ message: fs.readFileSync(resolveSuiteEntry(suiteRoot, turn.prompt, `journey prompt ${scenario.id}/${turn.id}`), "utf8").trim(),
61
+ reconnectBefore: turn.reconnectBefore === true,
62
+ receiptUncertain: turn.receiptUncertain === true,
63
+ ...(turn.workflow ? { workflow: turn.workflow } : {})
64
+ };
65
+ });
66
+ }
67
+
68
+ /** Prospective Piagent request bytes only; no task admission, criterion or approval authority. */
69
+ export function benchmarkVerificationOperatorRequest({ message, workflow }) {
70
+ if (workflow != null && !isWebUiWorkflowId(workflow)) throw new TypeError("Unsupported verification workflow");
71
+ const request = buildWebUiWorkflowCommand(null, message);
72
+ // Raw input may be rewritten by commands, boilerplate collapse or a context-
73
+ // dependent fresh-session handoff. Explicit workflow follow-ups originate
74
+ // from the extension, so those preflight rewrites do not apply to them.
75
+ if (!workflow && (request.startsWith("/") || looksLikeGovernedBoilerplate(request) || request.length >= LONG_INPUT_CHARS)) {
76
+ throw new TypeError("Unsupported verification request ingress: declare a workflow or use bounded plain prose");
77
+ }
78
+ const delivered = workflow ? buildWorkflowFollowUp(workflow, request) : request;
79
+ // Attachment rewriting depends on project files and policy. Detect possible
80
+ // paths without reading them; never guess which image will be attached.
81
+ if (extractLocalImagePathCandidates(delivered, "/").length) throw new TypeError("Unsupported verification image request ingress");
82
+ const safeRequest = boundedOperatorRequest(agentStartTaskRequest(delivered), value => redactSensitiveText(value).text);
83
+ if (!safeRequest) throw new TypeError("Unbound verification operator request");
84
+ return safeRequest;
85
+ }
86
+
87
+ /** Prospective Piagent request identity only; no task admission, criterion or approval authority. */
88
+ export function benchmarkVerificationRequestDigest(input) {
89
+ return operatorRequestDigest(benchmarkVerificationOperatorRequest(input));
90
+ }
91
+
92
+ /** Preview the actual frozen runtime, not a live checkout with different build assets. */
93
+ export function benchmarkVerificationBinding({ installedRoot, suiteDigest }) {
94
+ if (!HASH.test(suiteDigest)) throw new TypeError("Invalid frozen verification suite digest");
95
+ return Object.freeze({ kind: "benchmark-verification-binding-v1", suiteDigest,
96
+ verifierDigest: installedContractVerifierDigest(installedRoot), approval: "not-granted" });
97
+ }
98
+
99
+ export function prepareBenchmarkVerification({ options, resumeState, registeredMeasurement, ...scope }) {
100
+ if (registeredMeasurement) {
101
+ if (options.verificationPlan || options.approveVerification) {
102
+ throw new Error("Registered measurement supplies its signed verification plans; legacy verification options are forbidden");
103
+ }
104
+ const plan = loadRegisteredBenchmarkVerificationPlan({ registeredMeasurement, ...scope });
105
+ if (resumeState && JSON.stringify(plan.identity) !== JSON.stringify(resumeState.manifest.verificationPlan?.identity ?? null)) {
106
+ throw new Error("Cannot resume benchmark: registered independent verification configuration changed");
107
+ }
108
+ // The detached trusted registration is the approval boundary. This flag is
109
+ // internal runner state; the registered CLI still rejects an arbitrary
110
+ // --approve-verification or --verification-plan input.
111
+ options.approveVerification = true;
112
+ return plan;
113
+ }
114
+ if (resumeState) {
115
+ if (options.verificationPlan && options.verificationPlan !== resumeState.manifest.verificationPlan?.file) throw new Error("Cannot change the verification plan on resume");
116
+ options.verificationPlan = resumeState.manifest.verificationPlan?.file;
117
+ }
118
+ if (options.approveVerification && !options.verificationPlan) throw new Error("--approve-verification requires a verification plan");
119
+ const plan = options.verificationPlan ? loadBenchmarkVerificationPlan({ ...scope, file: options.verificationPlan }) : null;
120
+ if (resumeState && JSON.stringify(plan?.identity ?? null) !== JSON.stringify(resumeState.manifest.verificationPlan?.identity ?? null)) {
121
+ throw new Error("Cannot resume benchmark: independent verification configuration changed");
122
+ }
123
+ if (plan && !options.dryRun && !options.preflightOnly && !options.approveVerification) {
124
+ throw new Error("Independent verification requires explicit --approve-verification; --yes is not approval");
125
+ }
126
+ if (plan) options.keepWorkspaces = true;
127
+ return plan;
128
+ }
129
+
130
+ function readRegisteredAsset(registeredMeasurement, relativePath) {
131
+ const root = registeredMeasurement?.assetRoot;
132
+ if (typeof root !== "string" || !path.isAbsolute(root) || fs.realpathSync.native(root) !== root) {
133
+ throw new Error("Registered verification asset root is invalid");
134
+ }
135
+ const entry = registeredMeasurement?.inventory?.entries?.find(item => item.path === relativePath);
136
+ if (!entry || !HASH.test(entry.sha256) || !Number.isSafeInteger(entry.bytes) || entry.bytes < 1 || entry.bytes > 2 * 1024 * 1024) {
137
+ throw new Error("Registered verification plan is absent from the approved inventory");
138
+ }
139
+ const file = path.join(root, ...relativePath.split("/")), relative = path.relative(root, file);
140
+ if (relative.split(path.sep).join("/") !== relativePath || relative.startsWith("../") || path.isAbsolute(relative)) {
141
+ throw new Error("Registered verification plan escapes its approved root");
142
+ }
143
+ const before = fs.lstatSync(file, { bigint: true });
144
+ if (!before.isFile() || before.isSymbolicLink() || before.nlink !== 1n || before.size !== BigInt(entry.bytes)) {
145
+ throw new Error("Registered verification plan is not one approved regular file");
146
+ }
147
+ const fd = fs.openSync(file, fs.constants.O_RDONLY | (fs.constants.O_NOFOLLOW ?? 0));
148
+ try {
149
+ const descriptor = fs.fstatSync(fd, { bigint: true }), bytes = fs.readFileSync(fd), after = fs.fstatSync(fd,
150
+ { bigint: true }), current = fs.lstatSync(file, { bigint: true }), fields =
151
+ ["dev", "ino", "mode", "nlink", "size", "mtimeNs", "ctimeNs"];
152
+ if (bytes.length !== entry.bytes || fields.some(name => before[name] !== descriptor[name]
153
+ || before[name] !== after[name] || before[name] !== current[name]) || hash(bytes) !== entry.sha256) {
154
+ throw new Error("Registered verification plan changed during approved read");
155
+ }
156
+ return bytes;
157
+ } finally { fs.closeSync(fd); }
158
+ }
159
+
160
+ function registeredText(bytes, label) {
161
+ let text;
162
+ try { text = new TextDecoder("utf-8", { fatal: true }).decode(bytes).trim(); }
163
+ catch { throw new Error(`Registered ${label} is not UTF-8`); }
164
+ if (!text || !text.isWellFormed()) throw new Error(`Registered ${label} is empty or malformed`);
165
+ return Object.freeze({ text, bytes: Buffer.byteLength(text), sha256: hash(text) });
166
+ }
167
+
168
+ function suitePromptText(suiteRoot, resolveSuiteEntry, relativePath, label) {
169
+ const file = resolveSuiteEntry(suiteRoot, relativePath, label);
170
+ return registeredText(fs.readFileSync(file), label);
171
+ }
172
+
173
+ function installedJson(installedRoot, relativePath, label) {
174
+ const file = path.join(installedRoot, ...relativePath.split("/"));
175
+ if (!inside(installedRoot, file) || fs.realpathSync.native(file) !== file) {
176
+ throw new Error(`Installed ${label} escapes the frozen candidate`);
177
+ }
178
+ const stat = fs.lstatSync(file);
179
+ if (!stat.isFile() || stat.isSymbolicLink() || stat.size < 2 || stat.size > 2 * 1024 * 1024) {
180
+ throw new Error(`Installed ${label} is not a bounded regular file`);
181
+ }
182
+ return JSON.parse(fs.readFileSync(file, "utf8"));
183
+ }
184
+
185
+ /** Provider-free preview of the exact runtime receipt used by registered-plan
186
+ * loading. This creates no approval, execution, assessment or PASS authority. */
187
+ export function benchmarkVerificationReceiptForTurn(turn, { profile, policy }) {
188
+ const query = benchmarkVerificationOperatorRequest(turn);
189
+ const protectedPaths = effectiveProtectedPaths(policy, profile).readProtectedPaths;
190
+ const changeMode = automaticTaskIntakeMode(query, protectedPaths);
191
+ if (!changeMode) throw new Error("Registered primary request is not admitted by the frozen runtime intake");
192
+ const mutationPolicy = automaticTaskMutationPolicy(query, changeMode);
193
+ const redact = value => redactSensitiveText(String(value ?? "")).text;
194
+ const summary = redact(automaticTaskSummary(query));
195
+ const expectedOutput = redact(automaticTaskExpectedOutput(mutationPolicy));
196
+ const acceptanceCriteria = automaticAcceptanceCriteria(query,
197
+ mutationPolicy === "forbidden" ? "read-only" : changeMode, mutationPolicy).map(redact);
198
+ const built = buildAcceptanceReceipt({
199
+ summary, expectedOutput, acceptanceCriteria, changeMode, mutationPolicy,
200
+ outOfScope: ["Unrelated files and behavior outside the operator request."],
201
+ protectedPaths: profile.protectedPaths ?? [], source: "runtime",
202
+ generatedAt: "1970-01-01T00:00:00.000Z"
203
+ });
204
+ return Object.freeze({ query, changeMode, mutationPolicy,
205
+ criteria: built.receipt.criteria.map((criterion, index) => Object.freeze({
206
+ criterionId: criterion.id, criterionHash: criterion.hash, criterionText: built.acceptanceCriteria[index]
207
+ })) });
208
+ }
209
+
210
+ function registeredCatalogAndInputs({ registeredMeasurement, scenarios, suiteRoot, resolveSuiteEntry }) {
211
+ const catalogBytes = readRegisteredAsset(registeredMeasurement, "catalog.json");
212
+ let catalog;
213
+ try { catalog = JSON.parse(catalogBytes); }
214
+ catch { throw new Error("Registered public input catalog is not JSON"); }
215
+ const fields = ["schemaVersion", "kind", "authority", "suiteId", "scenarioCount", "publicInputCount",
216
+ "variantRoleCounts", "scenarios"];
217
+ const scenarioIds = scenarios.map(item => item.id), payload = registeredMeasurement.payload;
218
+ if (!exact(catalog, fields) || catalog.schemaVersion !== 1
219
+ || catalog.kind !== "benchmark-public-input-catalog-v1" || catalog.authority !== "none"
220
+ || catalog.suiteId !== payload.suiteId || catalog.scenarioCount !== 27 || catalog.publicInputCount !== 54
221
+ || hash(JSON.stringify(catalog)) !== payload.catalogDigest
222
+ || JSON.stringify(payload.scenarioIds) !== JSON.stringify(scenarioIds)
223
+ || !Array.isArray(catalog.scenarios) || catalog.scenarios.length !== scenarios.length
224
+ || JSON.stringify(catalog.scenarios.map(item => item.scenarioId)) !== JSON.stringify(scenarioIds)) {
225
+ throw new Error("Registered public input catalog does not match the detached measurement");
226
+ }
227
+ const changed = new Set(payload.promptRolesChanged), inputs = new Map();
228
+ let publicInputCount = 0;
229
+ for (const [scenarioIndex, scenario] of scenarios.entries()) {
230
+ const entry = catalog.scenarios[scenarioIndex], sourceTurns = scenario.userJourney?.turns;
231
+ if (!exact(entry, ["scenarioId", "variantRole", "planRef", "turnCount", "turns"])
232
+ || !Array.isArray(sourceTurns) || entry.scenarioId !== scenario.id
233
+ || entry.variantRole !== scenario.variantRole || entry.planRef !== `plan:${scenario.id}`
234
+ || entry.turnCount !== sourceTurns.length || !Array.isArray(entry.turns)
235
+ || entry.turns.length !== sourceTurns.length) {
236
+ throw new Error("Registered public input scenario does not match the frozen base suite");
237
+ }
238
+ let amendmentUses = 0;
239
+ const turns = sourceTurns.map((source, index) => {
240
+ const amended = changed.has(scenario.id) && source.prompt === scenario.prompt;
241
+ if (amended) amendmentUses += 1;
242
+ const prompt = amended
243
+ ? registeredText(readRegisteredAsset(registeredMeasurement,
244
+ `measurement/prompts/${scenario.id}.md`), `prompt amendment ${scenario.id}`)
245
+ : suitePromptText(suiteRoot, resolveSuiteEntry, source.prompt,
246
+ `registered public input ${scenario.id}/${source.id}`);
247
+ const turn = Object.freeze({ id: source.id, message: prompt.text,
248
+ reconnectBefore: source.reconnectBefore === true, receiptUncertain: source.receiptUncertain === true,
249
+ ...(source.workflow ? { workflow: source.workflow } : {}) });
250
+ const projectedDigest = benchmarkVerificationRequestDigest(turn), registered = entry.turns[index];
251
+ const binding = { version: 1, suiteId: catalog.suiteId, scenarioId: scenario.id,
252
+ planRef: entry.planRef, variantRole: entry.variantRole, turnIndex: index + 1,
253
+ turnId: source.id, promptPath: source.prompt, promptSha256: prompt.sha256,
254
+ promptBytes: prompt.bytes, workflow: source.workflow ?? null,
255
+ reconnectBefore: source.reconnectBefore === true, receiptUncertain: source.receiptUncertain === true,
256
+ operatorRequestDigest: projectedDigest };
257
+ if (!exact(registered, ["index", "turnId", "promptPath", "promptSha256", "promptBytes", "workflow",
258
+ "reconnectBefore", "receiptUncertain", "operatorRequestDigest", "bindingDigest"])
259
+ || registered.index !== index + 1 || registered.turnId !== source.id
260
+ || registered.promptPath !== source.prompt || registered.promptSha256 !== prompt.sha256
261
+ || registered.promptBytes !== prompt.bytes || registered.workflow !== (source.workflow ?? null)
262
+ || registered.reconnectBefore !== (source.reconnectBefore === true)
263
+ || registered.receiptUncertain !== (source.receiptUncertain === true)
264
+ || registered.operatorRequestDigest !== projectedDigest
265
+ || registered.bindingDigest !== hash(JSON.stringify(binding))) {
266
+ throw new Error("Registered public turn does not match the dispatched input");
267
+ }
268
+ publicInputCount += 1;
269
+ return turn;
270
+ });
271
+ if (changed.has(scenario.id) !== (amendmentUses === 1)) {
272
+ throw new Error("Registered prompt amendment does not bind exactly one primary turn");
273
+ }
274
+ const primary = changed.has(scenario.id)
275
+ ? registeredText(readRegisteredAsset(registeredMeasurement,
276
+ `measurement/prompts/${scenario.id}.md`), `primary prompt ${scenario.id}`).text
277
+ : suitePromptText(suiteRoot, resolveSuiteEntry, scenario.prompt,
278
+ `registered primary prompt ${scenario.id}`).text;
279
+ const selected = entry.variantRole === "interaction"
280
+ ? turns.find(turn => turn.id === "implement") : turns[0];
281
+ if (!selected) throw new Error("Registered scenario has no primary verification turn");
282
+ inputs.set(scenario.id, freeze({ scenarioId: scenario.id, role: entry.variantRole,
283
+ prompt: primary, turns, selected }));
284
+ }
285
+ if (publicInputCount !== catalog.publicInputCount || changed.size !== payload.promptRolesChanged.length) {
286
+ throw new Error("Registered public input catalog count changed");
287
+ }
288
+ return Object.freeze({ catalog: freeze(catalog), catalogBytes, inputs });
289
+ }
290
+
291
+ /**
292
+ * Load the exact detached-registration plan assets. The registration is the
293
+ * human approval boundary; this loader still proves plan/input/runtime equality
294
+ * before creating any per-run host authority.
295
+ */
296
+ export function loadRegisteredBenchmarkVerificationPlan({
297
+ registeredMeasurement, installedRoot, suiteDigest, scenarios, suiteRoot, resolveSuiteEntry
298
+ }) {
299
+ const root = registeredMeasurement?.assetRoot;
300
+ if (typeof root !== "string" || !path.isAbsolute(root) || fs.realpathSync.native(root) !== root) {
301
+ throw new Error("Registered verification asset root is invalid");
302
+ }
303
+ if (inside(installedRoot, root) || inside(suiteRoot, root)) {
304
+ throw new Error("Registered verification assets must be outside candidate and base suite source");
305
+ }
306
+ if (registeredMeasurement.payload.baseSuiteDigest !== suiteDigest) {
307
+ throw new Error("Registered verification does not match the frozen base suite");
308
+ }
309
+ const verifierDigest = installedContractVerifierDigest(installedRoot);
310
+ const { catalogBytes, inputs } = registeredCatalogAndInputs({
311
+ registeredMeasurement, scenarios, suiteRoot, resolveSuiteEntry
312
+ });
313
+ const nodeBytes = readRegisteredAsset(registeredMeasurement, "measurement/node-workload-api-v1.json");
314
+ const nodeProfile = JSON.parse(nodeBytes);
315
+ if (nodeProfile?.schemaVersion !== 1 || nodeProfile?.kind !== "node-workload-api-profile-v1"
316
+ || nodeProfile?.profile?.digest !== registeredMeasurement.payload.nodeProfileDigest
317
+ || !/^sha256:[a-f0-9]{64}$/.test(String(nodeProfile?.workerImage?.id ?? ""))
318
+ || JSON.stringify(nodeProfile?.publicCoverage?.allScenarioIds) !== JSON.stringify(scenarios.map(item => item.id))) {
319
+ throw new Error("Registered Node verifier profile does not match the measurement");
320
+ }
321
+ const noncode = new Set(nodeProfile.publicCoverage.noncodeScenarioIds);
322
+ if (noncode.size !== 4 || nodeProfile.publicCoverage.codeRecipeCount !== 23
323
+ || nodeProfile.publicCoverage.noncodeProfileCount !== 4) {
324
+ throw new Error("Registered verifier route inventory is invalid");
325
+ }
326
+ const profile = installedJson(installedRoot, "adapters/node-typescript/profile.json", "Node profile");
327
+ const policy = installedJson(installedRoot, "packages/piagent-core/policies/base-policy.json", "base policy");
328
+ const approvedDockerSha256 = registeredMeasurement.payload.resources.verifiers
329
+ .find(item => item.id === "docker-runtime")?.sha256;
330
+ if (!HASH.test(String(approvedDockerSha256 ?? ""))) {
331
+ throw new Error("Registered Docker runtime identity is missing");
332
+ }
333
+ const planAssets = [], entries = [];
334
+ let dockerCommand = null;
335
+ for (const scenario of scenarios) {
336
+ const relativePath = `plans/${scenario.id}.json`, bytes = readRegisteredAsset(registeredMeasurement, relativePath);
337
+ let plan;
338
+ try { plan = JSON.parse(bytes); }
339
+ catch { throw new Error(`Registered verification plan is not JSON: ${scenario.id}`); }
340
+ registeredPlanForSurface(plan, "piagent");
341
+ registeredPlanForSurface(plan, "codex-cli");
342
+ const selectedDocker = plan.backend?.dockerCommand;
343
+ if (JSON.stringify(Object.keys(selectedDocker ?? {})) !== JSON.stringify(["path", "sha256"])
344
+ || typeof selectedDocker.path !== "string" || !path.isAbsolute(selectedDocker.path)
345
+ || path.normalize(selectedDocker.path) !== selectedDocker.path || selectedDocker.path.includes("\0")
346
+ || selectedDocker.sha256 !== approvedDockerSha256) {
347
+ throw new Error(`Registered Docker command binding is invalid: ${scenario.id}`);
348
+ }
349
+ let observedDocker;
350
+ try { observedDocker = benchmarkCommandIdentity(selectedDocker.path, { fullPackageClosure: false }); }
351
+ catch { throw new Error(`Registered Docker command is unavailable: ${scenario.id}`); }
352
+ if (observedDocker.resolvedPath !== selectedDocker.path
353
+ || observedDocker.contentDigest !== selectedDocker.sha256 || observedDocker.executable !== true) {
354
+ throw new Error(`Registered Docker command changed: ${scenario.id}`);
355
+ }
356
+ if (dockerCommand && JSON.stringify(dockerCommand) !== JSON.stringify(selectedDocker)) {
357
+ throw new Error("Registered plans disagree on the Docker command identity");
358
+ }
359
+ dockerCommand = freeze({ path: selectedDocker.path, sha256: selectedDocker.sha256 });
360
+ const input = inputs.get(scenario.id), receipt = benchmarkVerificationReceiptForTurn(input.selected, { profile, policy });
361
+ if (plan.schemaVersion !== 3 || plan.operatorRequestDigest !== benchmarkVerificationRequestDigest(input.selected)
362
+ || plan.backend.imageId !== nodeProfile.workerImage.id
363
+ || plan.contracts.length !== receipt.criteria.length) {
364
+ throw new Error(`Registered verification plan does not match its primary request: ${scenario.id}`);
365
+ }
366
+ const expectedRoute = noncode.has(scenario.id) ? "composite" : "code";
367
+ for (const [index, contract] of plan.contracts.entries()) {
368
+ const criterion = receipt.criteria[index];
369
+ if (contract.route !== expectedRoute || contract.criterionId !== criterion.criterionId
370
+ || contract.criterionHash !== criterion.criterionHash) {
371
+ throw new Error(`Registered verification criterion does not match runtime intake: ${scenario.id}`);
372
+ }
373
+ if (contract.route === "composite") {
374
+ const identity = contract.planContext.identity;
375
+ if (!exact(identity, ["suiteDigest", "configDigest", "armDigests"])
376
+ || !exact(identity.armDigests, ["piagent", "codex-cli"])
377
+ || ![identity.suiteDigest, identity.configDigest, identity.armDigests.piagent,
378
+ identity.armDigests["codex-cli"]].every(value => HASH.test(value))) {
379
+ throw new Error(`Registered composite arm identities are incomplete: ${scenario.id}`);
380
+ }
381
+ const publicContract = JSON.parse(contract.planContext.contractText);
382
+ if (publicContract.criterionIndex !== index || publicContract.criterionId !== criterion.criterionId
383
+ || publicContract.criterionHash !== criterion.criterionHash
384
+ || publicContract.criterionText !== criterion.criterionText) {
385
+ throw new Error(`Registered composite criterion text does not match runtime intake: ${scenario.id}`);
386
+ }
387
+ }
388
+ }
389
+ planAssets.push(Object.freeze({ path: relativePath, sha256: hash(bytes), bytes: bytes.length }));
390
+ entries.push(Object.freeze({ scenarioId: scenario.id, plans: [freeze(plan)] }));
391
+ }
392
+ const boundAssets = [
393
+ { path: "catalog.json", sha256: hash(catalogBytes), bytes: catalogBytes.length },
394
+ { path: "measurement/node-workload-api-v1.json", sha256: hash(nodeBytes), bytes: nodeBytes.length },
395
+ ...registeredMeasurement.payload.promptRolesChanged.map(id => {
396
+ const relativePath = `measurement/prompts/${id}.md`,
397
+ inventory = registeredMeasurement.inventory.entries.find(item => item.path === relativePath);
398
+ return { path: relativePath, sha256: inventory.sha256, bytes: inventory.bytes };
399
+ }),
400
+ ...planAssets
401
+ ];
402
+ const contentDigest = hash(JSON.stringify(boundAssets)), catalog = freeze({
403
+ schemaVersion: 2, kind: NODE_BENCHMARK_VERIFICATION_PLAN_VERSION,
404
+ suiteDigest, verifierDigest, scenarios: entries
405
+ });
406
+ const identity = freeze({ kind: catalog.kind, contentDigest, suiteDigest, verifierDigest,
407
+ scenarios: entries.map(entry => ({ scenarioId: entry.scenarioId,
408
+ requests: entry.plans.map(plan => ({ operatorRequestDigest: plan.operatorRequestDigest,
409
+ criterionCount: plan.contracts.length, criteria: plan.contracts.map(contract => ({
410
+ criterionId: contract.criterionId, criterionHash: contract.criterionHash
411
+ })) })) })) });
412
+ const isCurrent = () => {
413
+ try {
414
+ return installedContractVerifierDigest(installedRoot) === verifierDigest
415
+ && boundAssets.every(asset => hash(readRegisteredAsset(registeredMeasurement, asset.path)) === asset.sha256);
416
+ } catch { return false; }
417
+ };
418
+ if (!dockerCommand) throw new Error("Registered Docker command binding is unavailable");
419
+ return Object.freeze({ identity, isCurrent, dockerCommand,
420
+ registeredSuiteId: registeredMeasurement.payload.suiteId,
421
+ measurementConfigurationDigest: registeredMeasurement.payload.sharedEnvironmentDigest,
422
+ registeredInput(scenarioId) {
423
+ if (!isCurrent()) throw new Error("Registered measurement input or verifier changed");
424
+ return inputs.get(scenarioId) ?? null;
425
+ },
426
+ prepare({ scenarioId, surface, projectRoot, directory, approved = false }) {
427
+ if (surface !== "piagent") return null;
428
+ if (approved !== true) throw new Error("Registered benchmark verification is not approved");
429
+ if (!isCurrent()) throw new Error("Registered benchmark verification changed");
430
+ const entry = entries.find(item => item.scenarioId === scenarioId);
431
+ if (!entry) return Object.freeze({ environment: Object.freeze({}), observe: () => freeze({ schemaVersion: 1,
432
+ planDigest: contentDigest, status: "not-configured", attempts: 0, workersObserved: 0, requests: [] }) });
433
+ const plans = entry.plans.map(plan => registeredPlanForSurface(plan, surface));
434
+ const { configPath } = writeHostContractApproval({
435
+ directory, projectRoot, installedRoot, plans, approved: true
436
+ });
437
+ return Object.freeze({ environment: Object.freeze({ PIAGENT_INDEPENDENT_VERIFICATION_CONFIG: configPath }),
438
+ observe(tasks) { return observeRequests({ configPath, projectRoot, installedRoot, plans,
439
+ planDigest: contentDigest, tasks, isCurrent }); } });
440
+ }
441
+ });
442
+ }
443
+
444
+ function readPlan(file) {
445
+ if (!path.isAbsolute(file) || fs.realpathSync.native(file) !== file) throw new Error("Verification plan path must be canonical");
446
+ const fd = fs.openSync(file, fs.constants.O_RDONLY | fs.constants.O_NOFOLLOW);
447
+ try {
448
+ const stat = fs.fstatSync(fd);
449
+ if (!stat.isFile() || stat.nlink !== 1 || stat.uid !== process.getuid() || (stat.mode & 0o077) !== 0
450
+ || stat.size < 1 || stat.size > 2 * 1024 * 1024) throw new Error("Verification plan must be a private bounded host file");
451
+ const bytes = fs.readFileSync(fd), after = fs.fstatSync(fd), current = fs.lstatSync(file);
452
+ if (bytes.length !== stat.size || current.isSymbolicLink()
453
+ || ["dev", "ino", "size", "mode", "nlink", "mtimeMs", "ctimeMs"].some(key => stat[key] !== after[key] || stat[key] !== current[key])) {
454
+ throw new Error("Verification plan changed during read");
455
+ }
456
+ return bytes;
457
+ } finally { fs.closeSync(fd); }
458
+ }
459
+
460
+ /** Structural validation is not operator approval or source/plan authentication. */
461
+ export function validateBenchmarkVerificationPlan(value) {
462
+ const nodeProfile = value?.schemaVersion === 2 && value?.kind === NODE_BENCHMARK_VERIFICATION_PLAN_VERSION;
463
+ if (!exact(value, ["schemaVersion", "kind", "suiteDigest", "verifierDigest", "scenarios"])
464
+ || !nodeProfile && (value.schemaVersion !== 1 || value.kind !== BENCHMARK_VERIFICATION_PLAN_VERSION)
465
+ || !HASH.test(value.suiteDigest) || !HASH.test(value.verifierDigest)
466
+ || !Array.isArray(value.scenarios) || value.scenarios.length < 1 || value.scenarios.length > 100) {
467
+ throw new TypeError("Invalid benchmark verification catalog");
468
+ }
469
+ const seen = new Set();
470
+ for (const entry of value.scenarios) {
471
+ if (!exact(entry, ["scenarioId", "plans"]) || typeof entry.scenarioId !== "string"
472
+ || !/^[a-z0-9][a-z0-9._-]{0,79}$/.test(entry.scenarioId) || seen.has(entry.scenarioId)) {
473
+ throw new TypeError("Invalid or duplicate verification scenario");
474
+ }
475
+ seen.add(entry.scenarioId);
476
+ validateHostContractPlan({ schemaVersion: nodeProfile ? 4 : 2, plans: entry.plans });
477
+ }
478
+ return value;
479
+ }
480
+
481
+ /** Read and bind operator-authored expected results; never derive them from a candidate or grader. */
482
+ export function loadBenchmarkVerificationPlan({ file, installedRoot, suiteDigest, scenarios, suiteRoot, resolveSuiteEntry }) {
483
+ if (inside(installedRoot, file) || inside(suiteRoot, file)) throw new Error("Verification catalog must be outside candidate and suite source");
484
+ const bytes = readPlan(file), value = validateBenchmarkVerificationPlan(JSON.parse(bytes));
485
+ if (value.suiteDigest !== suiteDigest || value.verifierDigest !== installedContractVerifierDigest(installedRoot)) {
486
+ throw new Error("Verification plan does not match the frozen suite and installed verifier");
487
+ }
488
+ const known = new Map(scenarios.map(scenario => [scenario.id, scenario]));
489
+ for (const entry of value.scenarios) {
490
+ const scenario = known.get(entry.scenarioId);
491
+ if (!scenario) throw new Error("Unknown verification scenario");
492
+ // Piagent journeys dispatch workflow metadata before automatic intake.
493
+ // Baseline surfaces receive no approval and keep their own raw turn text.
494
+ const turns = resolvedJourneyTurns(scenario, suiteRoot, resolveSuiteEntry) ?? [{ message: fs.readFileSync(
495
+ resolveSuiteEntry(suiteRoot, scenario.prompt, "verification public prompt"), "utf8").trim() }];
496
+ const requests = new Map();
497
+ for (const turn of turns) {
498
+ const digest = benchmarkVerificationRequestDigest(turn), source = JSON.stringify([turn.workflow ?? null, turn.message]);
499
+ if (requests.has(digest) && requests.get(digest) !== source) throw new Error("Ambiguous verification request identity after normalization");
500
+ requests.set(digest, source);
501
+ }
502
+ if (entry.plans.some(plan => !requests.has(plan.operatorRequestDigest))) throw new Error("Verification plan authorizes a request not sent by this scenario");
503
+ }
504
+ const catalog = freeze(value);
505
+ const identity = freeze({ kind: catalog.kind, contentDigest: hash(bytes),
506
+ suiteDigest, verifierDigest: catalog.verifierDigest,
507
+ scenarios: catalog.scenarios.map(entry => ({ scenarioId: entry.scenarioId,
508
+ requests: entry.plans.map(plan => ({ operatorRequestDigest: plan.operatorRequestDigest, criterionCount: plan.contracts.length,
509
+ criteria: plan.contracts.map(contract => ({ criterionId: contract.criterionId, criterionHash: contract.criterionHash })) })) })) });
510
+ const isCurrent = () => {
511
+ try { return hash(readPlan(file)) === identity.contentDigest && installedContractVerifierDigest(installedRoot) === identity.verifierDigest; }
512
+ catch { return false; }
513
+ };
514
+ return Object.freeze({ identity, isCurrent,
515
+ prepare({ scenarioId, surface, projectRoot, directory, approved = false }) {
516
+ if (surface !== "piagent") return null;
517
+ if (approved !== true) throw new Error("Benchmark verification requires explicit --approve-verification");
518
+ if (inside(projectRoot, file)) throw new Error("Verification catalog must be outside the candidate project");
519
+ if (!isCurrent()) throw new Error("Frozen benchmark verification plan or verifier changed");
520
+ const entry = catalog.scenarios.find(item => item.scenarioId === scenarioId);
521
+ if (!entry) return Object.freeze({ environment: Object.freeze({}), observe: () => freeze({ schemaVersion: 1,
522
+ planDigest: identity.contentDigest, status: "not-configured", attempts: 0, workersObserved: 0, requests: [] }) });
523
+ const { configPath } = writeHostContractApproval({ directory, projectRoot, installedRoot, plans: entry.plans, approved: true });
524
+ return Object.freeze({ environment: Object.freeze({ PIAGENT_INDEPENDENT_VERIFICATION_CONFIG: configPath }),
525
+ observe(tasks) { return observeRequests({ configPath, projectRoot, installedRoot, plans: entry.plans,
526
+ planDigest: identity.contentDigest, tasks, isCurrent }); } });
527
+ }
528
+ });
529
+ }
530
+
531
+ /** Observation only, never completion authority. Keep failures and pending attempts in the denominator. */
532
+ function observeRequests({ configPath, projectRoot, installedRoot, plans, planDigest, tasks, isCurrent }) {
533
+ let config;
534
+ try {
535
+ if (!isCurrent()) throw new Error("Plan drift");
536
+ if (!Array.isArray(tasks) || tasks.length > 1000 || tasks.some(task => typeof task?.taskRunId !== "string")
537
+ || new Set(tasks.map(task => task.taskRunId)).size !== tasks.length) throw new Error("Invalid task observation");
538
+ config = openHostContractConfiguration({ configPath, projectRoot, installedRoot });
539
+ let attempts = 0, workersObserved = 0, complete = true;
540
+ const requests = plans.map(plan => {
541
+ const matched = tasks.filter(task => task.operatorRequestDigest === plan.operatorRequestDigest);
542
+ if (matched.length === 0) complete = false;
543
+ const nodeProfile = plan.schemaVersion === 3;
544
+ const profile = nodeProfile ? plan.backend.profile : undefined;
545
+ const templateFor = contract => compileIndependentContract(JSON.stringify({ schemaVersion: nodeProfile ? 2 : 1,
546
+ ...(nodeProfile ? { profile } : {}), source: "export const placeholder=0;", exportName: contract.exportName, checks: contract.checks }));
547
+ const codeContract = plan.contracts.find(contract => contract.route !== "composite");
548
+ const compilerVersion = codeContract ? templateFor(codeContract).version : null;
549
+ const backendDigest = compilerVersion ? hash(JSON.stringify([DURABLE_EXECUTION_VERSION, compilerVersion,
550
+ EXECUTION_SNAPSHOT_VERSION, plan.backend.imageId, plan.backend.dockerSocket,
551
+ plan.backend.dockerCommand, plan.backend.timeoutMs, profile ?? null,
552
+ ...(plan.backend.startupAllowanceMs ? [plan.backend.startupAllowanceMs] : [])])) : null;
553
+ const publicationStore = plan.contracts.some(contract => contract.route === "composite")
554
+ ? config.withCompositeRecovery(({ key, directory, projectRoot: approvedRoot }) =>
555
+ openCompositeTaskPublicationStore({ key, directory, projectRoot: approvedRoot })) : null;
556
+ const runs = matched.map(task => ({ taskRunId: task.taskRunId, criteria: plan.contracts.map(contract => {
557
+ if (contract.route === "composite") {
558
+ const result = { criterionId: contract.criterionId, criterionHash: contract.criterionHash,
559
+ attempts: 0, phase: "not-observed", verdict: null, workerObserved: false };
560
+ if (!publicationStore || typeof task.sessionId !== "string") { complete = false; return result; }
561
+ const record = publicationStore.read(task.taskRunId, task.sessionId);
562
+ if (!record) { complete = false; return result; }
563
+ result.attempts = 1; attempts += 1;
564
+ const matching = task.acceptanceReceipt?.criteria.some(criterion =>
565
+ criterion.id === contract.criterionId && criterion.hash === contract.criterionHash);
566
+ const entry = record.entries.find(item => item.criterionId === contract.criterionId);
567
+ const taskDigest = compositeTaskPublicationDigest(task);
568
+ const taskBound = task.trace?.outcome === "completed"
569
+ ? taskDigest === record.terminalTaskDigest : taskDigest === record.pendingTaskDigest;
570
+ if (!matching || !entry || entry.criterionHash !== contract.criterionHash
571
+ || record.operatorRequestDigest !== plan.operatorRequestDigest || !taskBound) {
572
+ complete = false; result.phase = "binding-mismatch"; return result;
573
+ }
574
+ const status = publicationStore.inspect(record).statuses.find(item =>
575
+ item.criterionId === contract.criterionId)?.status;
576
+ if (status !== "task-completed" || task.trace?.outcome !== "completed") {
577
+ complete = false; result.phase = "reserved"; return result;
578
+ }
579
+ result.phase = "settled"; result.verdict = "pass";
580
+ // The legacy field name is retained for report compatibility. Here it
581
+ // means the host observer re-opened a signed, fully settled composite
582
+ // publication; it does not claim that a code worker ran.
583
+ result.workerObserved = true; workersObserved += 1;
584
+ return result;
585
+ }
586
+ const event = config.store.latest({ taskRunId: task.taskRunId, criterionId: contract.criterionId });
587
+ const result = { criterionId: contract.criterionId, criterionHash: contract.criterionHash,
588
+ attempts: event?.attempt ?? 0, phase: event?.phase ?? "not-observed", verdict: null, workerObserved: false };
589
+ attempts += result.attempts;
590
+ const matching = task.acceptanceReceipt?.criteria.some(criterion => criterion.id === contract.criterionId && criterion.hash === contract.criterionHash);
591
+ if (!matching || !event || event.binding.criterionHash !== contract.criterionHash
592
+ || event.binding.verifierDigest !== config.payload.verifierDigest || event.binding.backendDigest !== backendDigest) {
593
+ complete = false; result.phase = event ? "binding-mismatch" : "not-observed"; return result;
594
+ }
595
+ if (event.phase !== "settled") { complete = false; return result; }
596
+ const evidence = JSON.parse(event.evidenceText);
597
+ if (evidence.version !== DURABLE_EXECUTION_VERSION || evidence.snapshotDigest !== event.binding.snapshotDigest
598
+ || evidence.planDigest !== event.binding.planDigest || !["pass", "fail", "unknown", "error"].includes(evidence.verdict)) {
599
+ complete = false; result.phase = "invalid-evidence"; return result;
600
+ }
601
+ result.verdict = evidence.verdict;
602
+ const observed = evidence.observed, execution = observed?.result?.execution;
603
+ const template = templateFor(contract);
604
+ if (observed?.snapshotDigest === event.binding.snapshotDigest && observed.result?.version === template.version
605
+ && observed.result.planDigest === event.binding.planDigest && execution?.runId === event.attemptId
606
+ && execution.imageId === plan.backend.imageId && HASH.test(execution.sourceDigest) && HASH.test(execution.requestDigest)
607
+ && execution.observation && execution.cleanupConfirmed === true) {
608
+ const response = parseResponse(JSON.stringify(execution.observation), parseRequest(template.requestText), execution.requestDigest);
609
+ const compared = compareIndependentExecution({ ...template, planDigest: event.binding.planDigest }, execution);
610
+ result.workerObserved = response.status === execution.status && compared.verdict === evidence.verdict
611
+ && compared.verdict === observed.verdict && compared.verdict === observed.result.verdict
612
+ && JSON.stringify(compared.checks) === JSON.stringify(observed.result.checks)
613
+ && JSON.stringify(compared.counterexamples) === JSON.stringify(observed.result.counterexamples);
614
+ }
615
+ if (result.workerObserved) workersObserved += 1;
616
+ else complete = false;
617
+ return result;
618
+ }) }));
619
+ return { operatorRequestDigest: plan.operatorRequestDigest, runs };
620
+ });
621
+ if (!config.isCurrent() || !isCurrent()) throw new Error("Approval drift");
622
+ return freeze({ schemaVersion: 1, planDigest, status: complete ? "observed" : "partial", attempts, workersObserved, requests });
623
+ } catch {
624
+ // Usage has already been collected by the caller. Invalid verification
625
+ // evidence must not discard the paid attempt or reveal private plan data.
626
+ return freeze({ schemaVersion: 1, planDigest, status: "unavailable", attempts: null, workersObserved: null, requests: [] });
627
+ } finally { config?.close(); }
628
+ }