code-coordinator 0.5.195__tar.gz → 0.5.197__tar.gz

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 (792) hide show
  1. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/.github/workflows/test.yml +33 -0
  2. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/PKG-INFO +1 -1
  3. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/code_coordinator.egg-info/PKG-INFO +1 -1
  4. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/code_coordinator.egg-info/SOURCES.txt +3 -1
  5. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/code_coordinator.egg-info/scm_file_list.json +3 -1
  6. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/code_coordinator.egg-info/scm_version.json +2 -2
  7. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/commands/release.py +67 -1
  8. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/commands/status.py +43 -0
  9. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/release_cordon.py +43 -0
  10. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/release_propagate.py +8 -0
  11. code_coordinator-0.5.197/scripts/check_gh_argv_containment.py +176 -0
  12. code_coordinator-0.5.197/tests/test_check_gh_argv_containment.py +156 -0
  13. code_coordinator-0.5.197/tests/test_release_cordon_stuck_2490.py +272 -0
  14. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_release_propagate.py +20 -0
  15. code_coordinator-0.5.195/tests/test_no_direct_gh_calls.py +0 -112
  16. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/.claude/commands/board.md +0 -0
  17. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/.claude/commands/complete-session.md +0 -0
  18. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/.claude/commands/coordinator.md +0 -0
  19. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/.githooks/_lib.sh +0 -0
  20. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/.githooks/post-checkout +0 -0
  21. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/.githooks/post-commit +0 -0
  22. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/.githooks/post-merge +0 -0
  23. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/.github/ISSUE_TEMPLATE/bug_report.md +0 -0
  24. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/.github/coord-ci-acceptance.yml +0 -0
  25. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/.github/workflows/auto-release.yml +0 -0
  26. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/.github/workflows/cargo-test.yml +0 -0
  27. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/.github/workflows/publish.yml +0 -0
  28. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/.github/workflows/release-tui.yml +0 -0
  29. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/.gitignore +0 -0
  30. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/CLAUDE.md +0 -0
  31. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/GOAL.md +0 -0
  32. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/LICENSE +0 -0
  33. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/MANIFEST.in +0 -0
  34. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/README.md +0 -0
  35. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/code_coordinator.egg-info/dependency_links.txt +0 -0
  36. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/code_coordinator.egg-info/entry_points.txt +0 -0
  37. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/code_coordinator.egg-info/requires.txt +0 -0
  38. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/code_coordinator.egg-info/top_level.txt +0 -0
  39. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/__init__.py +0 -0
  40. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/_board_mapping.py +0 -0
  41. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/acceptance.py +0 -0
  42. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/acceptance_drivers.py +0 -0
  43. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/agent.py +0 -0
  44. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/agent_app.py +0 -0
  45. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/agent_update.py +0 -0
  46. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/agents/opencode/.gitignore +0 -0
  47. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/agents/opencode/agents/work.md +0 -0
  48. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/agents/opencode/routing.jsonc +0 -0
  49. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/audit.py +0 -0
  50. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/auto_loop.py +0 -0
  51. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/block_log.py +0 -0
  52. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/board_bool_guard.py +0 -0
  53. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/board_service.py +0 -0
  54. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/board_wire.py +0 -0
  55. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/brain.py +0 -0
  56. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/branch_model.py +0 -0
  57. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/bug_intake.py +0 -0
  58. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/cargo_cache.py +0 -0
  59. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/ci_github.py +0 -0
  60. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/ci_store.py +0 -0
  61. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/claim.py +0 -0
  62. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/cli.py +0 -0
  63. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/client.py +0 -0
  64. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/commands/__init__.py +0 -0
  65. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/commands/_common.py +0 -0
  66. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/commands/acceptance.py +0 -0
  67. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/commands/agent_ops.py +0 -0
  68. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/commands/audit.py +0 -0
  69. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/commands/chat.py +0 -0
  70. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/commands/dispatch.py +0 -0
  71. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/commands/dispatch_workers.py +0 -0
  72. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/commands/drive.py +0 -0
  73. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/commands/drive_queue.py +0 -0
  74. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/commands/gate_a.py +0 -0
  75. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/commands/gates.py +0 -0
  76. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/commands/issues.py +0 -0
  77. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/commands/lifecycle.py +0 -0
  78. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/commands/merge.py +0 -0
  79. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/commands/milestone.py +0 -0
  80. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/commands/plan_followup.py +0 -0
  81. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/commands/plans.py +0 -0
  82. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/commands/portal.py +0 -0
  83. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/commands/repo.py +0 -0
  84. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/commands/report.py +0 -0
  85. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/commands/review.py +0 -0
  86. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/commands/scorecard.py +0 -0
  87. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/commands/sessions.py +0 -0
  88. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/commands/setup.py +0 -0
  89. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/commands/terminal.py +0 -0
  90. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/commands/test_gate.py +0 -0
  91. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/commands/tui.py +0 -0
  92. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/comments.py +0 -0
  93. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/config.py +0 -0
  94. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/config_reload.py +0 -0
  95. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/confirm_test.py +0 -0
  96. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/conflict_fix.py +0 -0
  97. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/dao.py +0 -0
  98. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/dashboard/__init__.py +0 -0
  99. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/dashboard/fixture.py +0 -0
  100. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/dashboard/index.html +0 -0
  101. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/dashboard/server.py +0 -0
  102. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/dashboard/terminal.py +0 -0
  103. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/db.py +0 -0
  104. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/dead_end.py +0 -0
  105. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/deploy/README.md +0 -0
  106. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/deploy/coord-agent.service +0 -0
  107. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/deploy/coord-db-backup.service +0 -0
  108. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/deploy/coord-db-backup.sh +0 -0
  109. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/deploy/coord-db-backup.timer +0 -0
  110. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/deploy/coord-drive-queue.service +0 -0
  111. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/deploy/coord-drive-queue.timer +0 -0
  112. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/deploy/coord-notify.service +0 -0
  113. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/deploy/coord-notify.timer +0 -0
  114. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/deploy/coord-release-propagate.service +0 -0
  115. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/deploy/coord-release-propagate.timer +0 -0
  116. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/deploy/coord-release-window.service +0 -0
  117. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/deploy/coord-release-window.timer +0 -0
  118. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/deploy/coord-serve.service +0 -0
  119. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/deploy/coord-web-dist-build.service +0 -0
  120. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/deploy/coord-web-dist-build.timer +0 -0
  121. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/deploy/coord-web.service +0 -0
  122. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/deploy_manifest.py +0 -0
  123. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/deploy_units.py +0 -0
  124. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/deps.py +0 -0
  125. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/diagnose.py +0 -0
  126. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/dispatch.py +0 -0
  127. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/dist_name.py +0 -0
  128. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/drive.py +0 -0
  129. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/drive_queue.py +0 -0
  130. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/drive_state.py +0 -0
  131. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/events.py +0 -0
  132. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/failure_class.py +0 -0
  133. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/filelock.py +0 -0
  134. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/fleet_config_health.py +0 -0
  135. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/forge_availability.py +0 -0
  136. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/freshness.py +0 -0
  137. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/gate_a.py +0 -0
  138. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/gate_b.py +0 -0
  139. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/gate_snapshot.py +0 -0
  140. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/gates.py +0 -0
  141. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/github_ops.py +0 -0
  142. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/goal.py +0 -0
  143. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/graph_health.py +0 -0
  144. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/health/__init__.py +0 -0
  145. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/health/aggregate.py +0 -0
  146. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/health/checks/__init__.py +0 -0
  147. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/health/checks/agent_install.py +0 -0
  148. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/health/checks/cargo_targets.py +0 -0
  149. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/health/checks/claude_binary.py +0 -0
  150. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/health/checks/coord_web_ci_pin.py +0 -0
  151. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/health/checks/deploy_lane_facts.py +0 -0
  152. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/health/checks/disk.py +0 -0
  153. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/health/checks/fleet_board.py +0 -0
  154. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/health/checks/fleet_deploy_lanes.py +0 -0
  155. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/health/checks/fleet_phantom.py +0 -0
  156. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/health/checks/fleet_unit_drift.py +0 -0
  157. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/health/checks/graph.py +0 -0
  158. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/health/checks/graphify_cli.py +0 -0
  159. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/health/checks/index_lock.py +0 -0
  160. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/health/checks/plan_usage.py +0 -0
  161. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/health/checks/repo_state.py +0 -0
  162. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/health/checks/spawned_coord.py +0 -0
  163. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/health/checks/timer_active.py +0 -0
  164. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/health/checks/toolchain.py +0 -0
  165. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/health/checks/unit_drift.py +0 -0
  166. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/health/checks/unit_enablement.py +0 -0
  167. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/health/checks/worktrees.py +0 -0
  168. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/health/cli.py +0 -0
  169. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/health/context.py +0 -0
  170. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/health/fleet_snapshot.py +0 -0
  171. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/health/models.py +0 -0
  172. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/health/pypi.py +0 -0
  173. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/health/registry.py +0 -0
  174. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/health/render.py +0 -0
  175. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/health/units.py +0 -0
  176. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/hooks.py +0 -0
  177. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/housekeeping.py +0 -0
  178. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/interactive.py +0 -0
  179. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/issue_store.py +0 -0
  180. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/liveness_auditor.py +0 -0
  181. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/machine_pause.py +0 -0
  182. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/merge_queue.py +0 -0
  183. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/milestone_chat.py +0 -0
  184. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/milestone_dispatch.py +0 -0
  185. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/milestone_gate.py +0 -0
  186. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/milestone_order.py +0 -0
  187. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/mock_author.py +0 -0
  188. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/models.py +0 -0
  189. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/network.py +0 -0
  190. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/new_issue_chat.py +0 -0
  191. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/notifier/__init__.py +0 -0
  192. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/notifier/baseline.py +0 -0
  193. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/notifier/cli.py +0 -0
  194. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/notifier/collect.py +0 -0
  195. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/notifier/digest.py +0 -0
  196. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/notifier/models.py +0 -0
  197. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/notifier/predicate.py +0 -0
  198. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/notifier/service.py +0 -0
  199. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/notifier/store.py +0 -0
  200. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/notifier/transport.py +0 -0
  201. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/notify.py +0 -0
  202. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/openapi.py +0 -0
  203. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/overlap_fence.py +0 -0
  204. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/overlap_predict.py +0 -0
  205. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/parentage.py +0 -0
  206. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/parentage_github.py +0 -0
  207. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/pipeline.py +0 -0
  208. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/plan_parser.py +0 -0
  209. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/plans.py +0 -0
  210. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/platform_paths.py +0 -0
  211. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/portal_bridge.py +0 -0
  212. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/portal_store.py +0 -0
  213. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/portal_sync.py +0 -0
  214. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/pr_body_lint.py +0 -0
  215. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/prereqs.py +0 -0
  216. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/progress.py +0 -0
  217. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/providers/__init__.py +0 -0
  218. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/providers/base.py +0 -0
  219. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/providers/claude.py +0 -0
  220. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/providers/claude_pty.py +0 -0
  221. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/providers/opencode.py +0 -0
  222. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/queue_diagnose.py +0 -0
  223. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/reconcile.py +0 -0
  224. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/reconcile_tick.py +0 -0
  225. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/refine_chat.py +0 -0
  226. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/release_verify.py +0 -0
  227. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/release_window.py +0 -0
  228. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/repo_edit.py +0 -0
  229. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/repo_onboard.py +0 -0
  230. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/reports.py +0 -0
  231. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/revalidate.py +0 -0
  232. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/review.py +0 -0
  233. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/scorecard.py +0 -0
  234. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/self_health.py +0 -0
  235. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/serve_app.py +0 -0
  236. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/skills/coord-dispatch-verbs/SKILL.md +0 -0
  237. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/skills/drive-queue-preflight/SKILL.md +0 -0
  238. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/skills/fleet-restart-safety/SKILL.md +0 -0
  239. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/skills/merge-stuck-triage/SKILL.md +0 -0
  240. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/skills/pipeline-limbo-triage/SKILL.md +0 -0
  241. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/skills/portal-followup/SKILL.md +0 -0
  242. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/skills/review-verdict-recovery/SKILL.md +0 -0
  243. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/skills/tui-quadraui-workflow/SKILL.md +0 -0
  244. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/skills/update-issue/SKILL.md +0 -0
  245. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/smoke.py +0 -0
  246. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/spend_ceiling.py +0 -0
  247. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/split_work.py +0 -0
  248. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/stage_projection.py +0 -0
  249. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/state.py +0 -0
  250. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/test_author.py +0 -0
  251. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/test_chat.py +0 -0
  252. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/test_orchestrator.py +0 -0
  253. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/test_report.py +0 -0
  254. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/tui_release.py +0 -0
  255. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/usage.py +0 -0
  256. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/usage_limits.py +0 -0
  257. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/usage_rollup.py +0 -0
  258. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coord/worker_events.py +0 -0
  259. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/coordinator.example.yml +0 -0
  260. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/deploy/coord-agent.service +0 -0
  261. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/deploy/coord-db-backup.service +0 -0
  262. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/deploy/coord-db-backup.sh +0 -0
  263. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/deploy/coord-db-backup.timer +0 -0
  264. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/deploy/coord-drive-queue.service +0 -0
  265. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/deploy/coord-drive-queue.timer +0 -0
  266. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/deploy/coord-notify.service +0 -0
  267. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/deploy/coord-notify.timer +0 -0
  268. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/deploy/coord-release-propagate.service +0 -0
  269. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/deploy/coord-release-propagate.timer +0 -0
  270. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/deploy/coord-release-window.service +0 -0
  271. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/deploy/coord-release-window.timer +0 -0
  272. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/deploy/coord-serve.service +0 -0
  273. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/deploy/coord-web-dist-build.service +0 -0
  274. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/deploy/coord-web-dist-build.sh +0 -0
  275. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/deploy/coord-web-dist-build.timer +0 -0
  276. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/deploy/coord-web-rollback.sh +0 -0
  277. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/deploy/coord-web.service +0 -0
  278. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/deploy/node-shim.sh +0 -0
  279. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/docs/ADR_COORD_WEB_ACCEPTANCE_SUITE.md +0 -0
  280. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/docs/ADR_COORD_WEB_CI.md +0 -0
  281. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/docs/ADR_COORD_WEB_DIST.md +0 -0
  282. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/docs/AGENT_OPERATIONS.md +0 -0
  283. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/docs/ARCHITECTURE.md +0 -0
  284. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/docs/ARCH_SECURITY_GATES.md +0 -0
  285. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/docs/COCKPIT.md +0 -0
  286. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/docs/CONTROL_CENTER.md +0 -0
  287. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/docs/COST_DISCIPLINE.md +0 -0
  288. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/docs/CROSS_PLATFORM.md +0 -0
  289. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/docs/CUSTOMER_PORTAL.md +0 -0
  290. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/docs/DRIVE_QUEUE.md +0 -0
  291. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/docs/EPHEMERAL_WORKERS.md +0 -0
  292. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/docs/FORGE_MIGRATION.md +0 -0
  293. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/docs/GRAPHIFY_SETUP.md +0 -0
  294. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/docs/ISSUE_GUIDANCE.md +0 -0
  295. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/docs/MAC_MINI.md +0 -0
  296. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/docs/MERGE_AUTO_DRAIN_TRUST_BAR.md +0 -0
  297. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/docs/NOTIFIER.md +0 -0
  298. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/docs/OPENCODE_VERIFICATION.md +0 -0
  299. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/docs/OPERATING_GOTCHAS.md +0 -0
  300. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/docs/ORACLE_LOOP.md +0 -0
  301. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/docs/PHONE_WEBAPP.md +0 -0
  302. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/docs/PIPELINE_V2.md +0 -0
  303. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/docs/PLATFORM_EVOLUTION.md +0 -0
  304. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/docs/SECOND_BACKEND.md +0 -0
  305. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/docs/STORE_SERVICE.md +0 -0
  306. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/docs/TEST_FIRST_BUG_LANE.md +0 -0
  307. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/docs/WEB_CONTROL_CENTER.md +0 -0
  308. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/docs/WSL_WINDOWS_WORKER.md +0 -0
  309. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/docs/mocks/web/README.md +0 -0
  310. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/docs/mocks/web/_tokens.css +0 -0
  311. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/docs/mocks/web/issue-detail.html +0 -0
  312. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/docs/mocks/web/pipeline-narrow.html +0 -0
  313. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/docs/mocks/web/pipeline-wide.html +0 -0
  314. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/graphify-out/.gitignore +0 -0
  315. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/install-agent.sh +0 -0
  316. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/pyproject.toml +0 -0
  317. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/scripts/audit_review_verdict_overrides.py +0 -0
  318. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/scripts/azure-workers/bootstrap-shared.sh +0 -0
  319. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/scripts/azure-workers/build-worker-image.sh +0 -0
  320. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/scripts/azure-workers/coordinator-machine.py +0 -0
  321. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/scripts/azure-workers/epic-down.sh +0 -0
  322. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/scripts/azure-workers/epic-up.sh +0 -0
  323. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/scripts/azure-workers/preflight.sh +0 -0
  324. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/scripts/azure-workers/provision-worker.sh +0 -0
  325. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/scripts/azure-workers/scrub-and-generalize.sh +0 -0
  326. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/scripts/azure-workers/tailnet-acl.hujson +0 -0
  327. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/scripts/azure-workers/verify-github-token.sh +0 -0
  328. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/scripts/codegen.py +0 -0
  329. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/scripts/coord-test-runner.sh +0 -0
  330. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/scripts/drive-batch.sh +0 -0
  331. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/scripts/gen_board_fixture.py +0 -0
  332. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/scripts/next_release_tag.py +0 -0
  333. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/scripts/run_tests_in_populated_home.sh +0 -0
  334. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/scripts/run_tests_without_gh.sh +0 -0
  335. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/scripts/smoke_437_interactive.py +0 -0
  336. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/scripts/verify_878_review_capture.py +0 -0
  337. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/scripts/verify_release_published.py +0 -0
  338. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/scripts/verify_release_wheel.py +0 -0
  339. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/setup.cfg +0 -0
  340. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/SMOKE_SET.md +0 -0
  341. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/__init__.py +0 -0
  342. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-33/audit_1039.rs +0 -0
  343. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-33/contract.md +0 -0
  344. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-33/manifest.yml +0 -0
  345. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-33/mocks/audit-panel-detail.screen +0 -0
  346. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-33/mocks/audit-panel-empty.screen +0 -0
  347. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-33/mocks/audit-panel-filters.screen +0 -0
  348. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-33/mocks/audit-panel-populated.screen +0 -0
  349. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-37/conftest.py +0 -0
  350. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-37/contract.md +0 -0
  351. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-37/manifest.yml +0 -0
  352. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-37/test_usage_cli_1115.py +0 -0
  353. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-37/test_usage_core_1118.py +0 -0
  354. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-38/contract.md +0 -0
  355. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-38/manifest.yml +0 -0
  356. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-38/mocks/plans-base.screen +0 -0
  357. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-38/mocks/plans-detail-pane.screen +0 -0
  358. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-38/mocks/plans-help-overlay.screen +0 -0
  359. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-38/mocks/plans-palette.screen +0 -0
  360. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-38/mocks/plans-rightclick-epic.screen +0 -0
  361. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-38/mocks/plans-rightclick-header.screen +0 -0
  362. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-38/mocks/plans-rightclick-stub.screen +0 -0
  363. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-38/plans_detail_1122.rs +0 -0
  364. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-38/plans_help_1124.rs +0 -0
  365. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-38/plans_rightclick_1123.rs +0 -0
  366. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-51/contract.md +0 -0
  367. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-51/home-active-extended.spec.ts +0 -0
  368. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-51/home-active.spec.ts +0 -0
  369. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-51/manifest.yml +0 -0
  370. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-51/mocks/home-active.html +0 -0
  371. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-51/tsconfig.json +0 -0
  372. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-65/board_split_2288.rs +0 -0
  373. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-65/board_tabs_2282.rs +0 -0
  374. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-65/board_tabs_close_2283.rs +0 -0
  375. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-65/contract.md +0 -0
  376. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-65/detail_substate_2285.rs +0 -0
  377. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-65/manifest.yml +0 -0
  378. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-65/mocks/board-baseline-no-tabs.screen +0 -0
  379. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-65/mocks/board-pinned-3-tabs.screen +0 -0
  380. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-65/mocks/board-preview-tab.screen +0 -0
  381. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-65/mocks/board-split-side-by-side.screen +0 -0
  382. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-65/mocks/board-tab-context-menu.screen +0 -0
  383. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-65/mocks/board-tabs-help-overlay.screen +0 -0
  384. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-65/mocks/board-tabs-overflow.screen +0 -0
  385. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-65/mocks/pipeline-tabs-independent.screen +0 -0
  386. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-65/pipeline_tabs_2284.rs +0 -0
  387. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-65/tabs_discoverability_2287.rs +0 -0
  388. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-65/tabs_persistence_2286.rs +0 -0
  389. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/acceptance/ms-example/mocks/home-active.html +0 -0
  390. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/conftest.py +0 -0
  391. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/fixtures/board-pipeline-basic.json +0 -0
  392. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/fixtures/board-pipeline-terminal-gates.json +0 -0
  393. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/fixtures/opencode_run_failure_sample.jsonl +0 -0
  394. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/fixtures/opencode_run_length_sample.jsonl +0 -0
  395. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/fixtures/opencode_run_sample.jsonl +0 -0
  396. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/fixtures/playwright/all_pass.json +0 -0
  397. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/fixtures/playwright/global_setup_crash.json +0 -0
  398. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/fixtures/playwright/mixed_fail.json +0 -0
  399. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/fixtures/playwright/retry_then_pass.json +0 -0
  400. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/fixtures/playwright/retry_then_pass.junit.xml +0 -0
  401. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/fixtures/playwright/skip.json +0 -0
  402. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/fixtures/playwright/truncated.json +0 -0
  403. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/fixtures/test_report/cargo_compile_error.txt +0 -0
  404. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/fixtures/test_report/cargo_multi_target_failures.txt +0 -0
  405. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/fixtures/test_report/cargo_no_parseable_failures.txt +0 -0
  406. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/fixtures/test_report/pytest_collection_error.txt +0 -0
  407. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/fixtures/test_report/pytest_error_string_in_body.txt +0 -0
  408. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/fixtures/test_report/pytest_internal_error.txt +0 -0
  409. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/fixtures/test_report/pytest_mixed_failures.txt +0 -0
  410. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/fixtures/test_report/pytest_no_parseable_failures.txt +0 -0
  411. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_acceptance.py +0 -0
  412. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_acceptance_drivers.py +0 -0
  413. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_agent.py +0 -0
  414. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_agent_api_error.py +0 -0
  415. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_agent_app.py +0 -0
  416. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_agent_branch_base.py +0 -0
  417. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_agent_branch_capture.py +0 -0
  418. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_agent_config_free_1712.py +0 -0
  419. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_agent_deploy_units_endpoint.py +0 -0
  420. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_agent_dirty_worktree.py +0 -0
  421. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_agent_drive_queue_reconcile_2373.py +0 -0
  422. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_agent_graph_self_heal.py +0 -0
  423. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_agent_health_h3.py +0 -0
  424. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_agent_idle_restart.py +0 -0
  425. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_agent_push_failure.py +0 -0
  426. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_agent_reap.py +0 -0
  427. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_agent_repos_and_pull.py +0 -0
  428. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_agent_restart_services_endpoint.py +0 -0
  429. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_agent_skills_self_heal.py +0 -0
  430. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_agent_startup_diagnostics.py +0 -0
  431. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_agent_update.py +0 -0
  432. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_agent_update_bluegreen.py +0 -0
  433. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_agent_usage_limit.py +0 -0
  434. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_agent_zero_commit.py +0 -0
  435. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_ambient_home_isolation.py +0 -0
  436. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_approve_reject_plan.py +0 -0
  437. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_approve_usage_gate.py +0 -0
  438. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_assignment_already_recorded_daemon.py +0 -0
  439. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_audit_log.py +0 -0
  440. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_audit_outcome.py +0 -0
  441. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_audit_query.py +0 -0
  442. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_auto_loop.py +0 -0
  443. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_auto_release_publish_2035.py +0 -0
  444. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_base_checkout_restore.py +0 -0
  445. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_block_log.py +0 -0
  446. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_board_cap_762.py +0 -0
  447. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_board_fixture.py +0 -0
  448. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_board_read_path.py +0 -0
  449. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_board_service.py +0 -0
  450. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_board_state.py +0 -0
  451. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_board_wire.py +0 -0
  452. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_brain.py +0 -0
  453. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_branch_model.py +0 -0
  454. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_bug_intake.py +0 -0
  455. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_build_worker_image_env_update.py +0 -0
  456. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cargo_cache.py +0 -0
  457. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_ci_acceptance_gate_1950.py +0 -0
  458. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_ci_parity_2091.py +0 -0
  459. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_ci_store.py +0 -0
  460. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_claim.py +0 -0
  461. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_acceptance.py +0 -0
  462. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_assign.py +0 -0
  463. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_assign_interactive_oracle_gate.py +0 -0
  464. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_assign_interactive_remote.py +0 -0
  465. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_assign_provider.py +0 -0
  466. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_assign_repo_drift_2219.py +0 -0
  467. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_audit.py +0 -0
  468. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_chat_continue.py +0 -0
  469. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_decide.py +0 -0
  470. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_diagnose_config_provenance.py +0 -0
  471. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_diagnose_forge_availability.py +0 -0
  472. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_diagnose_graph.py +0 -0
  473. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_diagnose_self.py +0 -0
  474. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_doctor.py +0 -0
  475. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_doctor_config_free_1801.py +0 -0
  476. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_doctor_config_mismatch_1712.py +0 -0
  477. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_drive.py +0 -0
  478. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_drive_queue.py +0 -0
  479. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_escalate.py +0 -0
  480. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_fix_headless_review.py +0 -0
  481. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_gate_a.py +0 -0
  482. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_install_drift.py +0 -0
  483. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_install_skills.py +0 -0
  484. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_issue_create_label.py +0 -0
  485. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_issue_reopen.py +0 -0
  486. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_merge.py +0 -0
  487. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_milestone_assign.py +0 -0
  488. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_milestone_capture.py +0 -0
  489. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_milestone_chat_add_child.py +0 -0
  490. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_milestone_dispatch.py +0 -0
  491. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_milestone_gate_b.py +0 -0
  492. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_milestone_gate_c.py +0 -0
  493. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_milestone_order.py +0 -0
  494. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_milestone_remove_and_issue_close.py +0 -0
  495. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_milestone_ship.py +0 -0
  496. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_network.py +0 -0
  497. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_new_issue_chat.py +0 -0
  498. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_plans.py +0 -0
  499. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_portal.py +0 -0
  500. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_pull_artifact.py +0 -0
  501. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_queue.py +0 -0
  502. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_reattach_sessions.py +0 -0
  503. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_refine_board.py +0 -0
  504. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_release_preflight.py +0 -0
  505. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_release_propagate.py +0 -0
  506. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_release_window.py +0 -0
  507. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_repo_2220.py +0 -0
  508. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_scorecard.py +0 -0
  509. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_set_review_findings.py +0 -0
  510. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_status_advisory_terminal.py +0 -0
  511. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_status_merge_queue.py +0 -0
  512. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_status_provider.py +0 -0
  513. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_status_review_finalizing.py +0 -0
  514. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_status_test_failed_tag.py +0 -0
  515. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_status_usage_limit.py +0 -0
  516. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_sync_comments_873.py +0 -0
  517. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_test_plan.py +0 -0
  518. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_track.py +0 -0
  519. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_tui_update.py +0 -0
  520. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cli_wait.py +0 -0
  521. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_client_base_install.py +0 -0
  522. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_comments.py +0 -0
  523. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_completion_summary.py +0 -0
  524. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_config.py +0 -0
  525. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_config_acceptance.py +0 -0
  526. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_config_audit.py +0 -0
  527. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_config_pricing.py +0 -0
  528. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_config_snapshot_noncanonical_2208.py +0 -0
  529. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_config_usage_gate.py +0 -0
  530. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_confirm_test.py +0 -0
  531. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_conflict_fix.py +0 -0
  532. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_conflict_fix_semantic.py +0 -0
  533. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_coord_test.py +0 -0
  534. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_coord_test_runner_baseline.py +0 -0
  535. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_coord_test_runner_populated_home.py +0 -0
  536. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_coord_test_runner_routing.py +0 -0
  537. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_coord_test_runner_toolchain.py +0 -0
  538. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_coord_web_sse_restart_live.py +0 -0
  539. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_coordinator_machine.py +0 -0
  540. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_cross_platform_imports.py +0 -0
  541. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_dashboard.py +0 -0
  542. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_dashboard_fixture.py +0 -0
  543. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_dashboard_terminal.py +0 -0
  544. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_dashboard_terminal_live.py +0 -0
  545. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_db.py +0 -0
  546. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_dead_end.py +0 -0
  547. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_deploy_coord_db_backup.py +0 -0
  548. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_deploy_coord_web_dist.py +0 -0
  549. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_deploy_coord_web_rollback.py +0 -0
  550. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_deploy_drive_queue_unit.py +0 -0
  551. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_deploy_manifest.py +0 -0
  552. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_deploy_units_lane.py +0 -0
  553. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_deploy_web_unit.py +0 -0
  554. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_deps.py +0 -0
  555. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_diagnose.py +0 -0
  556. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_dispatch.py +0 -0
  557. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_dispatch_target_validation.py +0 -0
  558. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_dist_name.py +0 -0
  559. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_done_housekeeping.py +0 -0
  560. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_drive.py +0 -0
  561. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_drive_queue.py +0 -0
  562. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_drive_state.py +0 -0
  563. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_drive_tmux.py +0 -0
  564. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_epic_up_capability_detection.py +0 -0
  565. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_epic_up_down_symlinked_config_1887.py +0 -0
  566. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_epic_up_image_provenance.py +0 -0
  567. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_errors.py +0 -0
  568. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_events.py +0 -0
  569. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_failure_class.py +0 -0
  570. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_filelock.py +0 -0
  571. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_finalize_interactive_exit_test_verdict.py +0 -0
  572. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_fix_of_force_override.py +0 -0
  573. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_fleet_config_health.py +0 -0
  574. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_fleet_health_probes.py +0 -0
  575. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_fleet_health_snapshot.py +0 -0
  576. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_forge_availability.py +0 -0
  577. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_freshness.py +0 -0
  578. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_gate_a.py +0 -0
  579. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_gate_b.py +0 -0
  580. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_gate_snapshot_staleness.py +0 -0
  581. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_gates.py +0 -0
  582. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_gather_fleet_tmux_sessions.py +0 -0
  583. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_generated_types_fixture.py +0 -0
  584. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_github_ops.py +0 -0
  585. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_goal.py +0 -0
  586. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_graph_health.py +0 -0
  587. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_graph_selfheal_absent_2237.py +0 -0
  588. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_handoff.py +0 -0
  589. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_health_checks.py +0 -0
  590. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_health_cli.py +0 -0
  591. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_health_cli_graph.py +0 -0
  592. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_health_config.py +0 -0
  593. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_health_context.py +0 -0
  594. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_health_coord_web_ci_pin.py +0 -0
  595. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_health_deploy_lane_facts.py +0 -0
  596. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_health_incident_regression.py +0 -0
  597. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_health_pypi.py +0 -0
  598. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_health_registry.py +0 -0
  599. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_health_timer_active.py +0 -0
  600. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_health_toolchain.py +0 -0
  601. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_health_unit_drift.py +0 -0
  602. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_health_unit_enablement.py +0 -0
  603. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_hooks.py +0 -0
  604. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_human_attended_437.py +0 -0
  605. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_init.py +0 -0
  606. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_integration.py +0 -0
  607. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_interactive_briefing_echo.py +0 -0
  608. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_interactive_prefill_state.py +0 -0
  609. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_interactive_session_relaunch.py +0 -0
  610. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_interactive_test_verdict_backstop.py +0 -0
  611. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_interactive_token_attribution.py +0 -0
  612. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_interactive_worktree.py +0 -0
  613. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_issue_store_seam.py +0 -0
  614. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_liveness_auditor.py +0 -0
  615. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_liveness_notify.py +0 -0
  616. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_machine_pause.py +0 -0
  617. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_merge_queue.py +0 -0
  618. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_merge_verify.py +0 -0
  619. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_milestone_chat.py +0 -0
  620. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_milestone_dispatch.py +0 -0
  621. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_milestone_gate.py +0 -0
  622. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_milestone_order.py +0 -0
  623. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_milestone_seam.py +0 -0
  624. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_mock_author.py +0 -0
  625. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_model_tiering.py +0 -0
  626. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_models.py +0 -0
  627. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_models_config_labels.py +0 -0
  628. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_needs_attention.py +0 -0
  629. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_network.py +0 -0
  630. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_new_issue_chat.py +0 -0
  631. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_next_release_tag.py +0 -0
  632. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_node_shim.py +0 -0
  633. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_notifier_baseline.py +0 -0
  634. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_notifier_cli.py +0 -0
  635. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_notifier_collect.py +0 -0
  636. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_notifier_config.py +0 -0
  637. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_notifier_drive_seam.py +0 -0
  638. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_notifier_isolation.py +0 -0
  639. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_notifier_predicate.py +0 -0
  640. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_notifier_quiet_hours.py +0 -0
  641. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_notifier_service.py +0 -0
  642. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_notify.py +0 -0
  643. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_notify_drain.py +0 -0
  644. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_openapi.py +0 -0
  645. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_operational_defaults.py +0 -0
  646. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_overlap_fence.py +0 -0
  647. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_overlap_predict.py +0 -0
  648. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_packaged_deploy_units.py +0 -0
  649. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_parentage.py +0 -0
  650. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_paste_landed.py +0 -0
  651. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_pipeline.py +0 -0
  652. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_plan_followup_approve_plan_command.py +0 -0
  653. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_plan_followup_pr_command.py +0 -0
  654. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_plan_followup_review_command.py +0 -0
  655. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_plan_only.py +0 -0
  656. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_plan_parser.py +0 -0
  657. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_platform_paths.py +0 -0
  658. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_portal_bridge.py +0 -0
  659. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_portal_config.py +0 -0
  660. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_portal_sync.py +0 -0
  661. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_pr_body_lint.py +0 -0
  662. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_prereqs.py +0 -0
  663. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_production_db_guard.py +0 -0
  664. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_progress.py +0 -0
  665. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_provider_seam.py +0 -0
  666. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_providers.py +0 -0
  667. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_providers_config_labels.py +0 -0
  668. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_providers_pty.py +0 -0
  669. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_quiet_hours.py +0 -0
  670. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_quiet_hours_store_2146.py +0 -0
  671. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_reap_merged_sessions.py +0 -0
  672. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_reap_stale_interactive_tick.py +0 -0
  673. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_reconcile.py +0 -0
  674. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_reconcile_branch.py +0 -0
  675. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_reconcile_completions.py +0 -0
  676. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_reconcile_merges.py +0 -0
  677. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_reconcile_no_agent_record.py +0 -0
  678. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_reconcile_tick.py +0 -0
  679. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_reconcile_usage_limit_done.py +0 -0
  680. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_refine_chat.py +0 -0
  681. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_release_cordon_2101.py +0 -0
  682. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_release_cordon_daemon_leads_2176.py +0 -0
  683. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_release_cordon_deadlock_2240.py +0 -0
  684. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_release_unified_1242.py +0 -0
  685. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_release_verify.py +0 -0
  686. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_release_window.py +0 -0
  687. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_remote_auto_prune.py +0 -0
  688. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_remote_interactive_reaper.py +0 -0
  689. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_repo_edit_2220.py +0 -0
  690. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_repo_graph_fleet_2237.py +0 -0
  691. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_repo_onboard_2220.py +0 -0
  692. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_report_result_push.py +0 -0
  693. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_reports.py +0 -0
  694. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_retry.py +0 -0
  695. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_retry_advisory_1606.py +0 -0
  696. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_retry_type_1636.py +0 -0
  697. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_revalidate.py +0 -0
  698. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_review.py +0 -0
  699. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_review_end_review_without_verdict.py +0 -0
  700. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_review_parse_failure_diagnostic.py +0 -0
  701. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_review_reaffirm.py +0 -0
  702. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_review_state.py +0 -0
  703. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_review_verdict_backstop.py +0 -0
  704. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_review_verdict_override_audit.py +0 -0
  705. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_review_verdict_relay.py +0 -0
  706. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_review_zero_commits.py +0 -0
  707. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_scoped_review_wiring.py +0 -0
  708. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_scorecard.py +0 -0
  709. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_self_health.py +0 -0
  710. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_serve.py +0 -0
  711. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_serve_app_board_trim.py +0 -0
  712. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_session.py +0 -0
  713. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_slice_issue_attribution.py +0 -0
  714. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_smoke.py +0 -0
  715. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_smoke_live_checkout_restore.py +0 -0
  716. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_smoke_workflow.py +0 -0
  717. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_spend_ceiling.py +0 -0
  718. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_spend_ceiling_coordinator.py +0 -0
  719. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_split.py +0 -0
  720. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_split_work.py +0 -0
  721. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_stage_projection.py +0 -0
  722. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_stalled_pipeline.py +0 -0
  723. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_state.py +0 -0
  724. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_state_review_findings_daemon.py +0 -0
  725. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_status_fleet_footer.py +0 -0
  726. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_stop_1567.py +0 -0
  727. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_stuck.py +0 -0
  728. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_terminal_command.py +0 -0
  729. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_test_author.py +0 -0
  730. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_test_chat.py +0 -0
  731. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_test_orchestrator.py +0 -0
  732. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_test_report.py +0 -0
  733. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_test_verdict_parsing.py +0 -0
  734. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_test_verdict_transcript_floor.py +0 -0
  735. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_thin_client_board_audit.py +0 -0
  736. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_thin_client_config_load_1080.py +0 -0
  737. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_thin_client_daemon_routing_906.py +0 -0
  738. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_tmux_host.py +0 -0
  739. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_tmux_session.py +0 -0
  740. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_transcript_floor.py +0 -0
  741. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_usage.py +0 -0
  742. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_usage_limits.py +0 -0
  743. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_usage_rollup.py +0 -0
  744. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_venv_live_install_2121.py +0 -0
  745. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_version_single_source.py +0 -0
  746. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_watch.py +0 -0
  747. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_windows_job_is_a_real_gate_2000.py +0 -0
  748. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_worker_events.py +0 -0
  749. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_worker_image_pin_sync.py +0 -0
  750. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_worker_safety.py +0 -0
  751. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_worker_test_scoping.py +0 -0
  752. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_worktree.py +0 -0
  753. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tests/test_worktree_rmtree_chokepoint.py +0 -0
  754. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tui/Cargo.lock +0 -0
  755. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tui/Cargo.toml +0 -0
  756. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tui/cargo-config-local-quadraui.toml.example +0 -0
  757. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tui/src/app/audit.rs +0 -0
  758. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tui/src/app/chat.rs +0 -0
  759. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tui/src/app/data.rs +0 -0
  760. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tui/src/app/dialogs.rs +0 -0
  761. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tui/src/app/doc_tabs.rs +0 -0
  762. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tui/src/app/drive.rs +0 -0
  763. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tui/src/app/drive_queue.rs +0 -0
  764. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tui/src/app/escalation.rs +0 -0
  765. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tui/src/app/events.rs +0 -0
  766. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tui/src/app/fixtures.rs +0 -0
  767. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tui/src/app/fleet_health.rs +0 -0
  768. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tui/src/app/fleet_sessions.rs +0 -0
  769. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tui/src/app/fleet_terminals.rs +0 -0
  770. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tui/src/app/format.rs +0 -0
  771. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tui/src/app/milestone_dag.rs +0 -0
  772. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tui/src/app/mod.rs +0 -0
  773. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tui/src/app/msv.rs +0 -0
  774. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tui/src/app/pipeline.rs +0 -0
  775. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tui/src/app/plans.rs +0 -0
  776. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tui/src/app/render.rs +0 -0
  777. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tui/src/app/reports.rs +0 -0
  778. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tui/src/app/sessions.rs +0 -0
  779. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tui/src/app/settings_ui.rs +0 -0
  780. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tui/src/app/sidebar.rs +0 -0
  781. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tui/src/app/terminal.rs +0 -0
  782. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tui/src/app/tests.rs +0 -0
  783. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tui/src/app/types.rs +0 -0
  784. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tui/src/app/workspace.rs +0 -0
  785. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tui/src/bin/gtk.rs +0 -0
  786. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tui/src/commands.rs +0 -0
  787. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tui/src/lib.rs +0 -0
  788. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tui/src/main.rs +0 -0
  789. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tui/src/settings.rs +0 -0
  790. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tui/tests/acceptance.rs +0 -0
  791. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tui/tests/cli.rs +0 -0
  792. {code_coordinator-0.5.195 → code_coordinator-0.5.197}/tui/tests/fixtures/board_sample.json +0 -0
