devlyn-cli 3.2.0 → 3.3.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (424) hide show
  1. package/AGENTS.md +2 -2
  2. package/CLAUDE.md +2 -2
  3. package/README.md +22 -113
  4. package/bin/devlyn.js +13 -225
  5. package/bin/instruction-templates.json +752 -1
  6. package/bin/instructions.js +101 -17
  7. package/config/skills/_shared/adapters/grok.md +1 -2
  8. package/config/skills/_shared/archive_run.py +15 -3
  9. package/config/skills/_shared/judge-role-evidence.py +21 -1
  10. package/config/skills/_shared/runtime-principles.md +1 -1
  11. package/config/skills/_shared/spec-verify-check.py +0 -653
  12. package/config/skills/_shared/state-phase-write.py +371 -30
  13. package/config/skills/_shared/task-complete.py +635 -143
  14. package/config/skills/_shared/terminal-claim-check.py +229 -4
  15. package/config/skills/_shared/verify-merge-findings.py +93 -2
  16. package/config/skills/devlyn:ideate/SKILL.md +3 -4
  17. package/config/skills/devlyn:ideate/references/elicitation.md +2 -35
  18. package/config/skills/devlyn:ideate/references/from-spec-mode.md +3 -18
  19. package/config/skills/devlyn:ideate/references/project-mode.md +1 -16
  20. package/config/skills/devlyn:ideate/references/spec-template.md +0 -2
  21. package/config/skills/devlyn:queue/SKILL.md +6 -4
  22. package/config/skills/devlyn:resolve/SKILL.md +16 -25
  23. package/config/skills/devlyn:resolve/references/free-form-mode.md +0 -14
  24. package/config/skills/devlyn:resolve/references/outer-loop.md +1 -1
  25. package/config/skills/devlyn:resolve/references/phases/build-gate.md +1 -1
  26. package/config/skills/devlyn:resolve/references/phases/cleanup.md +3 -3
  27. package/config/skills/devlyn:resolve/references/phases/implement.md +1 -1
  28. package/config/skills/devlyn:resolve/references/phases/probe-derive.md +1 -16
  29. package/config/skills/devlyn:resolve/references/phases/verify.md +4 -9
  30. package/config/skills/devlyn:resolve/references/state-schema.md +9 -7
  31. package/config/skills/devlyn:resolve/references/task-completion.md +46 -37
  32. package/{config/skills → optional-skills}/code-health-standards/SKILL.md +4 -13
  33. package/{config/skills → optional-skills}/code-review-standards/SKILL.md +4 -12
  34. package/{config/skills → optional-skills}/root-cause-analysis/SKILL.md +4 -12
  35. package/{config/skills → optional-skills}/ui-implementation-standards/SKILL.md +4 -14
  36. package/package.json +1 -57
  37. package/benchmark/auto-resolve/BENCHMARK-DESIGN.md +0 -289
  38. package/benchmark/auto-resolve/BENCHMARK-RESULTS.md +0 -341
  39. package/benchmark/auto-resolve/README.md +0 -696
  40. package/benchmark/auto-resolve/RUBRIC.md +0 -177
  41. package/benchmark/auto-resolve/fixtures/F1-cli-trivial-flag/NOTES.md +0 -34
  42. package/benchmark/auto-resolve/fixtures/F1-cli-trivial-flag/expected.json +0 -68
  43. package/benchmark/auto-resolve/fixtures/F1-cli-trivial-flag/metadata.json +0 -10
  44. package/benchmark/auto-resolve/fixtures/F1-cli-trivial-flag/setup.sh +0 -4
  45. package/benchmark/auto-resolve/fixtures/F1-cli-trivial-flag/spec.md +0 -44
  46. package/benchmark/auto-resolve/fixtures/F1-cli-trivial-flag/task.ko.txt +0 -8
  47. package/benchmark/auto-resolve/fixtures/F1-cli-trivial-flag/task.txt +0 -8
  48. package/benchmark/auto-resolve/fixtures/F10-persist-write-collision/NOTES.md +0 -68
  49. package/benchmark/auto-resolve/fixtures/F10-persist-write-collision/expected.json +0 -60
  50. package/benchmark/auto-resolve/fixtures/F10-persist-write-collision/metadata.json +0 -10
  51. package/benchmark/auto-resolve/fixtures/F10-persist-write-collision/setup.sh +0 -17
  52. package/benchmark/auto-resolve/fixtures/F10-persist-write-collision/spec.md +0 -51
  53. package/benchmark/auto-resolve/fixtures/F10-persist-write-collision/task.txt +0 -9
  54. package/benchmark/auto-resolve/fixtures/F10-persist-write-collision/verifiers/invalid.js +0 -29
  55. package/benchmark/auto-resolve/fixtures/F10-persist-write-collision/verifiers/parallel.js +0 -50
  56. package/benchmark/auto-resolve/fixtures/F11-batch-import-all-or-nothing/NOTES.md +0 -75
  57. package/benchmark/auto-resolve/fixtures/F11-batch-import-all-or-nothing/expected.json +0 -52
  58. package/benchmark/auto-resolve/fixtures/F11-batch-import-all-or-nothing/metadata.json +0 -10
  59. package/benchmark/auto-resolve/fixtures/F11-batch-import-all-or-nothing/setup.sh +0 -171
  60. package/benchmark/auto-resolve/fixtures/F11-batch-import-all-or-nothing/spec.md +0 -50
  61. package/benchmark/auto-resolve/fixtures/F11-batch-import-all-or-nothing/task.txt +0 -9
  62. package/benchmark/auto-resolve/fixtures/F12-webhook-raw-body-signature/NOTES.md +0 -89
  63. package/benchmark/auto-resolve/fixtures/F12-webhook-raw-body-signature/expected.json +0 -74
  64. package/benchmark/auto-resolve/fixtures/F12-webhook-raw-body-signature/metadata.json +0 -10
  65. package/benchmark/auto-resolve/fixtures/F12-webhook-raw-body-signature/setup.sh +0 -251
  66. package/benchmark/auto-resolve/fixtures/F12-webhook-raw-body-signature/spec.md +0 -57
  67. package/benchmark/auto-resolve/fixtures/F12-webhook-raw-body-signature/task.txt +0 -13
  68. package/benchmark/auto-resolve/fixtures/F12-webhook-raw-body-signature/verifiers/replay-malformed-body.js +0 -64
  69. package/benchmark/auto-resolve/fixtures/F15-frozen-diff-race-review/NOTES.md +0 -104
  70. package/benchmark/auto-resolve/fixtures/F15-frozen-diff-race-review/expected.json +0 -46
  71. package/benchmark/auto-resolve/fixtures/F15-frozen-diff-race-review/metadata.json +0 -10
  72. package/benchmark/auto-resolve/fixtures/F15-frozen-diff-race-review/setup.sh +0 -336
  73. package/benchmark/auto-resolve/fixtures/F15-frozen-diff-race-review/spec.md +0 -51
  74. package/benchmark/auto-resolve/fixtures/F15-frozen-diff-race-review/task.txt +0 -9
  75. package/benchmark/auto-resolve/fixtures/F16-cli-quote-tax-rules/NOTES.md +0 -38
  76. package/benchmark/auto-resolve/fixtures/F16-cli-quote-tax-rules/expected.json +0 -64
  77. package/benchmark/auto-resolve/fixtures/F16-cli-quote-tax-rules/metadata.json +0 -10
  78. package/benchmark/auto-resolve/fixtures/F16-cli-quote-tax-rules/setup.sh +0 -32
  79. package/benchmark/auto-resolve/fixtures/F16-cli-quote-tax-rules/spec.md +0 -63
  80. package/benchmark/auto-resolve/fixtures/F16-cli-quote-tax-rules/task.txt +0 -7
  81. package/benchmark/auto-resolve/fixtures/F16-cli-quote-tax-rules/verifiers/exact-success.js +0 -54
  82. package/benchmark/auto-resolve/fixtures/F16-cli-quote-tax-rules/verifiers/no-hardcoded-pricing.js +0 -47
  83. package/benchmark/auto-resolve/fixtures/F16-cli-quote-tax-rules/verifiers/stock-error.js +0 -45
  84. package/benchmark/auto-resolve/fixtures/F2-cli-medium-subcommand/NOTES.md +0 -57
  85. package/benchmark/auto-resolve/fixtures/F2-cli-medium-subcommand/expected-pair-plan-registry.json +0 -170
  86. package/benchmark/auto-resolve/fixtures/F2-cli-medium-subcommand/expected.json +0 -84
  87. package/benchmark/auto-resolve/fixtures/F2-cli-medium-subcommand/metadata.json +0 -21
  88. package/benchmark/auto-resolve/fixtures/F2-cli-medium-subcommand/pair-plan.sample-fail.json +0 -214
  89. package/benchmark/auto-resolve/fixtures/F2-cli-medium-subcommand/pair-plan.sample-pass.json +0 -223
  90. package/benchmark/auto-resolve/fixtures/F2-cli-medium-subcommand/setup.sh +0 -5
  91. package/benchmark/auto-resolve/fixtures/F2-cli-medium-subcommand/spec.md +0 -55
  92. package/benchmark/auto-resolve/fixtures/F2-cli-medium-subcommand/task.txt +0 -14
  93. package/benchmark/auto-resolve/fixtures/F21-cli-scheduler-priority/NOTES.md +0 -39
  94. package/benchmark/auto-resolve/fixtures/F21-cli-scheduler-priority/expected.json +0 -62
  95. package/benchmark/auto-resolve/fixtures/F21-cli-scheduler-priority/metadata.json +0 -10
  96. package/benchmark/auto-resolve/fixtures/F21-cli-scheduler-priority/setup.sh +0 -2
  97. package/benchmark/auto-resolve/fixtures/F21-cli-scheduler-priority/spec.md +0 -67
  98. package/benchmark/auto-resolve/fixtures/F21-cli-scheduler-priority/task.txt +0 -7
  99. package/benchmark/auto-resolve/fixtures/F21-cli-scheduler-priority/verifiers/error-order.js +0 -55
  100. package/benchmark/auto-resolve/fixtures/F21-cli-scheduler-priority/verifiers/priority-blocked.js +0 -48
  101. package/benchmark/auto-resolve/fixtures/F22-cli-ledger-close/NOTES.md +0 -35
  102. package/benchmark/auto-resolve/fixtures/F22-cli-ledger-close/expected.json +0 -56
  103. package/benchmark/auto-resolve/fixtures/F22-cli-ledger-close/metadata.json +0 -10
  104. package/benchmark/auto-resolve/fixtures/F22-cli-ledger-close/setup.sh +0 -2
  105. package/benchmark/auto-resolve/fixtures/F22-cli-ledger-close/spec.md +0 -64
  106. package/benchmark/auto-resolve/fixtures/F22-cli-ledger-close/task.txt +0 -7
  107. package/benchmark/auto-resolve/fixtures/F22-cli-ledger-close/verifiers/conflicting-duplicate.js +0 -34
  108. package/benchmark/auto-resolve/fixtures/F22-cli-ledger-close/verifiers/idempotent-close.js +0 -41
  109. package/benchmark/auto-resolve/fixtures/F23-cli-fulfillment-wave/NOTES.md +0 -39
  110. package/benchmark/auto-resolve/fixtures/F23-cli-fulfillment-wave/expected.json +0 -56
  111. package/benchmark/auto-resolve/fixtures/F23-cli-fulfillment-wave/metadata.json +0 -10
  112. package/benchmark/auto-resolve/fixtures/F23-cli-fulfillment-wave/setup.sh +0 -2
  113. package/benchmark/auto-resolve/fixtures/F23-cli-fulfillment-wave/spec.md +0 -76
  114. package/benchmark/auto-resolve/fixtures/F23-cli-fulfillment-wave/task.txt +0 -7
  115. package/benchmark/auto-resolve/fixtures/F23-cli-fulfillment-wave/verifiers/priority-rollback.js +0 -64
  116. package/benchmark/auto-resolve/fixtures/F23-cli-fulfillment-wave/verifiers/single-warehouse-fefo.js +0 -66
  117. package/benchmark/auto-resolve/fixtures/F25-cli-cart-promotion-rules/NOTES.md +0 -40
  118. package/benchmark/auto-resolve/fixtures/F25-cli-cart-promotion-rules/expected.json +0 -66
  119. package/benchmark/auto-resolve/fixtures/F25-cli-cart-promotion-rules/metadata.json +0 -10
  120. package/benchmark/auto-resolve/fixtures/F25-cli-cart-promotion-rules/setup.sh +0 -36
  121. package/benchmark/auto-resolve/fixtures/F25-cli-cart-promotion-rules/spec.md +0 -71
  122. package/benchmark/auto-resolve/fixtures/F25-cli-cart-promotion-rules/task.txt +0 -7
  123. package/benchmark/auto-resolve/fixtures/F25-cli-cart-promotion-rules/verifiers/catalog-source.js +0 -57
  124. package/benchmark/auto-resolve/fixtures/F25-cli-cart-promotion-rules/verifiers/exact-success.js +0 -63
  125. package/benchmark/auto-resolve/fixtures/F25-cli-cart-promotion-rules/verifiers/stock-error.js +0 -34
  126. package/benchmark/auto-resolve/fixtures/F26-cli-payout-ledger-rules/NOTES.md +0 -31
  127. package/benchmark/auto-resolve/fixtures/F26-cli-payout-ledger-rules/expected.json +0 -68
  128. package/benchmark/auto-resolve/fixtures/F26-cli-payout-ledger-rules/metadata.json +0 -10
  129. package/benchmark/auto-resolve/fixtures/F26-cli-payout-ledger-rules/setup.sh +0 -17
  130. package/benchmark/auto-resolve/fixtures/F26-cli-payout-ledger-rules/spec.md +0 -68
  131. package/benchmark/auto-resolve/fixtures/F26-cli-payout-ledger-rules/task.txt +0 -7
  132. package/benchmark/auto-resolve/fixtures/F26-cli-payout-ledger-rules/verifiers/conflicting-duplicate.js +0 -29
  133. package/benchmark/auto-resolve/fixtures/F26-cli-payout-ledger-rules/verifiers/exact-payout.js +0 -58
  134. package/benchmark/auto-resolve/fixtures/F26-cli-payout-ledger-rules/verifiers/rules-source.js +0 -56
  135. package/benchmark/auto-resolve/fixtures/F3-backend-contract-risk/NOTES.md +0 -35
  136. package/benchmark/auto-resolve/fixtures/F3-backend-contract-risk/expected-pair-plan-registry.json +0 -162
  137. package/benchmark/auto-resolve/fixtures/F3-backend-contract-risk/expected.json +0 -67
  138. package/benchmark/auto-resolve/fixtures/F3-backend-contract-risk/metadata.json +0 -19
  139. package/benchmark/auto-resolve/fixtures/F3-backend-contract-risk/setup.sh +0 -4
  140. package/benchmark/auto-resolve/fixtures/F3-backend-contract-risk/spec.md +0 -55
  141. package/benchmark/auto-resolve/fixtures/F3-backend-contract-risk/task.txt +0 -9
  142. package/benchmark/auto-resolve/fixtures/F31-cli-seat-rebalance/NOTES.md +0 -34
  143. package/benchmark/auto-resolve/fixtures/F31-cli-seat-rebalance/expected.json +0 -57
  144. package/benchmark/auto-resolve/fixtures/F31-cli-seat-rebalance/metadata.json +0 -10
  145. package/benchmark/auto-resolve/fixtures/F31-cli-seat-rebalance/setup.sh +0 -2
  146. package/benchmark/auto-resolve/fixtures/F31-cli-seat-rebalance/spec.md +0 -67
  147. package/benchmark/auto-resolve/fixtures/F31-cli-seat-rebalance/task.txt +0 -7
  148. package/benchmark/auto-resolve/fixtures/F31-cli-seat-rebalance/verifiers/duplicate-event-error.js +0 -35
  149. package/benchmark/auto-resolve/fixtures/F31-cli-seat-rebalance/verifiers/priority-transfer-rollback.js +0 -53
  150. package/benchmark/auto-resolve/fixtures/F32-cli-subscription-renewal/NOTES.md +0 -38
  151. package/benchmark/auto-resolve/fixtures/F32-cli-subscription-renewal/expected.json +0 -57
  152. package/benchmark/auto-resolve/fixtures/F32-cli-subscription-renewal/metadata.json +0 -10
  153. package/benchmark/auto-resolve/fixtures/F32-cli-subscription-renewal/setup.sh +0 -2
  154. package/benchmark/auto-resolve/fixtures/F32-cli-subscription-renewal/spec.md +0 -70
  155. package/benchmark/auto-resolve/fixtures/F32-cli-subscription-renewal/task.txt +0 -3
  156. package/benchmark/auto-resolve/fixtures/F32-cli-subscription-renewal/verifiers/duplicate-renewal-error.js +0 -42
  157. package/benchmark/auto-resolve/fixtures/F32-cli-subscription-renewal/verifiers/priority-credit-rollback.js +0 -70
  158. package/benchmark/auto-resolve/fixtures/F4-web-browser-design/NOTES.md +0 -47
  159. package/benchmark/auto-resolve/fixtures/F4-web-browser-design/expected.json +0 -57
  160. package/benchmark/auto-resolve/fixtures/F4-web-browser-design/metadata.json +0 -10
  161. package/benchmark/auto-resolve/fixtures/F4-web-browser-design/setup.sh +0 -6
  162. package/benchmark/auto-resolve/fixtures/F4-web-browser-design/spec.md +0 -48
  163. package/benchmark/auto-resolve/fixtures/F4-web-browser-design/task.txt +0 -9
  164. package/benchmark/auto-resolve/fixtures/F5-fix-loop-red-green/NOTES.md +0 -45
  165. package/benchmark/auto-resolve/fixtures/F5-fix-loop-red-green/expected.json +0 -65
  166. package/benchmark/auto-resolve/fixtures/F5-fix-loop-red-green/metadata.json +0 -10
  167. package/benchmark/auto-resolve/fixtures/F5-fix-loop-red-green/setup.sh +0 -55
  168. package/benchmark/auto-resolve/fixtures/F5-fix-loop-red-green/spec.md +0 -48
  169. package/benchmark/auto-resolve/fixtures/F5-fix-loop-red-green/task.txt +0 -7
  170. package/benchmark/auto-resolve/fixtures/F6-dep-audit-native-module/NOTES.md +0 -43
  171. package/benchmark/auto-resolve/fixtures/F6-dep-audit-native-module/expected.json +0 -77
  172. package/benchmark/auto-resolve/fixtures/F6-dep-audit-native-module/metadata.json +0 -10
  173. package/benchmark/auto-resolve/fixtures/F6-dep-audit-native-module/setup.sh +0 -4
  174. package/benchmark/auto-resolve/fixtures/F6-dep-audit-native-module/spec.md +0 -48
  175. package/benchmark/auto-resolve/fixtures/F6-dep-audit-native-module/task.txt +0 -10
  176. package/benchmark/auto-resolve/fixtures/F7-out-of-scope-trap/NOTES.md +0 -57
  177. package/benchmark/auto-resolve/fixtures/F7-out-of-scope-trap/expected.json +0 -76
  178. package/benchmark/auto-resolve/fixtures/F7-out-of-scope-trap/metadata.json +0 -10
  179. package/benchmark/auto-resolve/fixtures/F7-out-of-scope-trap/setup.sh +0 -36
  180. package/benchmark/auto-resolve/fixtures/F7-out-of-scope-trap/spec.md +0 -45
  181. package/benchmark/auto-resolve/fixtures/F7-out-of-scope-trap/task.txt +0 -7
  182. package/benchmark/auto-resolve/fixtures/F8-known-limit-ambiguous/NOTES.md +0 -53
  183. package/benchmark/auto-resolve/fixtures/F8-known-limit-ambiguous/expected.json +0 -63
  184. package/benchmark/auto-resolve/fixtures/F8-known-limit-ambiguous/metadata.json +0 -10
  185. package/benchmark/auto-resolve/fixtures/F8-known-limit-ambiguous/setup.sh +0 -4
  186. package/benchmark/auto-resolve/fixtures/F8-known-limit-ambiguous/spec.md +0 -48
  187. package/benchmark/auto-resolve/fixtures/F8-known-limit-ambiguous/task.txt +0 -1
  188. package/benchmark/auto-resolve/fixtures/F9-e2e-ideate-to-resolve/NOTES.md +0 -105
  189. package/benchmark/auto-resolve/fixtures/F9-e2e-ideate-to-resolve/expected.json +0 -74
  190. package/benchmark/auto-resolve/fixtures/F9-e2e-ideate-to-resolve/metadata.json +0 -10
  191. package/benchmark/auto-resolve/fixtures/F9-e2e-ideate-to-resolve/setup.sh +0 -28
  192. package/benchmark/auto-resolve/fixtures/F9-e2e-ideate-to-resolve/spec.md +0 -59
  193. package/benchmark/auto-resolve/fixtures/F9-e2e-ideate-to-resolve/task.txt +0 -5
  194. package/benchmark/auto-resolve/fixtures/SCHEMA.md +0 -188
  195. package/benchmark/auto-resolve/fixtures/retired/F27-cli-subscription-proration/NOTES.md +0 -37
  196. package/benchmark/auto-resolve/fixtures/retired/F27-cli-subscription-proration/RETIRED.md +0 -13
  197. package/benchmark/auto-resolve/fixtures/retired/F27-cli-subscription-proration/expected.json +0 -56
  198. package/benchmark/auto-resolve/fixtures/retired/F27-cli-subscription-proration/metadata.json +0 -10
  199. package/benchmark/auto-resolve/fixtures/retired/F27-cli-subscription-proration/setup.sh +0 -18
  200. package/benchmark/auto-resolve/fixtures/retired/F27-cli-subscription-proration/spec.md +0 -69
  201. package/benchmark/auto-resolve/fixtures/retired/F27-cli-subscription-proration/task.txt +0 -7
  202. package/benchmark/auto-resolve/fixtures/retired/F27-cli-subscription-proration/verifiers/exact-proration.js +0 -48
  203. package/benchmark/auto-resolve/fixtures/retired/F27-cli-subscription-proration/verifiers/rules-source-and-conflict.js +0 -79
  204. package/benchmark/auto-resolve/fixtures/retired/F28-cli-return-authorization/NOTES.md +0 -54
  205. package/benchmark/auto-resolve/fixtures/retired/F28-cli-return-authorization/RETIRED.md +0 -7
  206. package/benchmark/auto-resolve/fixtures/retired/F28-cli-return-authorization/expected.json +0 -67
  207. package/benchmark/auto-resolve/fixtures/retired/F28-cli-return-authorization/metadata.json +0 -10
  208. package/benchmark/auto-resolve/fixtures/retired/F28-cli-return-authorization/setup.sh +0 -2
  209. package/benchmark/auto-resolve/fixtures/retired/F28-cli-return-authorization/spec.md +0 -67
  210. package/benchmark/auto-resolve/fixtures/retired/F28-cli-return-authorization/task.txt +0 -5
  211. package/benchmark/auto-resolve/fixtures/retired/F28-cli-return-authorization/verifiers/policy-precedence.js +0 -72
  212. package/benchmark/auto-resolve/fixtures/retired/F28-cli-return-authorization/verifiers/validation-and-immutability.js +0 -43
  213. package/benchmark/auto-resolve/fixtures/retired/F28-cli-return-authorization/verifiers/validation-boundary.js +0 -116
  214. package/benchmark/auto-resolve/fixtures/retired/F30-cli-credit-hold-settlement/NOTES.md +0 -35
  215. package/benchmark/auto-resolve/fixtures/retired/F30-cli-credit-hold-settlement/RETIRED.md +0 -12
  216. package/benchmark/auto-resolve/fixtures/retired/F30-cli-credit-hold-settlement/expected.json +0 -58
  217. package/benchmark/auto-resolve/fixtures/retired/F30-cli-credit-hold-settlement/metadata.json +0 -10
  218. package/benchmark/auto-resolve/fixtures/retired/F30-cli-credit-hold-settlement/setup.sh +0 -2
  219. package/benchmark/auto-resolve/fixtures/retired/F30-cli-credit-hold-settlement/spec.md +0 -73
  220. package/benchmark/auto-resolve/fixtures/retired/F30-cli-credit-hold-settlement/task.txt +0 -17
  221. package/benchmark/auto-resolve/fixtures/retired/F30-cli-credit-hold-settlement/verifiers/mixed-idempotent-settlement.js +0 -53
  222. package/benchmark/auto-resolve/fixtures/retired/F30-cli-credit-hold-settlement/verifiers/rejection-boundaries.js +0 -74
  223. package/benchmark/auto-resolve/fixtures/retired/F34-cli-settle-inflight/NOTES.md +0 -28
  224. package/benchmark/auto-resolve/fixtures/retired/F34-cli-settle-inflight/RETIRED.md +0 -15
  225. package/benchmark/auto-resolve/fixtures/retired/F34-cli-settle-inflight/expected.json +0 -57
  226. package/benchmark/auto-resolve/fixtures/retired/F34-cli-settle-inflight/metadata.json +0 -10
  227. package/benchmark/auto-resolve/fixtures/retired/F34-cli-settle-inflight/setup.sh +0 -50
  228. package/benchmark/auto-resolve/fixtures/retired/F34-cli-settle-inflight/spec.md +0 -59
  229. package/benchmark/auto-resolve/fixtures/retired/F34-cli-settle-inflight/task.txt +0 -9
  230. package/benchmark/auto-resolve/fixtures/retired/F34-cli-settle-inflight/verifiers/ordered-settlement.js +0 -88
  231. package/benchmark/auto-resolve/fixtures/retired/F34-cli-settle-inflight/verifiers/reject-invalid.js +0 -45
  232. package/benchmark/auto-resolve/fixtures/retired/F35-cli-apply-journal/NOTES.md +0 -30
  233. package/benchmark/auto-resolve/fixtures/retired/F35-cli-apply-journal/RETIRED.md +0 -16
  234. package/benchmark/auto-resolve/fixtures/retired/F35-cli-apply-journal/expected.json +0 -64
  235. package/benchmark/auto-resolve/fixtures/retired/F35-cli-apply-journal/metadata.json +0 -10
  236. package/benchmark/auto-resolve/fixtures/retired/F35-cli-apply-journal/setup.sh +0 -21
  237. package/benchmark/auto-resolve/fixtures/retired/F35-cli-apply-journal/spec.md +0 -58
  238. package/benchmark/auto-resolve/fixtures/retired/F35-cli-apply-journal/task.txt +0 -9
  239. package/benchmark/auto-resolve/fixtures/retired/F35-cli-apply-journal/verifiers/dup-op.js +0 -54
  240. package/benchmark/auto-resolve/fixtures/retired/F35-cli-apply-journal/verifiers/priority-apply.js +0 -82
  241. package/benchmark/auto-resolve/fixtures/retired/F35-cli-apply-journal/verifiers/rollback.js +0 -77
  242. package/benchmark/auto-resolve/fixtures/retired/F36-cli-session-admission/NOTES.md +0 -99
  243. package/benchmark/auto-resolve/fixtures/retired/F36-cli-session-admission/RETIRED.md +0 -18
  244. package/benchmark/auto-resolve/fixtures/retired/F36-cli-session-admission/expected.json +0 -64
  245. package/benchmark/auto-resolve/fixtures/retired/F36-cli-session-admission/metadata.json +0 -10
  246. package/benchmark/auto-resolve/fixtures/retired/F36-cli-session-admission/setup.sh +0 -4
  247. package/benchmark/auto-resolve/fixtures/retired/F36-cli-session-admission/spec.md +0 -61
  248. package/benchmark/auto-resolve/fixtures/retired/F36-cli-session-admission/task.txt +0 -9
  249. package/benchmark/auto-resolve/fixtures/retired/F36-cli-session-admission/verifiers/correctness-small.js +0 -135
  250. package/benchmark/auto-resolve/fixtures/retired/F36-cli-session-admission/verifiers/scale.js +0 -100
  251. package/benchmark/auto-resolve/fixtures/retired/F36-cli-session-admission/verifiers/validation.js +0 -75
  252. package/benchmark/auto-resolve/fixtures/retired/F37-cli-rule-lookup/NOTES.md +0 -93
  253. package/benchmark/auto-resolve/fixtures/retired/F37-cli-rule-lookup/RETIRED.md +0 -16
  254. package/benchmark/auto-resolve/fixtures/retired/F37-cli-rule-lookup/expected.json +0 -65
  255. package/benchmark/auto-resolve/fixtures/retired/F37-cli-rule-lookup/metadata.json +0 -10
  256. package/benchmark/auto-resolve/fixtures/retired/F37-cli-rule-lookup/setup.sh +0 -18
  257. package/benchmark/auto-resolve/fixtures/retired/F37-cli-rule-lookup/spec.md +0 -66
  258. package/benchmark/auto-resolve/fixtures/retired/F37-cli-rule-lookup/task.txt +0 -9
  259. package/benchmark/auto-resolve/fixtures/retired/F37-cli-rule-lookup/verifiers/correctness-small.js +0 -84
  260. package/benchmark/auto-resolve/fixtures/retired/F37-cli-rule-lookup/verifiers/scale.js +0 -184
  261. package/benchmark/auto-resolve/fixtures/retired/F37-cli-rule-lookup/verifiers/validation.js +0 -74
  262. package/benchmark/auto-resolve/fixtures/retired/F9-e2e-ideate-to-preflight/NOTES.md +0 -60
  263. package/benchmark/auto-resolve/fixtures/retired/F9-e2e-ideate-to-preflight/RETIRED.md +0 -29
  264. package/benchmark/auto-resolve/fixtures/retired/F9-e2e-ideate-to-preflight/expected.json +0 -73
  265. package/benchmark/auto-resolve/fixtures/retired/F9-e2e-ideate-to-preflight/metadata.json +0 -10
  266. package/benchmark/auto-resolve/fixtures/retired/F9-e2e-ideate-to-preflight/setup.sh +0 -28
  267. package/benchmark/auto-resolve/fixtures/retired/F9-e2e-ideate-to-preflight/spec.md +0 -58
  268. package/benchmark/auto-resolve/fixtures/retired/F9-e2e-ideate-to-preflight/task.txt +0 -5
  269. package/benchmark/auto-resolve/fixtures/test-repo/README.md +0 -12
  270. package/benchmark/auto-resolve/fixtures/test-repo/bin/cli.js +0 -63
  271. package/benchmark/auto-resolve/fixtures/test-repo/package-lock.json +0 -823
  272. package/benchmark/auto-resolve/fixtures/test-repo/package.json +0 -22
  273. package/benchmark/auto-resolve/fixtures/test-repo/playwright.config.js +0 -17
  274. package/benchmark/auto-resolve/fixtures/test-repo/server/index.js +0 -37
  275. package/benchmark/auto-resolve/fixtures/test-repo/tests/cli.test.js +0 -25
  276. package/benchmark/auto-resolve/fixtures/test-repo/tests/server.test.js +0 -58
  277. package/benchmark/auto-resolve/fixtures/test-repo/web/index.html +0 -37
  278. package/benchmark/auto-resolve/results/20260507-f10-f11-tier1-full-pipeline/headroom-gate.json +0 -25
  279. package/benchmark/auto-resolve/results/20260507-f10-f11-tier1-full-pipeline/headroom-gate.md +0 -10
  280. package/benchmark/auto-resolve/results/20260508-f22-exact-error-headroom/headroom-gate.json +0 -18
  281. package/benchmark/auto-resolve/results/20260508-f22-exact-error-headroom/headroom-gate.md +0 -9
  282. package/benchmark/auto-resolve/results/20260508-f26-headroom/headroom-gate.json +0 -18
  283. package/benchmark/auto-resolve/results/20260508-f26-headroom/headroom-gate.md +0 -9
  284. package/benchmark/auto-resolve/results/20260510-f16-f23-f25-combined-proof/F16-cli-quote-tax-rules/l2_risk_probes/result.json +0 -28
  285. package/benchmark/auto-resolve/results/20260510-f16-f23-f25-combined-proof/F23-cli-fulfillment-wave/l2_risk_probes/result.json +0 -28
  286. package/benchmark/auto-resolve/results/20260510-f16-f23-f25-combined-proof/F25-cli-cart-promotion-rules/l2_risk_probes/result.json +0 -30
  287. package/benchmark/auto-resolve/results/20260510-f16-f23-f25-combined-proof/full-pipeline-pair-gate.json +0 -82
  288. package/benchmark/auto-resolve/results/20260510-f16-f23-f25-combined-proof/full-pipeline-pair-gate.md +0 -18
  289. package/benchmark/auto-resolve/results/20260510-f16-f23-f25-combined-proof/headroom-gate.json +0 -46
  290. package/benchmark/auto-resolve/results/20260510-f16-f23-f25-combined-proof/headroom-gate.md +0 -17
  291. package/benchmark/auto-resolve/results/20260511-f12-webhook-headroom/headroom-gate.json +0 -28
  292. package/benchmark/auto-resolve/results/20260511-f12-webhook-headroom/headroom-gate.md +0 -15
  293. package/benchmark/auto-resolve/results/20260511-f15-concurrency-headroom/headroom-gate.json +0 -28
  294. package/benchmark/auto-resolve/results/20260511-f15-concurrency-headroom/headroom-gate.md +0 -15
  295. package/benchmark/auto-resolve/results/20260511-f21-current-riskprobes-v1/F21-cli-scheduler-priority/l2_risk_probes/result.json +0 -32
  296. package/benchmark/auto-resolve/results/20260511-f21-current-riskprobes-v1/full-pipeline-pair-gate.json +0 -44
  297. package/benchmark/auto-resolve/results/20260511-f21-current-riskprobes-v1/full-pipeline-pair-gate.md +0 -16
  298. package/benchmark/auto-resolve/results/20260511-f21-current-riskprobes-v1/headroom-gate.json +0 -18
  299. package/benchmark/auto-resolve/results/20260511-f21-current-riskprobes-v1/headroom-gate.md +0 -9
  300. package/benchmark/auto-resolve/results/20260511-f3-http-error-headroom/headroom-gate.json +0 -28
  301. package/benchmark/auto-resolve/results/20260511-f3-http-error-headroom/headroom-gate.md +0 -15
  302. package/benchmark/auto-resolve/results/20260512-f2-medium-headroom/headroom-gate.json +0 -28
  303. package/benchmark/auto-resolve/results/20260512-f2-medium-headroom/headroom-gate.md +0 -15
  304. package/benchmark/auto-resolve/results/20260512-f31-seat-rebalance-headroom/headroom-gate.json +0 -28
  305. package/benchmark/auto-resolve/results/20260512-f31-seat-rebalance-headroom/headroom-gate.md +0 -15
  306. package/benchmark/auto-resolve/results/20260512-f32-subscription-renewal-headroom/headroom-gate.json +0 -28
  307. package/benchmark/auto-resolve/results/20260512-f32-subscription-renewal-headroom/headroom-gate.md +0 -15
  308. package/benchmark/auto-resolve/results/20260512-f4-web-headroom/headroom-gate.json +0 -28
  309. package/benchmark/auto-resolve/results/20260512-f4-web-headroom/headroom-gate.md +0 -15
  310. package/benchmark/auto-resolve/results/20260512-f5-fixloop-headroom/headroom-gate.json +0 -28
  311. package/benchmark/auto-resolve/results/20260512-f5-fixloop-headroom/headroom-gate.md +0 -15
  312. package/benchmark/auto-resolve/results/20260512-f6-checksum-headroom/headroom-gate.json +0 -28
  313. package/benchmark/auto-resolve/results/20260512-f6-checksum-headroom/headroom-gate.md +0 -15
  314. package/benchmark/auto-resolve/results/20260512-f7-scope-headroom/headroom-gate.json +0 -28
  315. package/benchmark/auto-resolve/results/20260512-f7-scope-headroom/headroom-gate.md +0 -15
  316. package/benchmark/auto-resolve/results/20260512-f9-e2e-headroom/headroom-gate.json +0 -28
  317. package/benchmark/auto-resolve/results/20260512-f9-e2e-headroom/headroom-gate.md +0 -15
  318. package/benchmark/auto-resolve/run-real-benchmark.md +0 -303
  319. package/benchmark/auto-resolve/scripts/audit-headroom-rejections.py +0 -441
  320. package/benchmark/auto-resolve/scripts/audit-pair-evidence.py +0 -1256
  321. package/benchmark/auto-resolve/scripts/build-pair-eligible-manifest.py +0 -306
  322. package/benchmark/auto-resolve/scripts/check-f9-artifacts.py +0 -268
  323. package/benchmark/auto-resolve/scripts/collect-swebench-predictions.py +0 -108
  324. package/benchmark/auto-resolve/scripts/compile-report.py +0 -493
  325. package/benchmark/auto-resolve/scripts/fetch-swebench-instances.py +0 -129
  326. package/benchmark/auto-resolve/scripts/frozen-verify-gate.py +0 -434
  327. package/benchmark/auto-resolve/scripts/full-pipeline-pair-gate.py +0 -612
  328. package/benchmark/auto-resolve/scripts/headroom-gate.py +0 -378
  329. package/benchmark/auto-resolve/scripts/iter-0033c-compare.py +0 -683
  330. package/benchmark/auto-resolve/scripts/iter-0033c-l1-summary.py +0 -97
  331. package/benchmark/auto-resolve/scripts/judge-opus-pass.sh +0 -542
  332. package/benchmark/auto-resolve/scripts/judge.sh +0 -565
  333. package/benchmark/auto-resolve/scripts/oracle-scope-tier-a.py +0 -256
  334. package/benchmark/auto-resolve/scripts/oracle-scope-tier-b.py +0 -287
  335. package/benchmark/auto-resolve/scripts/oracle-test-fidelity.py +0 -328
  336. package/benchmark/auto-resolve/scripts/pair-candidate-frontier.py +0 -469
  337. package/benchmark/auto-resolve/scripts/pair-plan-idgen.py +0 -401
  338. package/benchmark/auto-resolve/scripts/pair-plan-lint.py +0 -475
  339. package/benchmark/auto-resolve/scripts/pair-rejected-fixtures.sh +0 -103
  340. package/benchmark/auto-resolve/scripts/pair_evidence_contract.py +0 -270
  341. package/benchmark/auto-resolve/scripts/prepare-swebench-frozen-case.py +0 -273
  342. package/benchmark/auto-resolve/scripts/prepare-swebench-frozen-corpus.py +0 -148
  343. package/benchmark/auto-resolve/scripts/prepare-swebench-solver-worktree.py +0 -210
  344. package/benchmark/auto-resolve/scripts/recent-benchmark-summary.py +0 -232
  345. package/benchmark/auto-resolve/scripts/run-fixture.sh +0 -1024
  346. package/benchmark/auto-resolve/scripts/run-frozen-verify-pair.sh +0 -683
  347. package/benchmark/auto-resolve/scripts/run-full-pipeline-pair-candidate.sh +0 -458
  348. package/benchmark/auto-resolve/scripts/run-headroom-candidate.sh +0 -336
  349. package/benchmark/auto-resolve/scripts/run-iter-0033c.sh +0 -208
  350. package/benchmark/auto-resolve/scripts/run-suite.sh +0 -251
  351. package/benchmark/auto-resolve/scripts/run-swebench-frozen-corpus.sh +0 -310
  352. package/benchmark/auto-resolve/scripts/run-swebench-solver-batch.sh +0 -257
  353. package/benchmark/auto-resolve/scripts/ship-gate.py +0 -391
  354. package/benchmark/auto-resolve/scripts/solo-ceiling-avoidance.py +0 -53
  355. package/benchmark/auto-resolve/scripts/solo-headroom-hypothesis.py +0 -77
  356. package/benchmark/auto-resolve/scripts/swebench-frozen-matrix.py +0 -478
  357. package/benchmark/auto-resolve/scripts/test-audit-headroom-rejections.sh +0 -288
  358. package/benchmark/auto-resolve/scripts/test-audit-pair-evidence.sh +0 -1672
  359. package/benchmark/auto-resolve/scripts/test-benchmark-arg-parsing.sh +0 -1015
  360. package/benchmark/auto-resolve/scripts/test-build-pair-eligible-manifest.sh +0 -491
  361. package/benchmark/auto-resolve/scripts/test-check-f9-artifacts.sh +0 -91
  362. package/benchmark/auto-resolve/scripts/test-frozen-verify-gate.sh +0 -517
  363. package/benchmark/auto-resolve/scripts/test-full-pipeline-pair-gate.sh +0 -610
  364. package/benchmark/auto-resolve/scripts/test-headroom-gate.sh +0 -401
  365. package/benchmark/auto-resolve/scripts/test-iter-0033c-compare.sh +0 -525
  366. package/benchmark/auto-resolve/scripts/test-iter-0033c-l1-summary.sh +0 -254
  367. package/benchmark/auto-resolve/scripts/test-lint-fixtures.sh +0 -580
  368. package/benchmark/auto-resolve/scripts/test-pair-candidate-frontier.sh +0 -591
  369. package/benchmark/auto-resolve/scripts/test-run-full-pipeline-pair-candidate.sh +0 -497
  370. package/benchmark/auto-resolve/scripts/test-run-headroom-candidate.sh +0 -401
  371. package/benchmark/auto-resolve/scripts/test-run-swebench-solver-batch.sh +0 -111
  372. package/benchmark/auto-resolve/scripts/test-ship-gate.sh +0 -1189
  373. package/benchmark/auto-resolve/scripts/test-swebench-frozen-case.sh +0 -1221
  374. package/benchmark/auto-resolve/shadow-fixtures/S1-cli-lang-flag/NOTES.md +0 -28
  375. package/benchmark/auto-resolve/shadow-fixtures/S1-cli-lang-flag/expected.json +0 -63
  376. package/benchmark/auto-resolve/shadow-fixtures/S1-cli-lang-flag/metadata.json +0 -10
  377. package/benchmark/auto-resolve/shadow-fixtures/S1-cli-lang-flag/setup.sh +0 -3
  378. package/benchmark/auto-resolve/shadow-fixtures/S1-cli-lang-flag/spec.md +0 -47
  379. package/benchmark/auto-resolve/shadow-fixtures/S1-cli-lang-flag/task.txt +0 -1
  380. package/benchmark/auto-resolve/shadow-fixtures/S2-cli-inventory-reservation/NOTES.md +0 -34
  381. package/benchmark/auto-resolve/shadow-fixtures/S2-cli-inventory-reservation/expected.json +0 -53
  382. package/benchmark/auto-resolve/shadow-fixtures/S2-cli-inventory-reservation/metadata.json +0 -10
  383. package/benchmark/auto-resolve/shadow-fixtures/S2-cli-inventory-reservation/setup.sh +0 -3
  384. package/benchmark/auto-resolve/shadow-fixtures/S2-cli-inventory-reservation/spec.md +0 -50
  385. package/benchmark/auto-resolve/shadow-fixtures/S2-cli-inventory-reservation/task.txt +0 -1
  386. package/benchmark/auto-resolve/shadow-fixtures/S2-cli-inventory-reservation/verifiers/duplicate-order-error.js +0 -27
  387. package/benchmark/auto-resolve/shadow-fixtures/S2-cli-inventory-reservation/verifiers/priority-stock-reservation.js +0 -44
  388. package/benchmark/auto-resolve/shadow-fixtures/S3-cli-ticket-assignment/NOTES.md +0 -34
  389. package/benchmark/auto-resolve/shadow-fixtures/S3-cli-ticket-assignment/expected.json +0 -55
  390. package/benchmark/auto-resolve/shadow-fixtures/S3-cli-ticket-assignment/metadata.json +0 -10
  391. package/benchmark/auto-resolve/shadow-fixtures/S3-cli-ticket-assignment/setup.sh +0 -3
  392. package/benchmark/auto-resolve/shadow-fixtures/S3-cli-ticket-assignment/spec.md +0 -52
  393. package/benchmark/auto-resolve/shadow-fixtures/S3-cli-ticket-assignment/task.txt +0 -1
  394. package/benchmark/auto-resolve/shadow-fixtures/S3-cli-ticket-assignment/verifiers/duplicate-ticket-error.js +0 -29
  395. package/benchmark/auto-resolve/shadow-fixtures/S3-cli-ticket-assignment/verifiers/priority-agent-assignment.js +0 -48
  396. package/benchmark/auto-resolve/shadow-fixtures/S4-cli-return-routing/NOTES.md +0 -34
  397. package/benchmark/auto-resolve/shadow-fixtures/S4-cli-return-routing/expected.json +0 -55
  398. package/benchmark/auto-resolve/shadow-fixtures/S4-cli-return-routing/metadata.json +0 -10
  399. package/benchmark/auto-resolve/shadow-fixtures/S4-cli-return-routing/setup.sh +0 -3
  400. package/benchmark/auto-resolve/shadow-fixtures/S4-cli-return-routing/spec.md +0 -55
  401. package/benchmark/auto-resolve/shadow-fixtures/S4-cli-return-routing/task.txt +0 -1
  402. package/benchmark/auto-resolve/shadow-fixtures/S4-cli-return-routing/verifiers/duplicate-return-error.js +0 -43
  403. package/benchmark/auto-resolve/shadow-fixtures/S4-cli-return-routing/verifiers/priority-return-routing.js +0 -70
  404. package/benchmark/auto-resolve/shadow-fixtures/S5-cli-credit-grant-ledger/NOTES.md +0 -37
  405. package/benchmark/auto-resolve/shadow-fixtures/S5-cli-credit-grant-ledger/expected.json +0 -54
  406. package/benchmark/auto-resolve/shadow-fixtures/S5-cli-credit-grant-ledger/metadata.json +0 -10
  407. package/benchmark/auto-resolve/shadow-fixtures/S5-cli-credit-grant-ledger/setup.sh +0 -3
  408. package/benchmark/auto-resolve/shadow-fixtures/S5-cli-credit-grant-ledger/spec.md +0 -59
  409. package/benchmark/auto-resolve/shadow-fixtures/S5-cli-credit-grant-ledger/task.txt +0 -1
  410. package/benchmark/auto-resolve/shadow-fixtures/S5-cli-credit-grant-ledger/verifiers/credit-ledger-priority.js +0 -98
  411. package/benchmark/auto-resolve/shadow-fixtures/S5-cli-credit-grant-ledger/verifiers/duplicate-charge-error.js +0 -38
  412. package/benchmark/auto-resolve/shadow-fixtures/S6-cli-refund-window-ledger/NOTES.md +0 -36
  413. package/benchmark/auto-resolve/shadow-fixtures/S6-cli-refund-window-ledger/expected.json +0 -56
  414. package/benchmark/auto-resolve/shadow-fixtures/S6-cli-refund-window-ledger/metadata.json +0 -10
  415. package/benchmark/auto-resolve/shadow-fixtures/S6-cli-refund-window-ledger/setup.sh +0 -3
  416. package/benchmark/auto-resolve/shadow-fixtures/S6-cli-refund-window-ledger/spec.md +0 -59
  417. package/benchmark/auto-resolve/shadow-fixtures/S6-cli-refund-window-ledger/task.txt +0 -1
  418. package/benchmark/auto-resolve/shadow-fixtures/S6-cli-refund-window-ledger/verifiers/duplicate-refund-error.js +0 -41
  419. package/benchmark/auto-resolve/shadow-fixtures/S6-cli-refund-window-ledger/verifiers/priority-refund-ledger.js +0 -65
  420. package/config/skills/_shared/pair-plan-schema.md +0 -298
  421. package/scripts/lint-fixtures.sh +0 -352
  422. package/scripts/lint-shadow-fixtures.sh +0 -58
  423. package/scripts/lint-skills.sh +0 -4265
  424. package/scripts/test-owner-phases.py +0 -193