@@ -153,6 +153,39 @@ jobs:
153
153
  # gated separately through the #2164 CI wrapper.
154
154
  - run: scripts/run_tests_without_gh.sh python -m pytest tests/ -q --ignore=tests/acceptance
155
155
 
156
+ # #2135 (child of epic #1902): "every `gh` argv construction lives inside
157
+ # coord/github_ops.py" is the load-bearing assumption under the #1902
158
+ # forge-portability cost estimate — it's the fact that makes the eventual
159
+ # port a refactor instead of a rewrite. #1483 already guarded direct
160
+ # call-argument leaks with an AST scan (formerly
161
+ # tests/test_no_direct_gh_calls.py), but that walk missed the
162
+ # variable-indirection shape (`cmd = ["gh", ...]; subprocess.run(cmd)`).
163
+ # This job's dedicated regex scan catches that gap too, so
164
+ # test_no_direct_gh_calls.py was retired in its favor rather than kept
165
+ # running alongside it as a second, disagreeing implementation of the
166
+ # same invariant (#2135 review) — see scripts/check_gh_argv_containment.py's
167
+ # module docstring for the full reconciliation.
168
+ #
169
+ # scripts/check_gh_argv_containment.py scans coord/**/*.py for a bare
170
+ # `"gh"`/`'gh'` token outside coord/github_ops.py, with one explicit,
171
+ # commented allowlist entry for coord/prereqs.py's binary-version probe
172
+ # (it checks `gh` is installed; it doesn't drive the forge). See that
173
+ # script's module docstring for the full rationale and
174
+ # tests/test_check_gh_argv_containment.py for the negative-test proof
175
+ # that the guard can actually fail.
176
+ #
177
+ # Stdlib-only (re/pathlib/dataclasses), so no `pip install` needed here —
178
+ # this is meant to be as cheap as `no-gh-on-path` above, a grep-shaped
179
+ # check, not a build step.
180
+ gh-argv-containment:
181
+ runs-on: ubuntu-latest
182
+ steps:
183
+ - uses: actions/checkout@v4
184
+ - uses: actions/setup-python@v5
185
+ with:
186
+ python-version: "3.12"
187
+ - run: python scripts/check_gh_argv_containment.py .
188
+
156
189
  # #2170: run the full suite in the environment of a REAL FLEET MACHINE — a
157
190
  # populated `~/.coord/` (thin-client shaped), no `sqlite3` on PATH, and a
158
191
  # `$TMPDIR` under an ancestor pytest config.
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: code-coordinator
3
- Version: 0.5.195
3
+ Version: 0.5.197
4
4
  Summary: Coordinate Claude Code workers across multiple machines and repos.
5
5
  Author-email: John Donaghy <johnfdonaghy@gmail.com>
6
6
  License-Expression: LicenseRef-FSL-1.1-MIT
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: code-coordinator
3
- Version: 0.5.195
3
+ Version: 0.5.197
4
4
  Summary: Coordinate Claude Code workers across multiple machines and repos.
5
5
  Author-email: John Donaghy <johnfdonaghy@gmail.com>
6
6
  License-Expression: LicenseRef-FSL-1.1-MIT
@@ -309,6 +309,7 @@ docs/mocks/web/pipeline-narrow.html
309
309
  docs/mocks/web/pipeline-wide.html
310
310
  graphify-out/.gitignore
311
311
  scripts/audit_review_verdict_overrides.py
312
+ scripts/check_gh_argv_containment.py
312
313
  scripts/codegen.py
313
314
  scripts/coord-test-runner.sh
314
315
  scripts/drive-batch.sh
@@ -379,6 +380,7 @@ tests/test_branch_model.py
379
380
  tests/test_bug_intake.py