@@ -1,53 +0,0 @@
1
- #!/usr/bin/env python3
2
- """Validate a shadow fixture solo ceiling avoidance note."""
3
- from __future__ import annotations
4
-
5
- import argparse
6
- import pathlib
7
- import re
8
- import sys
9
-
10
-
11
- SECTION_RE = re.compile(r"(?ms)^##[ \t]+Solo ceiling avoidance\b[^\n]*\n(.*?)(?=^##[ \t]+|\Z)")
12
- CONTROL_RE = re.compile(r"\bS[2-6]\b|S2-S6|solo-saturated|rejected controls?", re.IGNORECASE)
13
- REASON_RE = re.compile(r"\bdiffer(?:s|ent|ence)?\b|\bunlike\b|\bbecause\b|\bpreserve\b|\bheadroom\b", re.IGNORECASE)
14
-
15
-
16
- def read_text(path: pathlib.Path) -> str:
17
- try:
18
- return path.read_text(encoding="utf-8")
19
- except UnicodeDecodeError as exc:
20
- print(f"{path}: expected UTF-8 text ({exc})", file=sys.stderr)
21
- raise SystemExit(2) from None
22
- except OSError as exc:
23
- print(f"{path}: unable to read ({exc})", file=sys.stderr)
24
- raise SystemExit(2) from None
25
-
26
-
27
- def solo_ceiling_avoidance_error(text: str) -> str | None:
28
- match = SECTION_RE.search(text)
29
- if not match:
30
- return "missing ## Solo ceiling avoidance section"
31
- section = match.group(1)
32
- if "solo_claude" not in section:
33
- return "solo ceiling avoidance must mention solo_claude"
34
- if not CONTROL_RE.search(section):
35
- return "solo ceiling avoidance must compare against rejected or solo-saturated controls such as S2-S6"
36
- if not REASON_RE.search(section):
37
- return "solo ceiling avoidance must state difference/headroom reasoning"
38
- return None
39
-
40
-
41
- def main(argv: list[str]) -> int:
42
- parser = argparse.ArgumentParser()
43
- parser.add_argument("path", type=pathlib.Path)
44
- args = parser.parse_args(argv)
45
- err = solo_ceiling_avoidance_error(read_text(args.path))
46
- if err:
47
- print(f"{args.path}: {err}", file=sys.stderr)
48
- return 1
49
- return 0
50
-
51
-
52
- if __name__ == "__main__":
53
- raise SystemExit(main(sys.argv[1:]))
@@ -1,77 +0,0 @@
1
- #!/usr/bin/env python3
2
- """Validate that a pair-candidate fixture states an actionable solo-headroom hypothesis."""
3
- from __future__ import annotations
4
-
5
- import argparse
6
- import json
7
- import pathlib
8
- import sys
9
-
10
-
11
- from pair_evidence_contract import (
12
- actionable_observable_commands,
13
- has_actionable_solo_headroom_hypothesis_text,
14
- )
15
-
16
-
17
- def combined_text(paths: list[pathlib.Path]) -> str:
18
- chunks: list[str] = []
19
- for path in paths:
20
- if not path.is_file():
21
- continue
22
- try:
23
- chunks.append(path.read_text(encoding="utf-8"))
24
- except UnicodeDecodeError as exc:
25
- print(f"{path}: expected UTF-8 text ({exc})", file=sys.stderr)
26
- raise SystemExit(2) from None
27
- return "\n".join(chunks)
28
-
29
-
30
- def has_actionable_hypothesis(text: str) -> bool:
31
- return has_actionable_solo_headroom_hypothesis_text(text)
32
-
33
-
34
- def expected_commands(path: pathlib.Path) -> set[str]:
35
- try:
36
- data = json.loads(path.read_text(encoding="utf-8"))
37
- except UnicodeDecodeError as exc:
38
- print(f"{path}: expected UTF-8 JSON ({exc})", file=sys.stderr)
39
- raise SystemExit(2) from None
40
- except json.JSONDecodeError as exc:
41
- print(f"{path}: invalid JSON ({exc})", file=sys.stderr)
42
- raise SystemExit(2) from None
43
-
44
- commands = data.get("verification_commands")
45
- if not isinstance(commands, list):
46
- print(f"{path}: verification_commands must be a list", file=sys.stderr)
47
- raise SystemExit(2)
48
-
49
- result: set[str] = set()
50
- for index, command in enumerate(commands):
51
- if not isinstance(command, dict) or not isinstance(command.get("cmd"), str):
52
- print(f"{path}: verification_commands[{index}].cmd must be a string", file=sys.stderr)
53
- raise SystemExit(2)
54
- result.add(command["cmd"])
55
- return result
56
-
57
-
58
- def main(argv: list[str]) -> int:
59
- parser = argparse.ArgumentParser()
60
- parser.add_argument(
61
- "--expected-json",
62
- type=pathlib.Path,
63
- help="Require the observable hypothesis command to match expected.json verification_commands[].cmd.",
64
- )
65
- parser.add_argument("paths", nargs="+", type=pathlib.Path)
66
- args = parser.parse_args(argv)
67
- text = combined_text(args.paths)
68
- if not has_actionable_hypothesis(text):
69
- return 1
70
- if args.expected_json is None:
71
- return 0
72
- expected = expected_commands(args.expected_json)
73
- return 0 if any(command in expected for command in actionable_observable_commands(text)) else 1
74
-
75
-
76
- if __name__ == "__main__":
77
- raise SystemExit(main(sys.argv[1:]))
@@ -1,478 +0,0 @@
1
- #!/usr/bin/env python3
2
- """Render a SWE-bench frozen VERIFY matrix from compare artifacts."""
3
-
4
- from __future__ import annotations
5
-
6
- import argparse
7
- import json
8
- import math
9
- import re
10
- from collections import Counter
11
- from pathlib import Path
12
- from typing import Any
13
-
14
- from pair_evidence_contract import (
15
- all_known_pair_trigger_reasons,
16
- has_canonical_pair_trigger_reason,
17
- has_known_pair_trigger_reason,
18
- loads_strict_json_object,
19
- path_has_actionable_solo_headroom_hypothesis,
20
- )
21
-
22
-
23
- RANK = {
24
- "PASS": 0,
25
- "PASS_WITH_ISSUES": 1,
26
- "NEEDS_WORK": 2,
27
- "BLOCKED": 3,
28
- }
29
-
30
-
31
- def rank(verdict: str | None) -> int:
32
- return RANK.get(verdict or "", -1)
33
-
34
-
35
- def load_json(path: Path) -> dict[str, Any]:
36
- try:
37
- return loads_strict_json_object(path.read_text(encoding="utf8"))
38
- except (json.JSONDecodeError, ValueError):
39
- return {}
40
-
41
-
42
- def object_field(payload: dict[str, Any], key: str) -> dict[str, Any]:
43
- value = payload.get(key)
44
- return value if isinstance(value, dict) else {}
45
-
46
-
47
- def verdict_field(payload: dict[str, Any], key: str) -> str | None:
48
- value = payload.get(key)
49
- return value if isinstance(value, str) else None
50
-
51
-
52
- def number_field(payload: dict[str, Any], key: str) -> int | float | None:
53
- value = payload.get(key)
54
- if isinstance(value, bool):
55
- return None
56
- if not isinstance(value, (int, float)) or not math.isfinite(value):
57
- return None
58
- return value
59
-
60
-
61
- def transcript_failure_reason(results_root: Path, run_id: str, arm: str) -> str | None:
62
- transcript_path = results_root / run_id / arm / "transcript.txt"
63
- if not transcript_path.is_file():
64
- return None
65
- transcript = transcript_path.read_text(encoding="utf8", errors="replace")
66
- if "You've hit your limit" in transcript:
67
- return "provider_limit"
68
- return None
69
-
70
-
71
- def infer_fixture_id(results_root: Path, run_id: str) -> str:
72
- for arm in ("pair", "solo"):
73
- input_path = results_root / run_id / arm / "input.md"
74
- if not input_path.exists():
75
- continue
76
- match = re.search(r"docs/roadmap/phase-1/([^`\s]+)\.md", input_path.read_text())
77
- if match:
78
- return match.group(1)
79
- return "unknown"
80
-
81
-
82
- def elapsed_ratio(pair_elapsed: Any, solo_elapsed: Any) -> float | None:
83
- if not isinstance(pair_elapsed, (int, float)) or not isinstance(solo_elapsed, (int, float)):
84
- return None
85
- if pair_elapsed <= 0 or solo_elapsed <= 0:
86
- return None
87
- return pair_elapsed / solo_elapsed
88
-
89
-
90
- def is_true(value: Any) -> bool:
91
- return value is True
92
-
93
-
94
- def pair_trigger_failures(
95
- pair: dict[str, Any],
96
- *,
97
- fixture_spec: Path | None = None,
98
- require_hypothesis_trigger: bool = False,
99
- ) -> list[str]:
100
- trigger = pair.get("pair_trigger")
101
- if not isinstance(trigger, dict):
102
- return ["pair_trigger missing or malformed"]
103
- eligible = trigger.get("eligible")
104
- reasons = trigger.get("reasons")
105
- skipped_reason = trigger.get("skipped_reason")
106
- if not isinstance(eligible, bool):
107
- return ["pair_trigger.eligible malformed"]
108
- if not isinstance(reasons, list) or not all(isinstance(reason, str) for reason in reasons):
109
- return ["pair_trigger.reasons malformed"]
110
- if skipped_reason is not None and not isinstance(skipped_reason, str):
111
- return ["pair_trigger.skipped_reason malformed"]
112
- if eligible is True:
113
- failures = []
114
- if not reasons:
115
- failures.append("pair_trigger eligible with empty reasons")
116
- if reasons and not has_known_pair_trigger_reason(reasons):
117
- failures.append("pair_trigger reasons missing known trigger reason")
118
- if (
119
- reasons
120
- and has_known_pair_trigger_reason(reasons)
121
- and not all_known_pair_trigger_reasons(reasons)
122
- ):
123
- failures.append("pair_trigger reasons contain unknown trigger reason")
124
- if (
125
- reasons
126
- and all_known_pair_trigger_reasons(reasons)
127
- and not has_canonical_pair_trigger_reason(reasons)
128
- ):
129
- failures.append("pair_trigger reasons missing canonical trigger reason")
130
- if skipped_reason is not None:
131
- failures.append("pair_trigger eligible with skipped_reason")
132
- if (
133
- require_hypothesis_trigger
134
- and fixture_spec is not None
135
- and path_has_actionable_solo_headroom_hypothesis(fixture_spec)
136
- and "spec.solo_headroom_hypothesis" not in reasons
137
- ):
138
- failures.append("pair_trigger missing spec.solo_headroom_hypothesis")
139
- return failures
140
- if reasons:
141
- return ["pair_trigger ineligible with reasons"]
142
- return []
143
-
144
-
145
- def pair_trigger_eligible(pair: dict[str, Any]) -> bool:
146
- trigger = pair.get("pair_trigger")
147
- return (
148
- isinstance(trigger, dict)
149
- and trigger.get("eligible") is True
150
- and isinstance(trigger.get("reasons"), list)
151
- and all(isinstance(reason, str) for reason in trigger["reasons"])
152
- and len(trigger["reasons"]) > 0
153
- and all_known_pair_trigger_reasons(trigger["reasons"])
154
- and has_canonical_pair_trigger_reason(trigger["reasons"])
155
- and trigger.get("skipped_reason") is None
156
- )
157
-
158
-
159
- def pair_trigger_reasons(pair: dict[str, Any]) -> list[str]:
160
- trigger = pair.get("pair_trigger")
161
- if not isinstance(trigger, dict):
162
- return []
163
- reasons = trigger.get("reasons")
164
- if not isinstance(reasons, list) or not all(isinstance(reason, str) for reason in reasons):
165
- return []
166
- return reasons
167
-
168
-
169
- def pair_trigger_label(row: dict[str, Any]) -> str:
170
- if row["pair_trigger_missed"]:
171
- return "missed"
172
- failures = row.get("pair_trigger_failures") or []
173
- if failures:
174
- return "malformed"
175
- if row["pair_trigger_eligible"]:
176
- return "eligible"
177
- return "not_eligible"
178
-
179
-
180
- def load_gate_rows(gate_json: Path | None) -> dict[str, dict[str, Any]]:
181
- if gate_json is None:
182
- return {}
183
- doc = load_json(gate_json)
184
- rows = doc.get("rows")
185
- if not isinstance(rows, list):
186
- return {}
187
- return {
188
- row["run_id"]: row for row in rows
189
- if isinstance(row, dict) and isinstance(row.get("run_id"), str)
190
- }
191
-
192
-
193
- def min_gate_rate(value: str) -> float:
194
- rate = float(value)
195
- if rate < 0 or rate > 1:
196
- raise argparse.ArgumentTypeError("--min-gate-rate must be between 0 and 1")
197
- return rate
198
-
199
-
200
- def non_negative_int(value: str) -> int:
201
- parsed = int(value)
202
- if parsed < 0:
203
- raise argparse.ArgumentTypeError("value must be >= 0")
204
- return parsed
205
-
206
-
207
- def classify(row: dict[str, Any], included: bool) -> str:
208
- if included:
209
- external = row["external_lift"]
210
- internal = row["internal_lift"]
211
- if external and internal:
212
- return "gate: external + internal lift"
213
- if external:
214
- return "gate: external lift"
215
- if internal:
216
- return "gate: internal lift"
217
- return "gate"
218
- if row.get("row_failed_before_compare"):
219
- row_exit = row.get("row_exit")
220
- suffix = f" exit={row_exit}" if isinstance(row_exit, int) else ""
221
- return f"failed attempt: row runner{suffix}"
222
- if row.get("compare_missing"):
223
- return "failed attempt: missing compare"
224
- if row.get("solo_timed_out") or row.get("pair_timed_out"):
225
- return "failed attempt: timeout"
226
- if row.get("solo_failure_reason") == "provider_limit" or row.get("pair_failure_reason") == "provider_limit":
227
- return "failed attempt: provider limit"
228
- if row.get("solo_environment_contamination") or row.get("pair_environment_contamination"):
229
- return "failed attempt: environment contamination"
230
- if row.get("solo_disqualifier") or row.get("pair_disqualifier"):
231
- return "failed attempt: disqualifier"
232
- if row.get("solo_invoke_failure") or row.get("pair_invoke_failure"):
233
- return "failed attempt: invoke failure"
234
- if row.get("solo_invoke_exit") not in (None, 0) or row.get("pair_invoke_exit") not in (None, 0):
235
- return "failed attempt: nonzero invoke exit"
236
- if row.get("malformed_compare"):
237
- return "failed attempt: malformed compare"
238
- if row.get("pair_trigger_missed"):
239
- return "failed attempt: pair trigger missed"
240
- trigger_failures = row.get("pair_trigger_failures") or []
241
- if trigger_failures:
242
- return "failed attempt: pair trigger contract: " + "; ".join(trigger_failures)
243
- if row["solo_mechanical"] == "FAIL":
244
- return "excluded: solo mechanical dominated"
245
- if row["external_lift"] or row["internal_lift"]:
246
- failures = row.get("gate_failures") or []
247
- if failures:
248
- return "lift excluded: " + "; ".join(failures)
249
- return "lift outside gate"
250
- if rank(row["pair_verdict"]) > rank(row["solo_verdict"]):
251
- return "recall-only advisory"
252
- if row["pair_found_more_low_or_worse"] or row["pair_found_more_findings"]:
253
- return "recall-only findings"
254
- return "no verdict lift"
255
-
256
-
257
- def build_row(
258
- results_root: Path,
259
- run_id: str,
260
- gate_rows_by_id: dict[str, dict[str, Any]],
261
- *,
262
- fixtures_root: Path | None,
263
- require_hypothesis_trigger: bool,
264
- ) -> dict[str, Any]:
265
- compare_path = results_root / run_id / "compare.json"
266
- malformed_compare = False
267
- if compare_path.exists():
268
- compare = load_json(compare_path)
269
- malformed_compare = not bool(compare)
270
- else:
271
- compare = {
272
- "solo": {},
273
- "pair": {},
274
- "comparison": {"compare_missing": True},
275
- }
276
- solo = object_field(compare, "solo")
277
- pair = object_field(compare, "pair")
278
- comparison = object_field(compare, "comparison")
279
- malformed_compare = malformed_compare or any(
280
- key in compare and not isinstance(compare.get(key), dict)
281
- for key in ("solo", "pair", "comparison")
282
- )
283
- pair_ratio = elapsed_ratio(
284
- number_field(pair, "elapsed_seconds"),
285
- number_field(solo, "elapsed_seconds"),
286
- )
287
- gate_row = gate_rows_by_id.get(run_id) or {}
288
- solo_verdict = (
289
- verdict_field(comparison, "solo_verdict")
290
- or verdict_field(solo, "verify_verdict")
291
- )
292
- pair_verdict = (
293
- verdict_field(comparison, "pair_verdict")
294
- or verdict_field(pair, "verify_verdict")
295
- )
296
- solo_sub = object_field(solo, "sub_verdicts")
297
- pair_sub = object_field(pair, "sub_verdicts")
298
- fixture_id = infer_fixture_id(results_root, run_id)
299
- fixture_spec = None
300
- if fixtures_root is not None and fixture_id != "unknown":
301
- fixture_spec = fixtures_root / fixture_id / "spec.md"
302
- trigger_failures = pair_trigger_failures(
303
- pair,
304
- fixture_spec=fixture_spec,
305
- require_hypothesis_trigger=require_hypothesis_trigger,
306
- )
307
- trigger_reasons = pair_trigger_reasons(pair)
308
- row = {
309
- "fixture_id": fixture_id,
310
- "run_id": run_id,
311
- "solo_verdict": solo_verdict,
312
- "pair_verdict": pair_verdict,
313
- "pair_mode": is_true(pair.get("pair_mode")),
314
- "pair_trigger_eligible": pair_trigger_eligible(pair),
315
- "pair_trigger_reasons": trigger_reasons,
316
- "pair_trigger_has_canonical_reason": has_canonical_pair_trigger_reason(trigger_reasons),
317
- "pair_trigger_missed": is_true(comparison.get("pair_trigger_missed")),
318
- "pair_trigger_failures": trigger_failures,
319
- "external_lift": is_true(comparison.get("pair_verdict_lift")),
320
- "internal_lift": is_true(comparison.get("pair_internal_verdict_lift")),
321
- "pair_found_more_findings": is_true(comparison.get("pair_found_more_findings")),
322
- "pair_found_more_low_or_worse": is_true(comparison.get("pair_found_more_low_or_worse")),
323
- "row_failed_before_compare": is_true(comparison.get("row_failed_before_compare")),
324
- "row_exit": comparison.get("row_exit"),
325
- "compare_missing": is_true(comparison.get("compare_missing")),
326
- "solo_invoke_exit": solo.get("invoke_exit"),
327
- "pair_invoke_exit": pair.get("invoke_exit"),
328
- "solo_failure_reason": solo.get("invoke_failure_reason")
329
- or transcript_failure_reason(results_root, run_id, "solo"),
330
- "pair_failure_reason": pair.get("invoke_failure_reason")
331
- or transcript_failure_reason(results_root, run_id, "pair"),
332
- "solo_invoke_failure": is_true(solo.get("invoke_failure")),
333
- "pair_invoke_failure": is_true(pair.get("invoke_failure")),
334
- "solo_environment_contamination": is_true(solo.get("environment_contamination")),
335
- "pair_environment_contamination": is_true(pair.get("environment_contamination")),
336
- "solo_disqualifier": is_true(solo.get("disqualifier")),
337
- "pair_disqualifier": is_true(pair.get("disqualifier")),
338
- "solo_timed_out": is_true(solo.get("timed_out")),
339
- "pair_timed_out": is_true(pair.get("timed_out")),
340
- "pair_solo_wall_ratio": pair_ratio,
341
- "solo_mechanical": verdict_field(solo_sub, "mechanical"),
342
- "pair_mechanical": verdict_field(pair_sub, "mechanical"),
343
- "included_in_gate": gate_row.get("status") == "PASS",
344
- "gate_failures": gate_row.get("failures") or [],
345
- "malformed_compare": malformed_compare,
346
- }
347
- row["classification"] = classify(row, row["included_in_gate"])
348
- return row
349
-
350
-
351
- def fmt_ratio(value: Any) -> str:
352
- return f"{value:.2f}x" if isinstance(value, (int, float)) else "n/a"
353
-
354
-
355
- def fmt_trigger_reasons(value: Any) -> str:
356
- if not isinstance(value, list) or not all(isinstance(item, str) for item in value):
357
- return ""
358
- return ",".join(value)
359
-
360
-
361
- def write_md(path: Path, report: dict[str, Any]) -> None:
362
- lines = [
363
- f"# {report['title']}",
364
- "",
365
- f"Verdict: **{report['verdict']}**",
366
- "",
367
- f"Runs: {report['runs_total']}",
368
- f"Included in gate: {report['gate_rows']}",
369
- f"Excluded/recall/no-lift: {report['excluded_or_recall_rows']}",
370
- f"Gate rate: {report['gate_rate']:.3f}",
371
- f"Trailing non-gate rows: {report['trailing_non_gate_rows']}",
372
- ]
373
- if report["yield_thresholds"]:
374
- lines.extend(["", f"Yield verdict: **{report['yield_verdict']}**"])
375
- if report["yield_failures"]:
376
- lines.append("Yield failures:")
377
- lines.extend(f"- {failure}" for failure in report["yield_failures"])
378
- if report.get("gate_artifact_json"):
379
- lines.extend(["", f"Gate artifact: `{report['gate_artifact_json']}`"])
380
- lines.extend(["", "Classification counts:"])
381
- for name, count in sorted(report["classification_counts"].items()):
382
- lines.append(f"- {name}: {count}")
383
- lines.extend(
384
- [
385
- "",
386
- "| Fixture | Solo VERIFY | Pair VERIFY | Pair mode | Pair trigger | Triggers | Wall ratio | External lift | Internal lift | Included | Classification |",
387
- "|---|---|---|---|---|---|---:|---|---|---|---|",
388
- ]
389
- )
390
- for row in report["rows"]:
391
- lines.append(
392
- f"| {row['fixture_id']} | {row['solo_verdict']} | {row['pair_verdict']} | "
393
- f"{str(row['pair_mode']).lower()} | {pair_trigger_label(row)} | "
394
- f"{fmt_trigger_reasons(row.get('pair_trigger_reasons'))} | "
395
- f"{fmt_ratio(row.get('pair_solo_wall_ratio'))} | "
396
- f"{str(row['external_lift']).lower()} | {str(row['internal_lift']).lower()} | "
397
- f"{str(row['included_in_gate']).lower()} | {row['classification']} |"
398
- )
399
- lines.append("")
400
- path.write_text("\n".join(lines), encoding="utf8")
401
-
402
-
403
- def main() -> int:
404
- parser = argparse.ArgumentParser()
405
- parser.add_argument("--results-root", default="benchmark/auto-resolve/results", type=Path)
406
- parser.add_argument("--fixtures-root", type=Path)
407
- parser.add_argument("--run-id", action="append", required=True)
408
- parser.add_argument("--gate-json", type=Path)
409
- parser.add_argument("--title", required=True)
410
- parser.add_argument("--verdict", required=True)
411
- parser.add_argument("--min-gate-rate", type=min_gate_rate)
412
- parser.add_argument("--max-trailing-non-gate", type=non_negative_int)
413
- parser.add_argument(
414
- "--require-hypothesis-trigger",
415
- action="store_true",
416
- help="require fixtures with actionable solo-headroom hypotheses to expose spec.solo_headroom_hypothesis in pair_trigger.reasons",
417
- )
418
- parser.add_argument("--out-json", required=True, type=Path)
419
- parser.add_argument("--out-md", required=True, type=Path)
420
- args = parser.parse_args()
421
- if args.require_hypothesis_trigger and args.fixtures_root is None:
422
- parser.error("--require-hypothesis-trigger requires --fixtures-root")
423
-
424
- gate_rows_by_id = load_gate_rows(args.gate_json)
425
- rows = [
426
- build_row(
427
- args.results_root,
428
- run_id,
429
- gate_rows_by_id,
430
- fixtures_root=args.fixtures_root,
431
- require_hypothesis_trigger=args.require_hypothesis_trigger,
432
- )
433
- for run_id in args.run_id
434
- ]
435
- gate_rows = sum(1 for row in rows if row["included_in_gate"])
436
- trailing_non_gate_rows = 0
437
- for row in reversed(rows):
438
- if row["included_in_gate"]:
439
- break
440
- trailing_non_gate_rows += 1
441
- gate_rate = gate_rows / len(rows) if rows else 0.0
442
- yield_thresholds = {
443
- "min_gate_rate": args.min_gate_rate,
444
- "max_trailing_non_gate": args.max_trailing_non_gate,
445
- }
446
- thresholds_configured = any(value is not None for value in yield_thresholds.values())
447
- yield_failures = []
448
- if args.min_gate_rate is not None and gate_rate < args.min_gate_rate:
449
- yield_failures.append(f"gate rate {gate_rate:.3f} < minimum {args.min_gate_rate:.3f}")
450
- if args.max_trailing_non_gate is not None and trailing_non_gate_rows > args.max_trailing_non_gate:
451
- yield_failures.append(
452
- f"trailing non-gate rows {trailing_non_gate_rows} > maximum {args.max_trailing_non_gate}"
453
- )
454
- report = {
455
- "title": args.title,
456
- "verdict": args.verdict,
457
- "runs_total": len(rows),
458
- "gate_rows": gate_rows,
459
- "excluded_or_recall_rows": len(rows) - gate_rows,
460
- "gate_rate": gate_rate,
461
- "trailing_non_gate_rows": trailing_non_gate_rows,
462
- "classification_counts": dict(Counter(row["classification"] for row in rows)),
463
- "yield_thresholds": {
464
- key: value for key, value in yield_thresholds.items() if value is not None
465
- },
466
- "yield_verdict": "FAIL" if yield_failures else "PASS" if thresholds_configured else "NOT_CONFIGURED",
467
- "yield_failures": yield_failures,
468
- "gate_artifact_json": str(args.gate_json) if args.gate_json else None,
469
- "rows": rows,
470
- }
471
- args.out_json.write_text(json.dumps(report, indent=2) + "\n", encoding="utf8")
472
- write_md(args.out_md, report)
473
- print(json.dumps(report, indent=2))
474
- return 2 if yield_failures else 0
475
-
476
-
477
- if __name__ == "__main__":
478
- raise SystemExit(main())