380
381
  tests/test_build_worker_image_env_update.py
381
382
  tests/test_cargo_cache.py
383
+ tests/test_check_gh_argv_containment.py
382
384
  tests/test_ci_acceptance_gate_1950.py
383
385
  tests/test_ci_parity_2091.py
384
386
  tests/test_ci_store.py
@@ -554,7 +556,6 @@ tests/test_needs_attention.py
554
556
  tests/test_network.py
555
557
  tests/test_new_issue_chat.py
556
558
  tests/test_next_release_tag.py
557
- tests/test_no_direct_gh_calls.py
558
559
  tests/test_node_shim.py
559
560
  tests/test_notifier_baseline.py
560
561
  tests/test_notifier_cli.py
@@ -607,6 +608,7 @@ tests/test_refine_chat.py
607
608
  tests/test_release_cordon_2101.py
608
609
  tests/test_release_cordon_daemon_leads_2176.py
609
610
  tests/test_release_cordon_deadlock_2240.py
611
+ tests/test_release_cordon_stuck_2490.py
610
612
  tests/test_release_propagate.py
611
613
  tests/test_release_unified_1242.py
612
614
  tests/test_release_verify.py
@@ -313,6 +313,7 @@
313
313
  "scripts/azure-workers/scrub-and-generalize.sh",
314
314
  "scripts/azure-workers/tailnet-acl.hujson",
315
315
  "scripts/azure-workers/verify-github-token.sh",
316
+ "scripts/check_gh_argv_containment.py",
316
317
  "scripts/codegen.py",
317
318
  "scripts/coord-test-runner.sh",
318
319
  "scripts/drive-batch.sh",
@@ -441,6 +442,7 @@
441
442
  "tests/test_bug_intake.py",
442
443
  "tests/test_build_worker_image_env_update.py",
443
444
  "tests/test_cargo_cache.py",
445
+ "tests/test_check_gh_argv_containment.py",
444
446
  "tests/test_ci_acceptance_gate_1950.py",
445
447
  "tests/test_ci_parity_2091.py",
446
448
  "tests/test_ci_store.py",
@@ -616,7 +618,6 @@
616
618
  "tests/test_network.py",
617
619
  "tests/test_new_issue_chat.py",
618
620
  "tests/test_next_release_tag.py",
619
- "tests/test_no_direct_gh_calls.py",
620
621
  "tests/test_node_shim.py",
621
622
  "tests/test_notifier_baseline.py",
622
623
  "tests/test_notifier_cli.py",
@@ -669,6 +670,7 @@
669
670
  "tests/test_release_cordon_2101.py",
670
671
  "tests/test_release_cordon_daemon_leads_2176.py",
671
672
  "tests/test_release_cordon_deadlock_2240.py",
673
+ "tests/test_release_cordon_stuck_2490.py",
672
674
  "tests/test_release_propagate.py",
673
675
  "tests/test_release_unified_1242.py",
674
676
  "tests/test_release_verify.py",
@@ -1,7 +1,7 @@
1
1
  {
2
- "tag": "0.5.195",
2
+ "tag": "0.5.197",
3
3
  "distance": 0,
4
- "node": "g2bb7d7ad4f498cd537a6acf1e85b0ee9e8573117",
4
+ "node": "gac6cd7be56630a9693710286586d56b6c59bc767",
5
5
  "dirty": false,
6
6
  "branch": "HEAD",
7
7
  "node_date": "2026-08-21"
@@ -1354,6 +1354,7 @@ def _apply_cordons( # noqa: PLR0912 — one linear apply-the-plan pass
1354
1354
  outcome.cooling_seconds = plan.cooling_seconds
1355
1355
  outcome.collateral_spared = list(plan.collateral_spared)
1356
1356
  outcome.blocked_behind = plan.blocked_behind
1357
+ outcome.stuck_in_cooldown = list(plan.stuck_in_cooldown)
1357
1358
  if plan.released is not None:
1358
1359
  outcome.released = plan.released.to_dict()
1359
1360
  # stderr as well as stdout: on the timer host this line IS the
@@ -2148,8 +2149,18 @@ def release_cordon(
2148
2149
  )
2149
2150
  )
2150
2151
  return
2152
+ # #2490: hosts the newest propagate run flagged as behind, idle, and
2153
+ # left uncordoned only because the #2240 cooldown is suppressing new
2154
+ # cordons. These are exactly the machines an operator would otherwise
2155
+ # have to notice by hand (`coord status` showing `online • idle` on a
2156
+ # host that's actually stuck on an old version) — surface them even when
2157
+ # `active` is empty, since a stuck host is by definition NOT cordoned.
2158
+ stuck_hosts, stuck_target = _stuck_hosts_from_journal()
2151
2159
  if not active:
2152
- click.echo("no machines are cordoned — the fleet is free to take work")
2160
+ if stuck_hosts:
2161
+ _echo_stuck_hosts(stuck_hosts, stuck_target)
2162
+ else:
2163
+ click.echo("no machines are cordoned — the fleet is free to take work")
2153
2164
  return
2154
2165
  for name, record in sorted(active.items()):
2155
2166
  remaining = max(0.0, record.expires_at - now) / 60.0
@@ -2180,6 +2191,8 @@ def release_cordon(
2180
2191
  f"`coord release propagate` releases it by itself after "
2181
2192
  f"{rc.DEFAULT_MAX_DEFERRALS}."
2182
2193
  )
2194
+ if stuck_hosts:
2195
+ _echo_stuck_hosts(stuck_hosts, stuck_target)
2183
2196
  click.echo(
2184
2197
  f"\nclear one with `coord release cordon --clear <machine>` "
2185
2198
  f"(default lifetime {rc.DEFAULT_TTL_SECONDS / 60:.0f}m — a cordon "
@@ -2197,6 +2210,59 @@ def _read_propagation_records() -> list[dict]:
2197
2210
  return []
2198
2211
 
2199
2212
 
2213
+ def _stuck_hosts_from_journal() -> tuple[list[str], str | None]:
2214
+ """Hosts the NEWEST propagate run flagged as stuck-in-cooldown (#2490).
2215
+
2216
+ ``CordonPlan.stuck_in_cooldown`` (mirrored onto ``CordonOutcome`` and
2217
+ journalled under a run's ``cordons`` key) names behind, idle hosts a run
2218
+ left uncordoned only because the #2240 deadlock-release cooldown is
2219
+ still active — the gap the issue is about: nothing gave such a host a
2220
+ signal or a path back to rolling for up to the cooldown's full length.
2221
+
2222
+ Only the single newest record counts, deliberately: this is a
2223
+ point-in-time reading ("as of the last tick"), and a host named in an
2224
+ older record may since have gone busy, rolled, or had its cooldown
2225
+ lift — reporting it from a stale record would be a false alarm, which is
2226
+ exactly the kind of noise this fleet already has too much of. No
2227
+ journal (a thin client, or a host that has never run propagate)
2228
+ degrades to nothing rather than raising — mirrors every other reader of
2229
+ this journal in this module.
2230
+ """
2231
+ try:
2232
+ records = _read_propagation_records()
2233
+ except Exception: # noqa: BLE001 — never load-bearing
2234
+ return [], None
2235
+ if not records:
2236
+ return [], None
2237
+ newest = records[-1]
2238
+ if not isinstance(newest, dict):
2239
+ return [], None
2240
+ cordons = newest.get("cordons")
2241
+ if not isinstance(cordons, dict):
2242
+ return [], None
2243
+ stuck = cordons.get("stuck_in_cooldown") or []
2244
+ if not isinstance(stuck, list):
2245
+ return [], None
2246
+ target = newest.get("target_version")
2247
+ return [str(h) for h in stuck], (str(target) if target else None)
2248
+
2249
+
2250
+ def _echo_stuck_hosts(stuck_hosts: list[str], stuck_target: str | None) -> None:
2251
+ """The #2490 notice both branches of ``release_cordon`` share.
2252
+
2253
+ One line per host, each naming its own override command — the format
2254
+ the issue itself asks for: "precision: 18m behind v0.5.192, idle, cordon
2255
+ suppressed by cooldown (#2240) — consider `coord agent update --machine
2256
+ precision`."
2257
+ """
2258
+ version = f"v{stuck_target}" if stuck_target else "the release"
2259
+ click.echo(f"\n! STUCK (#2490): behind {version}, idle, cordon suppressed "
2260
+ "by the #2240 deadlock-release cooldown — no automatic path "
2261
+ "back to rolling until it lifts on its own:")
2262
+ for host in sorted(stuck_hosts):
2263
+ click.echo(f" ! {host}: consider `coord agent update --machine {host}`")
2264
+
2265
+
2200
2266
  @release_group.command(
2201
2267
  "rollback",
2202
2268
  help=(
@@ -55,6 +55,30 @@ def _cordon_stall_suffix(cordons: dict) -> str:
55
55
  return f" ({described})" if described else ""
56
56
 
57
57
 
58
+ def _stuck_in_cooldown_hosts() -> dict[str, str | None]:
59
+ """Machine name -> target version, for hosts stuck-in-cooldown (#2490).
60
+
61
+ Thin wrapper around :func:`coord.commands.release._stuck_hosts_from_journal`
62
+ — same journal, same "newest record only" reading, reused rather than
63
+ reimplemented. A host in this dict is behind the target version, was
64
+ idle as of the last `coord release propagate` tick, and is NOT cordoned
65
+ (the #2240 cooldown is suppressing it) — which is exactly why it shows
66
+ up everywhere else in this command as a flatly ordinary `online • idle`.
67
+ That silence is the whole finding of #2490: a human noticed only because
68
+ they happened to be watching `coord status` themselves.
69
+
70
+ Degrades to ``{}`` on any error (no journal, an unreadable one, a thin
71
+ client) — never load-bearing, same contract as `_cordon_stall_suffix`.
72
+ """
73
+ from coord.commands.release import _stuck_hosts_from_journal # noqa: PLC0415
74
+
75
+ try:
76
+ hosts, target = _stuck_hosts_from_journal()
77
+ except Exception: # noqa: BLE001 — a status render must never fail on this
78
+ return {}
79
+ return {h: target for h in hosts}
80
+
81
+
58
82
  def _live_advisory_entries(
59
83
  entries: list[dict],
60
84
  cfg: "Config",
@@ -187,6 +211,9 @@ def status(config_path: Path, machine_filter: str | None, no_reconcile: bool, ti
187
211
  # same, which is why the 70-minute stall was invisible.
188
212
  cordon_stall = _cordon_stall_suffix(cordons)
189
213
  quiet_windows = effective_quiet_hours(cfg.machines)
214
+ # #2490: hosts the last propagate run flagged as behind + idle + stuck
215
+ # behind an active #2240 cooldown — see `_stuck_in_cooldown_hosts`.
216
+ stuck_in_cooldown = _stuck_in_cooldown_hosts()
190
217
 
191
218
  statuses = check_all(machines, timeout=timeout)
192
219
  agent_completed: dict[str, dict] = {}
@@ -314,6 +341,22 @@ def status(config_path: Path, machine_filter: str | None, no_reconcile: bool, ti
314
341
  for repo_name, reason in degraded.items():
315
342
  click.echo(f" ⚠ degraded: {repo_name} — {reason}")
316
343
 
344
+ # #2490: this host is behind the release, was idle last tick, and
345
+ # nothing is cordoning it because a #2240 deadlock-release cooldown
346
+ # is suppressing all new cordons fleet-wide. Without this line the
347
+ # machine above reads as a plain `online • idle` — indistinguishable
348
+ # from a machine with nothing to do, which is exactly how the
349
+ # 2026-08-20 incident went unnoticed for the length of the cooldown.
350
+ if m.name in stuck_in_cooldown:
351
+ stuck_target = stuck_in_cooldown[m.name]
352
+ stuck_version = f"v{stuck_target}" if stuck_target else "the release"
353
+ click.echo(
354
+ f" ⚠ STUCK: behind {stuck_version} and idle, but cordoning "
355
+ "is suppressed by an active #2240 deadlock-release cooldown "
356
+ "(#2490) — no automatic path back to rolling until it lifts; "
357
+ f"consider `coord agent update --machine {m.name}`"
358
+ )
359
+
317
360
  if status_result and status_result.ok and status_result.data:
318
361
  for entry in status_result.data.get("active", []):
319
362
  progress = entry.get("progress")
@@ -658,6 +658,17 @@ class CordonPlan:
658
658
  #: exactly when `collateral_spared` is non-empty. The single fact that
659
659
  #: would have turned a 40-minute puzzle into one line of output.
660
660
  blocked_behind: str | None = None
661
+ #: #2490: hosts that are BEHIND *target_version*, have no busy signal of
662
+ #: their own this run (idle), and are not being cordoned only because an
663
+ #: unexpired deadlock-release cooldown is suppressing all new cordons —
664
+ #: set exactly when ``cooling_seconds > 0``. This is the gap the issue
665
+ #: names: a host in this state has no automatic path back to rolling for
666
+ #: up to the cooldown's full length, and nothing surfaced that it was
667
+ #: sitting there idle, behind, and unflagged. Reported separately from
668
+ #: ``collateral_spared`` (blocked behind a busy daemon host — a different
669
+ #: reason a behind host stays uncordoned) so each surface can name the
670
+ #: actual cause instead of collapsing both into "not cordoned".
671
+ stuck_in_cooldown: tuple[str, ...] = ()
661
672
 
662
673
  @property
663
674
  def empty(self) -> bool:
@@ -668,6 +679,7 @@ class CordonPlan:
668
679
  or self.expired
669
680
  or self.released
670
681
  or self.collateral_spared
682
+ or self.stuck_in_cooldown
671
683
  )
672
684
 
673
685
  def to_dict(self) -> dict:
@@ -681,6 +693,7 @@ class CordonPlan:
681
693
  "cooling_seconds": self.cooling_seconds,
682
694
  "collateral_spared": list(self.collateral_spared),
683
695
  "blocked_behind": self.blocked_behind,
696
+ "stuck_in_cooldown": list(self.stuck_in_cooldown),
684
697
  }
685
698
 
686
699
  def render(self) -> list[str]:
@@ -718,6 +731,13 @@ class CordonPlan:
718
731
  "release (#2240) is still letting the fleet work; nothing was "
719
732
  "cordoned this run"
720
733
  )
734
+ for host in self.stuck_in_cooldown:
735
+ lines.append(
736
+ f" ! STUCK: {host} is behind and idle, but cordoning is "
737
+ "suppressed by the deadlock-release cooldown above (#2490) — "
738
+ f"it has no automatic path back to rolling until the cooldown "
739
+ f"lifts. Consider `coord agent update --machine {host}`."
740
+ )
721
741
  for esc in self.escalations:
722
742
  lines.append(f" ! {esc.message}")
723
743
  return lines
@@ -880,6 +900,21 @@ def plan_cordons(
880
900
  pressure = pressure or DeferralPressure()
881
901
  cooling = pressure.cooling_for(now, release_cooldown)
882
902
  if cooling > 0:
903
+ # #2490: a behind host with no busy signal of its own has nothing
904
+ # left holding it back except this cooldown — it is idle, it is
905
+ # behind, and it will sit exactly like that until the cooldown
906
+ # lifts (up to `release_cooldown` seconds) with no cordon and,
907
+ # before this, no signal anywhere that it needs attention.
908
+ # `collateral` hosts are excluded: those are uncordoned for an
909
+ # unrelated reason (blocked behind a busy daemon host) that already
910
+ # has its own name (`collateral_spared`/`blocked_behind`).
911
+ stuck = tuple(
912
+ sorted(
913
+ host
914
+ for host in (drift.behind - collateral)
915
+ if not (busy_reasons or {}).get(host)
916
+ )
917
+ )
883
918
  return CordonPlan(
884
919
  uncordon=to_uncordon,
885
920
  expired=expired,
@@ -887,6 +922,7 @@ def plan_cordons(
887
922
  unknown=tuple(sorted(drift.undecided & set(live))),
888
923
  collateral_spared=tuple(sorted(collateral)),
889
924
  blocked_behind=blocked_behind,
925
+ stuck_in_cooldown=stuck,
890
926
  )
891
927
  if max_deferrals > 0 and pressure.consecutive >= max_deferrals:
892
928
  return CordonPlan(
@@ -984,6 +1020,12 @@ class CordonOutcome:
984
1020
  #: #2176: the daemon host `collateral_spared` was spared on account of.
985
1021
  #: Mirrors `CordonPlan.blocked_behind`.
986
1022
  blocked_behind: str | None = None
1023
+ #: #2490: mirrors `CordonPlan.stuck_in_cooldown` — behind, idle hosts this
1024
+ #: run left uncordoned only because the #2240 deadlock cooldown is still
1025
+ #: active. Journalled (not just printed) so a read-only surface like
1026
+ #: `coord status` can flag them without recomputing `plan_cordons` itself
1027
+ #: — see `coord.commands.status._stuck_in_cooldown_hosts`.
1028
+ stuck_in_cooldown: list[str] = field(default_factory=list)
987
1029
 
988
1030
  def to_dict(self) -> dict:
989
1031
  return {
@@ -999,4 +1041,5 @@ class CordonOutcome:
999
1041
  "max_deferrals": self.max_deferrals,
1000
1042
  "collateral_spared": list(self.collateral_spared),
1001
1043
  "blocked_behind": self.blocked_behind,
1044
+ "stuck_in_cooldown": list(self.stuck_in_cooldown),
1002
1045
  }
@@ -1294,6 +1294,14 @@ def render_record(record: PropagationRecord | Mapping[str, Any]) -> list[str]:
1294
1294
  " cordons held off (post-release cooldown, #2240): "
1295
1295
  f"{float(cordons['cooling_seconds']) / 60.0:.0f}m left"
1296
1296
  )
1297
+ # #2490: name the hosts that were behind and idle but left uncordoned
1298
+ # purely because of the cooldown above — the gap that let `precision`
1299
+ # sit stuck for 30 minutes with no automatic path back to rolling.
1300
+ if cordons.get("stuck_in_cooldown"):
1301
+ lines.append(
1302
+ " ! STUCK (idle, behind, cooldown-suppressed, #2490): "
1303
+ + ", ".join(cordons["stuck_in_cooldown"])
1304
+ )
1297
1305
  for esc in cordons.get("escalated") or []:
1298
1306
  lines.append(f" ! {esc.get('message') or esc}")
1299
1307
  for err in cordons.get("errors") or []:
@@ -0,0 +1,176 @@
1
+ #!/usr/bin/env python3
2
+ """check_gh_argv_containment.py -- CI guard for #2135 (child of epic #1902).
3
+
4
+ The epic's headline finding (#1902) is that **every `["gh", ...]` argv
5
+ construction in this repo already lives inside `coord/github_ops.py`** --
6
+ that single fact is what makes the eventual forge-portability port a
7
+ *refactor* instead of a rewrite, and it is the load-bearing assumption
8
+ under the whole #1902 cost estimate. Until this script, that invariant was
9
+ protected by nothing but convention: whoever last thought to grep for it.
10
+
11
+ Same spirit as `scripts/run_tests_without_gh.sh` (#1484, the `no-gh-on-path`
12
+ CI job) -- that script proved `gh` calls are *mockable* by making the
13
+ binary unresolvable and watching the suite still pass; this script proves
14
+ they are *contained* by refusing any `gh` argv construction that lives
15
+ outside the one file that owns them. Deliberately kept a plain regex scan,
16
+ not an AST walk -- cheap enough to run on every PR, and the invariant it
17
+ guards ("does this file spell the literal string `gh` as its own quoted
18
+ token") does not need a parser to detect.
19
+
20
+ Supersedes `tests/test_no_direct_gh_calls.py` (#1483's original AST-based
21
+ guard for this same invariant, added when only `github_ops.py`'s
22
+ call-site shape needed catching). #2135 review flagged that the two
23
+ guards were an undocumented split-brain: the AST walk only fires when a
24
+ `["gh", ...]` literal is a *direct call argument*
25
+ (`subprocess.run(["gh", ...])`), so it silently missed the
26
+ variable-indirection shape (`cmd = ["gh", ...]; subprocess.run(cmd)`) that
27
+ this regex scan does catch, since it matches the token wherever it sits on
28
+ the line. Rather than keep two independently-maintained implementations of
29
+ one invariant with two different blind spots, `test_no_direct_gh_calls.py`
30
+ was deleted and this script is now the single implementation, exercised
31
+ both by the dedicated `gh-argv-containment` CI job (`.github/workflows/
32
+ test.yml`) and by the ordinary `pytest tests/` run, via
33
+ `tests/test_check_gh_argv_containment.py::test_real_tree_is_clean` and
34
+ friends -- one scan, reachable both ways, per the repo's "one question,
35
+ one answer" rule (epic #2096). The trade-off this leaves: being a plain
36
+ token scan rather than an AST walk, it can false-positive on a `"gh"`
37
+ token that isn't argv (e.g. inside a docstring or an unrelated string
38
+ literal) -- accepted deliberately, since a false positive costs an
39
+ allowlist entry or a reword, while a false negative (the AST gap above)
40
+ costs a silent regression of the epic's #1902 load-bearing assumption.
41
+
42
+ Usage:
43
+ python scripts/check_gh_argv_containment.py [repo-root]
44
+
45
+ Exit codes: 0 if the tree is clean, 1 if a `gh` argv construction is found
46
+ in coord/**/*.py outside coord/github_ops.py.
47
+ """
48
+
49
+ from __future__ import annotations
50
+
51
+ import re
52
+ import sys
53
+ from dataclasses import dataclass
54
+ from pathlib import Path
55
+
56
+ SEAM = "coord/github_ops.py"
57
+
58
+ # Matches a bare `"gh"` or `'gh'` token -- the exact spelling every gh argv
59
+ # construction in this repo starts with, whether written `["gh", ...]`,
60
+ # `("gh", ...)`, or (as in github_ops.py's PR-checks call, where the list is
61
+ # opened on the previous line) as a bare leading element `"gh", "pr", ...,`.
62
+ # The closing quote must land immediately after the 'h', so this does not
63
+ # match longer identifiers that merely contain "gh", like "github" or
64
+ # "ghost".
65
+ _GH_TOKEN_RE = re.compile(r"""(["'])gh\1""")
66
+
67
+ # Explicit allowlist: (file, substring-of-the-matched-line) pairs for
68
+ # known-legitimate `gh` mentions outside the seam. Keyed on line CONTENT,
69
+ # not a line number -- numbers drift as a file changes (this very entry's
70
+ # line moved from prereqs.py:288, where #2135 was filed, to prereqs.py:290
71
+ # by the time this script was written), and a number-keyed allowlist would
72
+ # either miss a real leak that later lands on that number, or stop
73
+ # exempting the intended line the moment it shifts.
74
+ #
75
+ # Add an entry here ONLY with a comment explaining why the mention is not
76
+ # an argv construction -- a loose pattern (e.g. "any line in prereqs.py")
77
+ # would let a real leak through under cover of the exemption, which is
78
+ # exactly the failure mode this script exists to prevent.
79
+ _ALLOWLIST: tuple[tuple[str, str], ...] = (
80
+ (
81
+ "coord/prereqs.py",
82
+ 'tool="gh", binary="gh"',
83
+ ),
84
+ # ^ Prereq(tool="gh", binary="gh", version_args=("--version",), ...)
85
+ # probes for the `gh` BINARY's presence/version via shutil.which +
86
+ # `gh --version` -- it does not drive the forge, so it correctly lives
87
+ # outside the seam (#2135).
88
+ )
89
+
90
+
91
+ @dataclass(frozen=True)
92
+ class Violation:
93
+ path: str
94
+ lineno: int
95
+ line: str
96
+
97
+
98
+ def _is_allowlisted(rel_path: str, line: str) -> bool:
99
+ return any(
100
+ rel_path == allow_path and allow_substr in line
101
+ for allow_path, allow_substr in _ALLOWLIST
102
+ )
103
+
104
+
105
+ def find_violations(repo_root: Path) -> list[Violation]:
106
+ """Scan coord/**/*.py for `gh` argv construction outside the seam.
107
+
108
+ Pure function of the filesystem under ``repo_root`` -- no subprocess,
109
+ no network -- so it is cheap to point at a synthetic fixture tree in
110
+ tests, not just the real repo.
111
+ """
112
+ violations: list[Violation] = []
113
+ coord_dir = repo_root / "coord"
114
+ if not coord_dir.is_dir():
115
+ return violations
116
+ for path in sorted(coord_dir.rglob("*.py")):
117
+ rel = path.relative_to(repo_root).as_posix()
118
+ if rel == SEAM:
119
+ continue
120
+ try:
121
+ text = path.read_text(encoding="utf-8")
122
+ except (UnicodeDecodeError, OSError) as exc:
123
+ # Every file under coord/ is expected to be UTF-8 Python
124
+ # source, so this should never actually fire -- but if it
125
+ # ever does, skipping silently would mean a real `gh` leak in
126
+ # that file goes undetected with no trace. Surface it on
127
+ # stderr rather than swallow it (#2135 review).
128
+ print(
129
+ f"check_gh_argv_containment: skipping {rel} "
130
+ f"(unreadable: {exc}) -- unable to scan for `gh` argv "
131
+ f"construction in this file",
132
+ file=sys.stderr,
133
+ )
134
+ continue
135
+ for lineno, line in enumerate(text.splitlines(), start=1):
136
+ if _GH_TOKEN_RE.search(line) and not _is_allowlisted(rel, line):
137
+ violations.append(Violation(rel, lineno, line.strip()))
138
+ return violations
139
+
140
+
141
+ def format_report(violations: list[Violation]) -> str:
142
+ lines = [
143
+ f"check_gh_argv_containment: found `gh` argv construction outside "
144
+ f"{SEAM}:",
145
+ "",
146
+ ]
147
+ for v in violations:
148
+ lines.append(f" {v.path}:{v.lineno}: {v.line}")
149
+ lines += [
150
+ "",
151
+ "Every `gh` invocation must go through coord/github_ops.py -- that "
152
+ "chokepoint is the load-bearing assumption behind the #1902 "
153
+ "forge-portability epic (it's what makes the eventual port a "
154
+ "refactor instead of a rewrite), and it's what makes `gh` mockable "
155
+ "for tests (the no-gh-on-path CI job, #1484, depends on it too).",
156
+ "",
157
+ 'Fix: move this call into coord/github_ops.py. If it is a genuine '
158
+ 'non-forge use of the literal string "gh" (like the binary-version '
159
+ "probe in coord/prereqs.py), add it to the ALLOWLIST in "
160
+ "scripts/check_gh_argv_containment.py with a comment explaining "
161
+ "why -- see #2135.",
162
+ ]
163
+ return "\n".join(lines)
164
+
165
+
166
+ def main(argv: list[str]) -> int:
167
+ repo_root = Path(argv[1]) if len(argv) > 1 else Path(".")
168
+ violations = find_violations(repo_root.resolve())
169
+ if not violations:
170
+ return 0
171
+ print(format_report(violations), file=sys.stderr)
172
+ return 1
173
+
174
+
175
+ if __name__ == "__main__":
176
+ sys.exit(main(sys.argv))