agentwire-dev 1.63.0__tar.gz → 1.64.0__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 (503) hide show
  1. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/PKG-INFO +1 -1
  2. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/__init__.py +1 -1
  3. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/config.py +10 -2
  4. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/doctor_cli.py +78 -0
  5. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/hooks/damage-control/bash-tool-damage-control.py +3 -2
  6. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/hooks/damage-control/edit-tool-damage-control.py +3 -2
  7. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/hooks/damage-control/mcp-tool-damage-control.py +3 -2
  8. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/hooks/damage-control/read-tool-damage-control.py +3 -2
  9. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/hooks/damage-control/write-tool-damage-control.py +3 -2
  10. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/safety/_core.py +3 -2
  11. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/scheduler/gates.py +29 -6
  12. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/scheduler/models.py +1 -0
  13. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/scheduler/report.py +2 -0
  14. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/scheduler/state.py +3 -0
  15. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/scheduler_cli.py +8 -2
  16. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/css/desktop.css +124 -27
  17. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/session-hud-controller.js +122 -10
  18. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/session-hud.js +149 -20
  19. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/sidebar/scheduler-section.js +6 -1
  20. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/topology-render.js +105 -13
  21. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/worktree.py +16 -5
  22. agentwire_dev-1.64.0/docs/design/session-card-fields.md +99 -0
  23. agentwire_dev-1.64.0/docs/design/session-card-recommendation.md +177 -0
  24. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/docs/wiki/architecture.md +10 -7
  25. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/docs/wiki/communication/channels.md +3 -2
  26. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/docs/wiki/communication/handoff.md +2 -2
  27. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/docs/wiki/concepts.md +3 -1
  28. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/docs/wiki/deployment/remote-access.md +5 -0
  29. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/docs/wiki/deployment/remote-machines.md +36 -31
  30. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/docs/wiki/glossary.md +6 -6
  31. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/docs/wiki/integrations/gws-google-workspace-cli.md +1 -1
  32. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/docs/wiki/internals/damage-control.md +29 -11
  33. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/docs/wiki/internals/portal.md +4 -2
  34. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/docs/wiki/internals/session-topology.md +1 -1
  35. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/docs/wiki/internals/shell-escaping.md +2 -2
  36. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/docs/wiki/internals/troubleshooting.md +2 -12
  37. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/docs/wiki/internals/window-collage.md +1 -1
  38. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/docs/wiki/research/orchestration-transport-alternatives.md +1 -1
  39. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/docs/wiki/scheduling/scheduled-workloads.md +4 -4
  40. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/docs/wiki/security/damage-control-hardening.md +7 -4
  41. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/docs/wiki/security/remote-access-hardening.md +30 -27
  42. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/docs/wiki/security/secrets.md +4 -5
  43. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/docs/wiki/sessions/claude-code-auto-mode.md +3 -7
  44. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/docs/wiki/sessions/prompt-routing.md +0 -1
  45. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/docs/wiki/voice/shim-contract.md +2 -2
  46. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/docs/wiki/voice/stt-self-hosted.md +28 -18
  47. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/integration/test_scheduler_board.py +22 -0
  48. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_damage_control_hooks.py +29 -12
  49. agentwire_dev-1.64.0/tests/unit/test_doctor_scheduler_staleness.py +109 -0
  50. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_scheduler.py +83 -0
  51. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_worktree.py +27 -0
  52. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/.agentwire.yml.example +0 -0
  53. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/.claude/commands/handoff.md +0 -0
  54. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/.claude/skills/wiki/SKILL.md +0 -0
  55. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/.github/FUNDING.yml +0 -0
  56. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/.github/ISSUE_TEMPLATE/bug_report.md +0 -0
  57. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/.github/ISSUE_TEMPLATE/feature_request.md +0 -0
  58. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/.github/ISSUE_TEMPLATE/question.md +0 -0
  59. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/.github/PULL_REQUEST_TEMPLATE.md +0 -0
  60. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/.github/workflows/pytest.yml +0 -0
  61. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/.github/workflows/ruff.yml +0 -0
  62. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/.github/workflows/security.yml +0 -0
  63. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/.github/workflows/tts-smoke.yml +0 -0
  64. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/.gitignore +0 -0
  65. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/AGENTS.md +0 -0
  66. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/CODE_OF_CONDUCT.md +0 -0
  67. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/CONTRIBUTING.md +0 -0
  68. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/Dockerfile.local +0 -0
  69. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/LICENSE +0 -0
  70. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/README.md +0 -0
  71. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/RELEASING.md +0 -0
  72. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/SECURITY.md +0 -0
  73. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/SPONSORS.md +0 -0
  74. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/__main__.py +0 -0
  75. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/agents/__init__.py +0 -0
  76. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/agents/base.py +0 -0
  77. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/agents/tmux.py +0 -0
  78. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/cached_status.py +0 -0
  79. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/channels/__init__.py +0 -0
  80. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/channels/base.py +0 -0
  81. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/channels/email.py +0 -0
  82. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/channels/push.py +0 -0
  83. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/channels/quo.py +0 -0
  84. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/channels_cli.py +0 -0
  85. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/chrome_tabs.py +0 -0
  86. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/completion.py +0 -0
  87. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/config_cli.py +0 -0
  88. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/core.py +0 -0
  89. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/council/__init__.py +0 -0
  90. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/council/cli.py +0 -0
  91. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/council/inbox.py +0 -0
  92. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/council/minutes.py +0 -0
  93. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/council/state.py +0 -0
  94. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/council/view.py +0 -0
  95. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/devices.py +0 -0
  96. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/diff_cli.py +0 -0
  97. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/doctor_voice.py +0 -0
  98. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/ensure_cli.py +0 -0
  99. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/fetch.py +0 -0
  100. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/handoff/__init__.py +0 -0
  101. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/handoff/git_state.py +0 -0
  102. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/handoff/instructions.py +0 -0
  103. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/handoff/parser.py +0 -0
  104. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/handoff/renderer.py +0 -0
  105. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/handoff/schema.py +0 -0
  106. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/handoff_cli.py +0 -0
  107. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/history.py +0 -0
  108. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/history_cli.py +0 -0
  109. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/hooks/__init__.py +0 -0
  110. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/hooks/agentwire-permission.sh +0 -0
  111. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/hooks/damage-control/__init__.py +0 -0
  112. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/hooks/damage-control/audit_logger.py +0 -0
  113. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/hooks/damage-control/rules/agentwire.yaml +0 -0
  114. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/hooks/damage-control/rules/aws.yaml +0 -0
  115. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/hooks/damage-control/rules/cloud-hosting.yaml +0 -0
  116. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/hooks/damage-control/rules/containers.yaml +0 -0
  117. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/hooks/damage-control/rules/control-plane.yaml +0 -0
  118. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/hooks/damage-control/rules/core.yaml +0 -0
  119. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/hooks/damage-control/rules/databases.yaml +0 -0
  120. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/hooks/damage-control/rules/firebase.yaml +0 -0
  121. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/hooks/damage-control/rules/gcp.yaml +0 -0
  122. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/hooks/damage-control/rules/git.yaml +0 -0
  123. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/hooks/damage-control/rules/gws.yaml +0 -0
  124. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/hooks/damage-control/rules/infrastructure.yaml +0 -0
  125. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/hooks/damage-control/rules/outbound.yaml +0 -0
  126. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/hooks/damage-control/rules/publish.yaml +0 -0
  127. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/hooks/damage-control/rules/remote.yaml +0 -0
  128. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/hooks/idle-handler.sh +0 -0
  129. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/hooks/queue-processor.sh +0 -0
  130. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/hooks_cli.py +0 -0
  131. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/inbox.py +0 -0
  132. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/limits_cli.py +0 -0
  133. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/listen.py +0 -0
  134. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/locking.py +0 -0
  135. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/machine_cli.py +0 -0
  136. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/mcp_channels.py +0 -0
  137. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/mcp_chrome.py +0 -0
  138. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/mcp_cli.py +0 -0
  139. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/mcp_core.py +0 -0
  140. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/mcp_council.py +0 -0
  141. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/mcp_desktop.py +0 -0
  142. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/mcp_handoff.py +0 -0
  143. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/mcp_history.py +0 -0
  144. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/mcp_listen.py +0 -0
  145. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/mcp_lock.py +0 -0
  146. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/mcp_machine.py +0 -0
  147. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/mcp_msg.py +0 -0
  148. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/mcp_notify.py +0 -0
  149. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/mcp_pane.py +0 -0
  150. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/mcp_projects.py +0 -0
  151. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/mcp_scheduler.py +0 -0
  152. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/mcp_scratchpad.py +0 -0
  153. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/mcp_server.py +0 -0
  154. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/mcp_services.py +0 -0
  155. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/mcp_session.py +0 -0
  156. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/mcp_status.py +0 -0
  157. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/mcp_task.py +0 -0
  158. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/mcp_tunnels.py +0 -0
  159. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/mcp_voice.py +0 -0
  160. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/mcp_wiki.py +0 -0
  161. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/mcp_worktree.py +0 -0
  162. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/msg_cli.py +0 -0
  163. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/network.py +0 -0
  164. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/notify_cli.py +0 -0
  165. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/onboarding.py +0 -0
  166. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/palette_cli.py +0 -0
  167. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/pane_cli.py +0 -0
  168. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/pane_manager.py +0 -0
  169. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/portal_cli.py +0 -0
  170. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/project_config.py +0 -0
  171. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/projects.py +0 -0
  172. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/prompt_router.py +0 -0
  173. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/prompts_cli.py +0 -0
  174. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/push_cli.py +0 -0
  175. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/push_store.py +0 -0
  176. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/repo_cli.py +0 -0
  177. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/research.py +0 -0
  178. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/roles/__init__.py +0 -0
  179. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/roles/agentwire.md +0 -0
  180. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/roles/anchor.md +0 -0
  181. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/roles/chatbot.md +0 -0
  182. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/roles/contributor.md +0 -0
  183. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/roles/correspondent.md +0 -0
  184. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/roles/council-brain.md +0 -0
  185. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/roles/council-conscience.md +0 -0
  186. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/roles/council-critic.md +0 -0
  187. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/roles/council-devils-advocate.md +0 -0
  188. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/roles/council-gut.md +0 -0
  189. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/roles/council-historian.md +0 -0
  190. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/roles/council-member.md +0 -0
  191. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/roles/council-orchestrator.md +0 -0
  192. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/roles/init.md +0 -0
  193. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/roles/notifications.md +0 -0
  194. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/roles/orchestrator.md +0 -0
  195. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/roles/soul.md +0 -0
  196. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/roles/task-runner.md +0 -0
  197. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/roles/voice.md +0 -0
  198. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/roles/worker-worktree.md +0 -0
  199. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/roles/worker.md +0 -0
  200. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/roles_cli.py +0 -0
  201. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/routes/__init__.py +0 -0
  202. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/routes/artifacts.py +0 -0
  203. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/routes/config.py +0 -0
  204. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/routes/council.py +0 -0
  205. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/routes/desktop.py +0 -0
  206. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/routes/history.py +0 -0
  207. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/routes/machines.py +0 -0
  208. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/routes/notify.py +0 -0
  209. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/routes/palette.py +0 -0
  210. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/routes/permission.py +0 -0
  211. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/routes/projects.py +0 -0
  212. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/routes/push.py +0 -0
  213. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/routes/safety.py +0 -0
  214. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/routes/scheduler.py +0 -0
  215. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/routes/scratchpad.py +0 -0
  216. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/routes/sessions.py +0 -0
  217. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/routes/sessions_admin.py +0 -0
  218. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/routes/voice.py +0 -0
  219. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/safety/__init__.py +0 -0
  220. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/safety_cli.py +0 -0
  221. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/safety_commands.py +0 -0
  222. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/scheduler/__init__.py +0 -0
  223. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/scheduler/dispatch.py +0 -0
  224. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/scheduler/loop.py +0 -0
  225. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/scheduler/schedule.py +0 -0
  226. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/scheduler/zombie.py +0 -0
  227. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/scratchpad.py +0 -0
  228. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/security.py +0 -0
  229. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/send_cli.py +0 -0
  230. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/server.py +0 -0
  231. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/services.py +0 -0
  232. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/session_cli.py +0 -0
  233. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/session_context.py +0 -0
  234. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/session_ready.py +0 -0
  235. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/ssh.py +0 -0
  236. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/agentwire-splash-logo-layers--agentwire-text.png +0 -0
  237. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/agentwire-splash-logo-layers--echo-claw-fg.png +0 -0
  238. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/agentwire-splash-logo-layers--echo.png +0 -0
  239. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/agentwire-splash-logo-layers--telephone.png +0 -0
  240. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/agentwire-splash-logo-layers--tree.png +0 -0
  241. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/announcements.json +0 -0
  242. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/apple-touch-icon.png +0 -0
  243. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/css/mobile.css +0 -0
  244. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/favicon-32.png +0 -0
  245. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/favicon-64.png +0 -0
  246. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/icons/sessions/bear.webp +0 -0
  247. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/icons/sessions/cat.webp +0 -0
  248. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/icons/sessions/crown.webp +0 -0
  249. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/icons/sessions/custom/agentwire-portal.webp +0 -0
  250. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/icons/sessions/custom/agentwire-tts.webp +0 -0
  251. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/icons/sessions/custom/agentwire.webp +0 -0
  252. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/icons/sessions/deer.webp +0 -0
  253. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/icons/sessions/drone.webp +0 -0
  254. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/icons/sessions/eagle.webp +0 -0
  255. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/icons/sessions/fox.webp +0 -0
  256. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/icons/sessions/hawk.webp +0 -0
  257. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/icons/sessions/horse.webp +0 -0
  258. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/icons/sessions/lion.webp +0 -0
  259. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/icons/sessions/rabbit.webp +0 -0
  260. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/icons/sessions/robot.webp +0 -0
  261. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/icons/sessions/tiger.webp +0 -0
  262. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/icons/sessions/wolf.webp +0 -0
  263. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/img/icon-192.png +0 -0
  264. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/img/icon-512.png +0 -0
  265. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/.gitkeep +0 -0
  266. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/announcement-modal.js +0 -0
  267. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/api.js +0 -0
  268. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/artifact-window.js +0 -0
  269. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/card-terminal.js +0 -0
  270. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/collage.js +0 -0
  271. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/command-palette.js +0 -0
  272. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/council-window.js +0 -0
  273. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/dead-key-suppressor.js +0 -0
  274. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/desktop-manager.js +0 -0
  275. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/desktop.js +0 -0
  276. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/help-modal.js +0 -0
  277. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/icon-manager.js +0 -0
  278. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/lineage.js +0 -0
  279. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/mobile.js +0 -0
  280. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/notification-prefs.js +0 -0
  281. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/notifications-panel.js +0 -0
  282. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/ptt.js +0 -0
  283. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/push-client.js +0 -0
  284. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/review-window.js +0 -0
  285. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/safety-shared.js +0 -0
  286. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/safety-window.js +0 -0
  287. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/scratchpad.js +0 -0
  288. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/service-classification.js +0 -0
  289. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/session-hud-spawn.js +0 -0
  290. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/session-id.js +0 -0
  291. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/session-window.js +0 -0
  292. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/shortcuts.js +0 -0
  293. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/sidebar/artifacts-section.js +0 -0
  294. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/sidebar/config-section.js +0 -0
  295. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/sidebar/council-section.js +0 -0
  296. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/sidebar/machines-section.js +0 -0
  297. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/sidebar/projects-section.js +0 -0
  298. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/sidebar/safety-section.js +0 -0
  299. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/sidebar/services-section.js +0 -0
  300. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/sidebar/sessions-section.js +0 -0
  301. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/sidebar.js +0 -0
  302. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/spawn-ghost.js +0 -0
  303. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/terminal-font-prefs.js +0 -0
  304. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/terminal-pane.js +0 -0
  305. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/tile-manager.js +0 -0
  306. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/toast.js +0 -0
  307. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/token-modal.js +0 -0
  308. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/utils/ansi.js +0 -0
  309. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/utils/swipe.js +0 -0
  310. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/voice/autosend-prefs.js +0 -0
  311. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/voice/browser-stt.js +0 -0
  312. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/voice/browser-tts.js +0 -0
  313. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/voice/jargon.js +0 -0
  314. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/voice/prompt.js +0 -0
  315. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/winbox.bundle.min.js +0 -0
  316. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/js/workspace-window.js +0 -0
  317. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/manifest.webmanifest +0 -0
  318. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/service-worker.js +0 -0
  319. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/static/topology-harness.html +0 -0
  320. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/stt/__init__.py +0 -0
  321. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/stt/base.py +0 -0
  322. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/stt/cloud.py +0 -0
  323. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/stt/engine.py +0 -0
  324. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/stt/local.py +0 -0
  325. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/stt/server_backend.py +0 -0
  326. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/stt/stt_server.py +0 -0
  327. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/system_cli.py +0 -0
  328. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/tabs_cli.py +0 -0
  329. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/tasks.py +0 -0
  330. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/tasks_cli.py +0 -0
  331. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/templates/__init__.py +0 -0
  332. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/templates/base.html +0 -0
  333. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/templates/council/minutes.html.j2 +0 -0
  334. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/templates/desktop.html +0 -0
  335. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/templates/email_notification.html +0 -0
  336. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/templates/handoff/show-the-story.html.j2 +0 -0
  337. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/templates/handoff/theme.css.j2 +0 -0
  338. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/templates/mobile.html +0 -0
  339. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/templates/pair.html +0 -0
  340. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/templates/tmux.conf +0 -0
  341. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/templating.py +0 -0
  342. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/tooldefs/aws.yaml +0 -0
  343. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/tooldefs/docker.yaml +0 -0
  344. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/tooldefs/gcp.yaml +0 -0
  345. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/tooldefs/gh.yaml +0 -0
  346. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/tooldefs/git.yaml +0 -0
  347. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/tooldefs/gws.yaml +0 -0
  348. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/tooldefs/kubectl.yaml +0 -0
  349. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/tooldefs/npm.yaml +0 -0
  350. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/tooldefs/terraform.yaml +0 -0
  351. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/tooldefs/uv.yaml +0 -0
  352. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/tts/__init__.py +0 -0
  353. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/tts/audio.py +0 -0
  354. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/tts/base.py +0 -0
  355. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/tts/engines/__init__.py +0 -0
  356. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/tts/engines/chatterbox.py +0 -0
  357. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/tts/engines/kokoro.py +0 -0
  358. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/tts/engines/zonos.py +0 -0
  359. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/tts/kokoro_server.py +0 -0
  360. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/tts/local.py +0 -0
  361. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/tts/registry.py +0 -0
  362. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/tts_cli.py +0 -0
  363. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/tts_server.py +0 -0
  364. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/tunnels.py +0 -0
  365. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/tunnels_cli.py +0 -0
  366. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/usage_limit.py +0 -0
  367. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/utils/__init__.py +0 -0
  368. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/utils/chunker.py +0 -0
  369. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/utils/event_log.py +0 -0
  370. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/utils/file_io.py +0 -0
  371. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/utils/paths.py +0 -0
  372. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/utils/speech.py +0 -0
  373. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/utils/subprocess.py +0 -0
  374. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/validation.py +0 -0
  375. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/voice_status.py +0 -0
  376. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/wiki.py +0 -0
  377. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/wiki_audit.py +0 -0
  378. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/wiki_cli.py +0 -0
  379. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/agentwire/worktree_registry.py +0 -0
  380. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/docs/decisions/obsidian-second-brain.md +0 -0
  381. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/docs/logo.png +0 -0
  382. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/docs/wiki/INDEX.md +0 -0
  383. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/docs/wiki/briefing-mode.md +0 -0
  384. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/docs/wiki/communication/hammerspoon.md +0 -0
  385. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/docs/wiki/council.md +0 -0
  386. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/docs/wiki/internals/parallel-refactor.md +0 -0
  387. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/docs/wiki/quickstart.md +0 -0
  388. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/docs/wiki/research/briefing-mode-feasibility.md +0 -0
  389. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/docs/wiki/security/pip-audit.md +0 -0
  390. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/docs/wiki/services.md +0 -0
  391. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/docs/wiki/sessions/messaging.md +0 -0
  392. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/docs/wiki/sessions/window-sizing.md +0 -0
  393. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/docs/wiki/sessions/worktree-sessions.md +0 -0
  394. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/docs/wiki/usage-limit-recovery.md +0 -0
  395. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/docs/wiki/voice/stt-cloud.md +0 -0
  396. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/docs/wiki/voice/tts-self-hosted.md +0 -0
  397. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/pyproject.toml +0 -0
  398. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/conftest.py +0 -0
  399. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/e2e/test_portal_ui.py +0 -0
  400. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/fixtures/sample_agentwire.yml +0 -0
  401. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/fixtures/sample_config.yaml +0 -0
  402. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/fixtures/sample_scheduler.yaml +0 -0
  403. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/integration/test_council_portal.py +0 -0
  404. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/integration/test_send_verified_tmux.py +0 -0
  405. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/integration/test_server_websockets.py +0 -0
  406. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/integration/test_worktree_cmd.py +0 -0
  407. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_announcements.py +0 -0
  408. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_build_agent_command.py +0 -0
  409. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_channels.py +0 -0
  410. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_chrome_tabs.py +0 -0
  411. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_cli_commands.py +0 -0
  412. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_cli_output.py +0 -0
  413. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_cli_smoke.py +0 -0
  414. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_config.py +0 -0
  415. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_config_cli.py +0 -0
  416. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_control_plane_protection.py +0 -0
  417. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_core_created_by_rooting.py +0 -0
  418. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_council_cli.py +0 -0
  419. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_council_inbox.py +0 -0
  420. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_council_minutes.py +0 -0
  421. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_council_state.py +0 -0
  422. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_council_view.py +0 -0
  423. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_damage_control_bypass.py +0 -0
  424. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_damage_control_sync.py +0 -0
  425. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_dangling_worktrees.py +0 -0
  426. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_devices.py +0 -0
  427. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_diff_cli.py +0 -0
  428. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_doctor_task_migration.py +0 -0
  429. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_doctor_voice.py +0 -0
  430. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_event_log.py +0 -0
  431. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_file_io.py +0 -0
  432. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_guarded_launch_command.py +0 -0
  433. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_handoff_git_state.py +0 -0
  434. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_handoff_instructions.py +0 -0
  435. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_handoff_parser.py +0 -0
  436. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_handoff_renderer.py +0 -0
  437. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_history.py +0 -0
  438. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_hooks_install.py +0 -0
  439. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_idle_handler.py +0 -0
  440. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_idle_nag.py +0 -0
  441. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_inbox.py +0 -0
  442. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_init_command.py +0 -0
  443. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_install_parity.py +0 -0
  444. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_limits_tick_isolation.py +0 -0
  445. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_locking.py +0 -0
  446. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_mcp_server.py +0 -0
  447. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_mcp_tools_args.py +0 -0
  448. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_msg_cli.py +0 -0
  449. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_notify_cli.py +0 -0
  450. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_onboarding_reinit.py +0 -0
  451. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_palette_cli.py +0 -0
  452. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_pip_environment.py +0 -0
  453. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_portal_api.py +0 -0
  454. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_posture_default.py +0 -0
  455. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_project_config.py +0 -0
  456. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_prompt_router.py +0 -0
  457. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_push.py +0 -0
  458. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_rebuild_guard.py +0 -0
  459. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_repo_cli.py +0 -0
  460. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_roles.py +0 -0
  461. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_routes_snapshot.py +0 -0
  462. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_safety_commands.py +0 -0
  463. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_safety_disabled_rules.py +0 -0
  464. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_safety_escape_hatch.py +0 -0
  465. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_safety_heal.py +0 -0
  466. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_safety_kill_switch.py +0 -0
  467. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_scheduler_parsing.py +0 -0
  468. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_scheduler_zombie.py +0 -0
  469. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_scratchpad.py +0 -0
  470. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_security.py +0 -0
  471. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_server_async.py +0 -0
  472. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_server_pure.py +0 -0
  473. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_services.py +0 -0
  474. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_session_context.py +0 -0
  475. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_session_created_by_env.py +0 -0
  476. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_session_ready.py +0 -0
  477. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_shared_dir_guard.py +0 -0
  478. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_shim_selfheal.py +0 -0
  479. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_skill_install.py +0 -0
  480. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_speech_tags.py +0 -0
  481. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_ssh.py +0 -0
  482. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_stt_backend.py +0 -0
  483. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_stt_cloud.py +0 -0
  484. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_stt_engine.py +0 -0
  485. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_task_cli.py +0 -0
  486. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_tasks.py +0 -0
  487. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_tasks_cli.py +0 -0
  488. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_templating.py +0 -0
  489. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_terminal_resize.py +0 -0
  490. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_tmux_template.py +0 -0
  491. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_tts_engine_resolution.py +0 -0
  492. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_tts_local.py +0 -0
  493. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_tunnels_probe.py +0 -0
  494. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_unattended_env_isolation.py +0 -0
  495. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_usage_limit.py +0 -0
  496. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_validation.py +0 -0
  497. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_voice_status.py +0 -0
  498. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_wiki.py +0 -0
  499. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_wiki_audit.py +0 -0
  500. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_window_cycling_binding.py +0 -0
  501. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_worktree_branch_cleanup.py +0 -0
  502. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_worktree_layout.py +0 -0
  503. {agentwire_dev-1.63.0 → agentwire_dev-1.64.0}/tests/unit/test_worktree_registry.py +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: agentwire-dev
3
- Version: 1.63.0
3
+ Version: 1.64.0
4
4
  Summary: Multi-session voice web interface for AI coding agents
5
5
  Project-URL: Homepage, https://agentwire.dev
6
6
  Project-URL: Repository, https://github.com/dotdevdotdev/agentwire-dev
@@ -1,3 +1,3 @@
1
1
  """AgentWire - Multi-session voice web interface for AI coding agents."""
2
2
 
3
- __version__ = "1.63.0"
3
+ __version__ = "1.64.0"
@@ -13,6 +13,14 @@ from typing import Optional
13
13
 
14
14
  import yaml
15
15
 
16
+ # Gitignored files a fresh git worktree needs seeded — a worktree can't load
17
+ # its session/task config without them. Single source of truth: referenced
18
+ # by WorktreesConfig's default below, the config-loading fallback further
19
+ # down, AND worktree.py's mandatory (never-omittable) seed set (#803) — a
20
+ # stale `copy_files:` in a user's config.yaml that predates one of these
21
+ # being added here must not silently drop it from every fresh worktree.
22
+ DEFAULT_WORKTREE_COPY_FILES = [".env", ".agentwire.yml", ".agentwire.tasks.yml"]
23
+
16
24
 
17
25
  def _get_default_agent_command() -> str:
18
26
  """Get the default agent command.
@@ -105,7 +113,7 @@ class WorktreesConfig:
105
113
  # tasks can't load their session/task config without them when the project
106
114
  # gitignores them (the latter is the protected, host-authored task-exec file —
107
115
  # #720).
108
- copy_files: list = field(default_factory=lambda: [".env", ".agentwire.yml", ".agentwire.tasks.yml"])
116
+ copy_files: list = field(default_factory=lambda: list(DEFAULT_WORKTREE_COPY_FILES))
109
117
 
110
118
 
111
119
  @dataclass
@@ -623,7 +631,7 @@ def _dict_to_config(data: dict) -> Config:
623
631
  enabled=worktrees_data.get("enabled", True),
624
632
  suffix=worktrees_data.get("suffix", "-worktrees"),
625
633
  auto_create_branch=worktrees_data.get("auto_create_branch", True),
626
- copy_files=worktrees_data.get("copy_files", [".env", ".agentwire.yml", ".agentwire.tasks.yml"]),
634
+ copy_files=worktrees_data.get("copy_files", list(DEFAULT_WORKTREE_COPY_FILES)),
627
635
  )
628
636
  projects = ProjectsConfig(
629
637
  dir=projects_data.get("dir", "~/projects"),
@@ -19,6 +19,7 @@ import shutil
19
19
  import socket
20
20
  import subprocess
21
21
  import sys
22
+ import time
22
23
  from pathlib import Path
23
24
 
24
25
  from .core import (
@@ -475,6 +476,75 @@ def _render_shim_liveness_section() -> int:
475
476
  return len(dead)
476
477
 
477
478
 
479
+ def _scheduler_daemon_started_at() -> float | None:
480
+ """Epoch seconds the scheduler daemon process started, or ``None`` if not running.
481
+
482
+ Reads the daemon's own self-reported ``started_at`` from the live-state
483
+ file it already writes every loop tick (``scheduler/loop.py`` ->
484
+ ``_write_live_state`` -> ``read_live_state()``) rather than reimplementing
485
+ process-start-time discovery via ``ps``/``pgrep`` PID matching, which is
486
+ both platform-fragile (``ps`` elapsed-time output format varies) and
487
+ ambiguous if a stray/duplicate daemon process happens to be running.
488
+ ``tmux_session_exists`` confirms the daemon is actually alive, so a
489
+ leftover live-state file from a since-stopped daemon doesn't produce a
490
+ false "stale" reading.
491
+ """
492
+ from .scheduler import SCHEDULER_SESSION, read_live_state
493
+
494
+ if not tmux_session_exists(SCHEDULER_SESSION):
495
+ return None
496
+ state = read_live_state()
497
+ if not state:
498
+ return None
499
+ started_at = state.get("started_at")
500
+ if not started_at:
501
+ return None
502
+ try:
503
+ from datetime import datetime
504
+ return datetime.fromisoformat(started_at).timestamp()
505
+ except (ValueError, TypeError):
506
+ return None
507
+
508
+
509
+ def _newest_installed_source_mtime(pkg_dir: Path | None = None) -> float:
510
+ """Newest mtime among the installed ``agentwire`` package's ``.py`` files."""
511
+ if pkg_dir is None:
512
+ pkg_dir = Path(__file__).resolve().parent
513
+ try:
514
+ return max((f.stat().st_mtime for f in pkg_dir.rglob("*.py")), default=0.0)
515
+ except Exception:
516
+ return 0.0
517
+
518
+
519
+ def _render_scheduler_staleness_section() -> int:
520
+ """Doctor section: flag a scheduler daemon older than the installed code (#803).
521
+
522
+ ``agentwire scheduler serve`` is a long-running Python process — like the
523
+ MCP server, it imports its modules once at start and never re-reads them.
524
+ ``agentwire rebuild`` updates the on-disk package but can't touch an
525
+ already-running interpreter's loaded bytecode, so a daemon that has been
526
+ up since before the last rebuild is silently executing stale dispatch
527
+ logic: any bug fixed since then stays live in production until the
528
+ daemon is restarted.
529
+ """
530
+ started_at = _scheduler_daemon_started_at()
531
+ if started_at is None:
532
+ print(" [..] Scheduler daemon not running — skipping staleness check")
533
+ return 0
534
+
535
+ newest_src = _newest_installed_source_mtime()
536
+ if not newest_src or newest_src <= started_at:
537
+ print(" [ok] Scheduler daemon is current with the installed package")
538
+ return 0
539
+
540
+ age_days = (time.time() - started_at) / 86400
541
+ print(f" [!!] Scheduler daemon has been running {age_days:.1f}d — "
542
+ "predates the most recent `agentwire rebuild`")
543
+ print(" Any dispatch bug fixed since then is still live in the running daemon.")
544
+ print(" Fix: agentwire scheduler stop && agentwire scheduler start")
545
+ return 1
546
+
547
+
478
548
  def cmd_doctor(args) -> int:
479
549
  """Auto-diagnose and fix common issues."""
480
550
  from .hooks_cli import _managed_file_state, _managed_hook_files, get_hooks_source
@@ -653,6 +723,14 @@ def cmd_doctor(args) -> int:
653
723
  else:
654
724
  print(" [ok] Local main up to date with origin/main")
655
725
 
726
+ # 4d. Scheduler daemon staleness — the daemon is a long-running process
727
+ # that never re-imports its code, so it can silently run a dispatch bug
728
+ # that's since been fixed on disk (#803). Distinct from the git-drift
729
+ # check above: that flags an out-of-date CHECKOUT, this flags a
730
+ # currently-running PROCESS that predates the last install.
731
+ print("\nChecking scheduler daemon freshness...")
732
+ issues_found += _render_scheduler_staleness_section()
733
+
656
734
  # Check custom services (registry-driven: built-in notifications bridge
657
735
  # + user-defined services from services.custom)
658
736
  print("\nChecking custom services...")
@@ -613,8 +613,8 @@ def load_config(
613
613
  # dispatch by the scheduler), the hook resolves ``ask`` by FAILING CLOSED:
614
614
  # block + notify the owner, UNLESS the matched rule's stable ID is on the
615
615
  # allowlist. The allowlist is the union of:
616
- # 1. ``DEFAULT_UNATTENDED_ALLOW`` below (tight — work + open a PR, nothing
617
- # irreversible or outward-facing),
616
+ # 1. ``DEFAULT_UNATTENDED_ALLOW`` below (work + open a PR + notify the owner
617
+ # by email — nothing else irreversible or outward-facing),
618
618
  # 2. ``safety.unattended_allow`` from global / project config,
619
619
  # 3. ``AGENTWIRE_UNATTENDED_ALLOW`` (comma-separated) — the per-task
620
620
  # extension the scheduler stamps from a task's ``unattended_allow``.
@@ -629,6 +629,7 @@ DEFAULT_UNATTENDED_ALLOW = {
629
629
  "git.commit", # commit
630
630
  "git.push", # push (force/delete are SEPARATE hard-block/ask rules)
631
631
  "gh.pr-create", # open a PR — the human-reviewed gate
632
+ "outbound.agentwire-email", # blanket allow, any recipient (#804)
632
633
  }
633
634
 
634
635
 
@@ -609,8 +609,8 @@ def load_config(
609
609
  # dispatch by the scheduler), the hook resolves ``ask`` by FAILING CLOSED:
610
610
  # block + notify the owner, UNLESS the matched rule's stable ID is on the
611
611
  # allowlist. The allowlist is the union of:
612
- # 1. ``DEFAULT_UNATTENDED_ALLOW`` below (tight — work + open a PR, nothing
613
- # irreversible or outward-facing),
612
+ # 1. ``DEFAULT_UNATTENDED_ALLOW`` below (work + open a PR + notify the owner
613
+ # by email — nothing else irreversible or outward-facing),
614
614
  # 2. ``safety.unattended_allow`` from global / project config,
615
615
  # 3. ``AGENTWIRE_UNATTENDED_ALLOW`` (comma-separated) — the per-task
616
616
  # extension the scheduler stamps from a task's ``unattended_allow``.
@@ -625,6 +625,7 @@ DEFAULT_UNATTENDED_ALLOW = {
625
625
  "git.commit", # commit
626
626
  "git.push", # push (force/delete are SEPARATE hard-block/ask rules)
627
627
  "gh.pr-create", # open a PR — the human-reviewed gate
628
+ "outbound.agentwire-email", # blanket allow, any recipient (#804)
628
629
  }
629
630
 
630
631
 
@@ -621,8 +621,8 @@ def load_config(
621
621
  # dispatch by the scheduler), the hook resolves ``ask`` by FAILING CLOSED:
622
622
  # block + notify the owner, UNLESS the matched rule's stable ID is on the
623
623
  # allowlist. The allowlist is the union of:
624
- # 1. ``DEFAULT_UNATTENDED_ALLOW`` below (tight — work + open a PR, nothing
625
- # irreversible or outward-facing),
624
+ # 1. ``DEFAULT_UNATTENDED_ALLOW`` below (work + open a PR + notify the owner
625
+ # by email — nothing else irreversible or outward-facing),
626
626
  # 2. ``safety.unattended_allow`` from global / project config,
627
627
  # 3. ``AGENTWIRE_UNATTENDED_ALLOW`` (comma-separated) — the per-task
628
628
  # extension the scheduler stamps from a task's ``unattended_allow``.
@@ -637,6 +637,7 @@ DEFAULT_UNATTENDED_ALLOW = {
637
637
  "git.commit", # commit
638
638
  "git.push", # push (force/delete are SEPARATE hard-block/ask rules)
639
639
  "gh.pr-create", # open a PR — the human-reviewed gate
640
+ "outbound.agentwire-email", # blanket allow, any recipient (#804)
640
641
  }
641
642
 
642
643
 
@@ -615,8 +615,8 @@ def load_config(
615
615
  # dispatch by the scheduler), the hook resolves ``ask`` by FAILING CLOSED:
616
616
  # block + notify the owner, UNLESS the matched rule's stable ID is on the
617
617
  # allowlist. The allowlist is the union of:
618
- # 1. ``DEFAULT_UNATTENDED_ALLOW`` below (tight — work + open a PR, nothing
619
- # irreversible or outward-facing),
618
+ # 1. ``DEFAULT_UNATTENDED_ALLOW`` below (work + open a PR + notify the owner
619
+ # by email — nothing else irreversible or outward-facing),
620
620
  # 2. ``safety.unattended_allow`` from global / project config,
621
621
  # 3. ``AGENTWIRE_UNATTENDED_ALLOW`` (comma-separated) — the per-task
622
622
  # extension the scheduler stamps from a task's ``unattended_allow``.
@@ -631,6 +631,7 @@ DEFAULT_UNATTENDED_ALLOW = {
631
631
  "git.commit", # commit
632
632
  "git.push", # push (force/delete are SEPARATE hard-block/ask rules)
633
633
  "gh.pr-create", # open a PR — the human-reviewed gate
634
+ "outbound.agentwire-email", # blanket allow, any recipient (#804)
634
635
  }
635
636
 
636
637
 
@@ -608,8 +608,8 @@ def load_config(
608
608
  # dispatch by the scheduler), the hook resolves ``ask`` by FAILING CLOSED:
609
609
  # block + notify the owner, UNLESS the matched rule's stable ID is on the
610
610
  # allowlist. The allowlist is the union of:
611
- # 1. ``DEFAULT_UNATTENDED_ALLOW`` below (tight — work + open a PR, nothing
612
- # irreversible or outward-facing),
611
+ # 1. ``DEFAULT_UNATTENDED_ALLOW`` below (work + open a PR + notify the owner
612
+ # by email — nothing else irreversible or outward-facing),
613
613
  # 2. ``safety.unattended_allow`` from global / project config,
614
614
  # 3. ``AGENTWIRE_UNATTENDED_ALLOW`` (comma-separated) — the per-task
615
615
  # extension the scheduler stamps from a task's ``unattended_allow``.
@@ -624,6 +624,7 @@ DEFAULT_UNATTENDED_ALLOW = {
624
624
  "git.commit", # commit
625
625
  "git.push", # push (force/delete are SEPARATE hard-block/ask rules)
626
626
  "gh.pr-create", # open a PR — the human-reviewed gate
627
+ "outbound.agentwire-email", # blanket allow, any recipient (#804)
627
628
  }
628
629
 
629
630
 
@@ -577,8 +577,8 @@ def load_config(
577
577
  # dispatch by the scheduler), the hook resolves ``ask`` by FAILING CLOSED:
578
578
  # block + notify the owner, UNLESS the matched rule's stable ID is on the
579
579
  # allowlist. The allowlist is the union of:
580
- # 1. ``DEFAULT_UNATTENDED_ALLOW`` below (tight — work + open a PR, nothing
581
- # irreversible or outward-facing),
580
+ # 1. ``DEFAULT_UNATTENDED_ALLOW`` below (work + open a PR + notify the owner
581
+ # by email — nothing else irreversible or outward-facing),
582
582
  # 2. ``safety.unattended_allow`` from global / project config,
583
583
  # 3. ``AGENTWIRE_UNATTENDED_ALLOW`` (comma-separated) — the per-task
584
584
  # extension the scheduler stamps from a task's ``unattended_allow``.
@@ -593,6 +593,7 @@ DEFAULT_UNATTENDED_ALLOW = {
593
593
  "git.commit", # commit
594
594
  "git.push", # push (force/delete are SEPARATE hard-block/ask rules)
595
595
  "gh.pr-create", # open a PR — the human-reviewed gate
596
+ "outbound.agentwire-email", # blanket allow, any recipient (#804)
596
597
  }
597
598
 
598
599
 
@@ -46,7 +46,25 @@ def _check_gate(board, task_name: str) -> bool:
46
46
  project = task.project
47
47
 
48
48
  def _gate_skip(gate_type: str, reason: str, **extra):
49
- """Record a gate skip, only logging on first occurrence."""
49
+ """Record a gate skip. Logs only on first occurrence (spam control),
50
+ but persists ``last_gate_skip`` on every REASON CHANGE.
51
+
52
+ Distinct from ``_gate_error`` below: this is the CLEAN "not ready
53
+ yet" path (e.g. a ``command`` gate legitimately returning nonzero),
54
+ not an exception. Recorded so the board can show "waiting on gate"
55
+ instead of reading as silently-falling-behind overdue (#803).
56
+ Persisting on reason-change (not just first-occurrence, which
57
+ ``_gated_tasks`` alone gates) matters for multi-condition gates: if
58
+ task's blocker shifts from ``git_commit`` to ``command`` without the
59
+ gate ever fully passing in between, ``task_name`` never leaves
60
+ ``_gated_tasks``, so a first-occurrence-only write would leave the
61
+ board showing the ORIGINAL, now-stale reason.
62
+ """
63
+ skip_text = f"{gate_type}: {reason}"
64
+ if state.last_gate_skip != skip_text:
65
+ state.last_gate_skip = skip_text
66
+ board.state[task_name] = state
67
+ _sched.save_board(board)
50
68
  if task_name not in _gated_tasks:
51
69
  _sched._log_event("task_gated", task=task_name, gate_type=gate_type,
52
70
  reason=reason, **extra)
@@ -69,6 +87,7 @@ def _check_gate(board, task_name: str) -> bool:
69
87
  print(f"[{_ts()}] Gate error on {task_name}: {gate_type} "
70
88
  f"({reason}) — failing open")
71
89
  state.last_gate_error = f"{gate_type}: {reason}"
90
+ state.last_gate_skip = "" # failing open — no longer "waiting on gate"
72
91
  board.state[task_name] = state
73
92
  _sched.save_board(board)
74
93
  _gated_tasks.discard(task_name)
@@ -131,16 +150,20 @@ def _check_gate(board, task_name: str) -> bool:
131
150
 
132
151
 
133
152
  def _clear_gate_error(board, task_name: str) -> None:
134
- """Clear a previously-recorded gate error once the gate evaluates cleanly.
153
+ """Clear a previously-recorded gate error/skip once the gate evaluates cleanly.
135
154
 
136
- No-op (and no board write) unless this task actually had an error, so
137
- the common clean path stays cheap.
155
+ No-op (and no board write) unless this task actually had something
156
+ recorded, so the common clean path stays cheap. Clears BOTH
157
+ ``last_gate_error`` (exception path) and ``last_gate_skip`` (clean
158
+ "not ready yet" path, #803) — both are stale the moment the gate passes.
138
159
  """
139
160
  from agentwire import scheduler as _sched
140
161
 
141
162
  state = board.state.get(task_name)
142
163
  had_tracked = _gate_errored.pop(task_name, None) is not None
143
- if had_tracked or (state is not None and state.last_gate_error):
144
- if state is not None and state.last_gate_error:
164
+ had_state = state is not None and (state.last_gate_error or state.last_gate_skip)
165
+ if had_tracked or had_state:
166
+ if state is not None and (state.last_gate_error or state.last_gate_skip):
145
167
  state.last_gate_error = ""
168
+ state.last_gate_skip = ""
146
169
  _sched.save_board(board)
@@ -89,6 +89,7 @@ class TaskState:
89
89
  run_count: int = 0
90
90
  last_summary: str = ""
91
91
  last_gate_error: str = "" # last gate-eval exception reason (failed open)
92
+ last_gate_skip: str = "" # currently-blocking gate reason (clean skip, not an error)
92
93
  last_gate_commit: str = "" # HEAD at last dispatch (for gate checks)
93
94
  last_dispatch: datetime | None = None # set BEFORE running (restart safety)
94
95
  # Active worktree-PR tracking (set on finalize, cleared by the reaper on
@@ -199,6 +199,8 @@ def get_board_display(board: Board) -> list[dict]:
199
199
  row["last_summary"] = state.last_summary
200
200
  if state.last_gate_error:
201
201
  row["last_gate_error"] = state.last_gate_error
202
+ if state.last_gate_skip:
203
+ row["last_gate_skip"] = state.last_gate_skip
202
204
  rows.append(row)
203
205
 
204
206
  # Sort: enabled first, then by overdue (most overdue first)
@@ -112,6 +112,7 @@ def load_board() -> Board:
112
112
  run_count=int(s.get("run_count", 0)),
113
113
  last_summary=str(s.get("last_summary", "")),
114
114
  last_gate_error=str(s.get("last_gate_error", "")),
115
+ last_gate_skip=str(s.get("last_gate_skip", "")),
115
116
  last_gate_commit=str(s.get("last_gate_commit", "")),
116
117
  last_dispatch=_parse_datetime_field(s.get("last_dispatch")),
117
118
  worktree_branch=str(s.get("worktree_branch", "")),
@@ -163,6 +164,8 @@ def _state_to_dict(board: Board) -> dict:
163
164
  entry["last_summary"] = s.last_summary
164
165
  if s.last_gate_error:
165
166
  entry["last_gate_error"] = s.last_gate_error
167
+ if s.last_gate_skip:
168
+ entry["last_gate_skip"] = s.last_gate_skip
166
169
  if s.last_gate_commit:
167
170
  entry["last_gate_commit"] = s.last_gate_commit
168
171
  if s.last_dispatch:
@@ -148,7 +148,7 @@ def _recent_activity(events: list[dict], limit: int = 5) -> list[dict]:
148
148
  glance at `scheduler status` shows recent results — including the
149
149
  fail-open gate errors that used to vanish entirely.
150
150
  """
151
- keep = {"task_completed", "task_failed", "gate_error"}
151
+ keep = {"task_completed", "task_failed", "gate_error", "task_gated"}
152
152
  out: list[dict] = []
153
153
  for evt in reversed(events):
154
154
  etype = evt.get("event")
@@ -165,6 +165,8 @@ def _recent_activity(events: list[dict], limit: int = 5) -> list[dict]:
165
165
  detail = f"{status}" + (f" — {summary}" if summary else "")
166
166
  elif etype == "task_failed":
167
167
  detail = "failed — " + (evt.get("summary") or evt.get("reason") or "?")
168
+ elif etype == "task_gated":
169
+ detail = f"[gated] {evt.get('gate_type', '?')}: {evt.get('reason', '?')}"
168
170
  else: # gate_error
169
171
  detail = f"[gate-error] {evt.get('gate_type', '?')}: {evt.get('reason', '?')}"
170
172
  if len(detail) > 80:
@@ -254,10 +256,14 @@ def cmd_scheduler_board(args) -> int:
254
256
  )
255
257
 
256
258
  # Surface WHY: a gate-eval error (fail-open, would otherwise be
257
- # invisible) takes precedence; else the summary behind a bad status.
259
+ # invisible) takes precedence; then a currently-blocking gate
260
+ # (so "+4h11m" reads as "waiting on gate", not silently falling
261
+ # behind, #803); else the summary behind a bad status.
258
262
  detail = ""
259
263
  if r.get("last_gate_error"):
260
264
  detail = f"[gate-error] {r['last_gate_error']}"
265
+ elif r.get("last_gate_skip"):
266
+ detail = f"[gated] {r['last_gate_skip']}"
261
267
  elif status_str in _BAD_STATUSES and r.get("last_summary"):
262
268
  detail = r["last_summary"]
263
269
  if detail:
@@ -5958,8 +5958,12 @@ body.sidebar-pinned .sidebar-tab {
5958
5958
 
5959
5959
  /* ============================================
5960
5960
  Session HUD — top-edge frosted drawer (#776, foundation shell)
5961
- Two detents (peek 33vh / half 50vh), top-center pull handle. Content is
5962
- mounted into .session-hud-canvas by a later issue (#777, TopologyView).
5961
+ Two detents, top-center pull handle: "peek" auto-sizes to content, floored
5962
+ and capped at the fixed "half" (50vh) ceiling (#802, session-hud.js's
5963
+ _applyAutoHeight); the 33vh height below is only the pre-JS-measurement
5964
+ fallback for the instant the drawer is created, before content exists.
5965
+ Content is mounted into .session-hud-canvas by a later issue (#777,
5966
+ TopologyView).
5963
5967
  ============================================ */
5964
5968
 
5965
5969
  /* Left offset shared by the drawer and its handle so the two never drift.
@@ -6655,20 +6659,60 @@ body.sidebar-pinned { --hud-left: var(--sidebar-width); }
6655
6659
  gap: 6px;
6656
6660
  }
6657
6661
 
6658
- .topology-spark {
6659
- display: flex;
6660
- align-items: flex-end;
6661
- gap: 2px;
6662
- height: 12px;
6662
+ /* Full-width activity pulse strip (#800), replacing the old bar sparkline.
6663
+ The rules below are the `idle` resting state — dim, slow, low-amplitude,
6664
+ still visibly "alive". flow/awaiting/stuck override speed/amplitude/colour
6665
+ further down, keyed off the card's state class. */
6666
+ .topology-pulse {
6667
+ position: relative;
6668
+ width: 100%;
6669
+ height: 20px;
6670
+ border-radius: 4px;
6663
6671
  }
6664
6672
 
6665
- .topology-spark i {
6673
+ .topology-pulse-svg {
6666
6674
  display: block;
6667
- width: 2px;
6668
- height: 3px;
6669
- border-radius: 1px;
6670
- background: var(--text-muted);
6671
- opacity: 0.5;
6675
+ width: 100%;
6676
+ height: 100%;
6677
+ }
6678
+
6679
+ .topology-pulse-base {
6680
+ stroke: var(--text-muted);
6681
+ stroke-width: 1px;
6682
+ opacity: 0.18;
6683
+ }
6684
+
6685
+ .topology-pulse-scroll {
6686
+ animation: topology-pulse-scroll 3.2s linear infinite;
6687
+ }
6688
+
6689
+ .topology-pulse-trace {
6690
+ fill: none;
6691
+ stroke: var(--text-muted);
6692
+ stroke-width: 1.6px;
6693
+ stroke-linecap: round;
6694
+ stroke-linejoin: round;
6695
+ opacity: 0.4;
6696
+ vector-effect: non-scaling-stroke;
6697
+ transform-box: fill-box;
6698
+ transform-origin: center;
6699
+ transform: scaleY(0.32);
6700
+ }
6701
+
6702
+ .topology-pulse-marker {
6703
+ position: absolute;
6704
+ top: 50%;
6705
+ right: 3px;
6706
+ width: 5px;
6707
+ height: 5px;
6708
+ margin-top: -2.5px;
6709
+ border-radius: 50%;
6710
+ opacity: 0;
6711
+ pointer-events: none;
6712
+ }
6713
+
6714
+ @keyframes topology-pulse-scroll {
6715
+ to { transform: translateX(-240px); }
6672
6716
  }
6673
6717
 
6674
6718
  .topology-card-machine {
@@ -6785,10 +6829,18 @@ body.sidebar-pinned { --hud-left: var(--sidebar-width); }
6785
6829
  opacity: 0.5;
6786
6830
  animation: topology-dot-ring 1.8s ease-out infinite;
6787
6831
  }
6788
- .topology-card--flow .topology-spark i {
6789
- background: var(--card-tint, var(--lineage-tint-1));
6790
- opacity: 0.9;
6791
- animation: topology-spark-eq 1s ease-in-out infinite;
6832
+ .topology-card--flow .topology-pulse-base {
6833
+ stroke: var(--card-tint, var(--lineage-tint-1));
6834
+ opacity: 0.22;
6835
+ }
6836
+ .topology-card--flow .topology-pulse-scroll {
6837
+ animation-duration: 1.15s;
6838
+ }
6839
+ .topology-card--flow .topology-pulse-trace {
6840
+ stroke: var(--card-tint, var(--lineage-tint-1));
6841
+ opacity: 0.95;
6842
+ transform: scaleY(1);
6843
+ filter: drop-shadow(0 0 3px color-mix(in srgb, var(--card-tint, var(--lineage-tint-1)) 55%, transparent));
6792
6844
  }
6793
6845
 
6794
6846
  /* Failure-state parity (#749): awaiting/stuck override the lineage tint
@@ -6803,9 +6855,19 @@ body.sidebar-pinned { --hud-left: var(--sidebar-width); }
6803
6855
  opacity: 0.6;
6804
6856
  animation: topology-dot-ring 1.3s ease-out infinite;
6805
6857
  }
6806
- .topology-card--awaiting .topology-spark i {
6858
+ .topology-card--awaiting .topology-pulse-trace {
6859
+ stroke: var(--topology-awaiting);
6860
+ opacity: 0.9;
6861
+ transform: scaleY(0.7);
6862
+ }
6863
+ .topology-card--awaiting .topology-pulse-scroll {
6864
+ animation-duration: 2s;
6865
+ }
6866
+ .topology-card--awaiting .topology-pulse-marker {
6807
6867
  background: var(--topology-awaiting);
6808
- opacity: 0.7;
6868
+ box-shadow: 0 0 5px var(--topology-awaiting-glow);
6869
+ opacity: 1;
6870
+ animation: topology-pulse-blink 1.1s ease-in-out infinite;
6809
6871
  }
6810
6872
  .topology-card--stuck .topology-status-dot {
6811
6873
  background: var(--topology-stuck);
@@ -6816,9 +6878,23 @@ body.sidebar-pinned { --hud-left: var(--sidebar-width); }
6816
6878
  opacity: 0.7;
6817
6879
  animation: topology-dot-ring 0.9s ease-out infinite;
6818
6880
  }
6819
- .topology-card--stuck .topology-spark i {
6881
+ .topology-card--stuck .topology-pulse-base {
6882
+ stroke: var(--topology-stuck);
6883
+ opacity: 0.3;
6884
+ }
6885
+ .topology-card--stuck .topology-pulse-trace {
6886
+ stroke: var(--topology-stuck);
6887
+ opacity: 0.9;
6888
+ transform: scaleY(0.16);
6889
+ }
6890
+ .topology-card--stuck .topology-pulse-scroll {
6891
+ animation-duration: 0.9s;
6892
+ }
6893
+ .topology-card--stuck .topology-pulse-marker {
6820
6894
  background: var(--topology-stuck);
6821
- opacity: 0.7;
6895
+ box-shadow: 0 0 6px var(--topology-stuck-glow);
6896
+ opacity: 1;
6897
+ animation: topology-pulse-blink 0.7s steps(2, jump-none) infinite;
6822
6898
  }
6823
6899
 
6824
6900
  /* "You-are-here" self/root card (#778) — the Session HUD's re-rooted view
@@ -6845,9 +6921,9 @@ body.sidebar-pinned { --hud-left: var(--sidebar-width); }
6845
6921
  0% { transform: scale(0.6); opacity: 0.7; }
6846
6922
  100% { transform: scale(1.9); opacity: 0; }
6847
6923
  }
6848
- @keyframes topology-spark-eq {
6849
- 0%, 100% { height: 3px; }
6850
- 50% { height: 11px; }
6924
+ @keyframes topology-pulse-blink {
6925
+ 0%, 100% { opacity: 1; }
6926
+ 50% { opacity: 0.15; }
6851
6927
  }
6852
6928
 
6853
6929
  .topology-link {
@@ -6886,7 +6962,8 @@ body.sidebar-pinned { --hud-left: var(--sidebar-width); }
6886
6962
 
6887
6963
  @media (prefers-reduced-motion: reduce) {
6888
6964
  .topology-status-dot::after,
6889
- .topology-card--flow .topology-spark i,
6965
+ .topology-pulse-scroll,
6966
+ .topology-pulse-marker,
6890
6967
  .topology-link--flow,
6891
6968
  .topology-link--awaiting,
6892
6969
  .topology-link--stuck {
@@ -6918,7 +6995,11 @@ body.sidebar-pinned { --hud-left: var(--sidebar-width); }
6918
6995
 
6919
6996
  .topology-view--shade .topology-family {
6920
6997
  flex: 0 0 auto;
6921
- gap: 6px;
6998
+ /* Vertical gap between depth rows — the connector bezier's min bend is 24px
6999
+ (bezierPath in topology-render.js), so give the wires at least that much
7000
+ room to travel between a parent row and its children (#792 was 6px, too
7001
+ tight for the S-curve to sit inside the gap). */
7002
+ gap: 26px;
6922
7003
  }
6923
7004
 
6924
7005
  .topology-view--shade .topology-row {
@@ -7038,7 +7119,8 @@ body.sidebar-pinned { --hud-left: var(--sidebar-width); }
7038
7119
  /* Expanded card hosts a live terminal — the activity sparkline is redundant
7039
7120
  and just steals a row, so hide it, and tighten the card's gap. Reclaims
7040
7121
  vertical space for terminal rows (the card was mostly chrome above it). */
7041
- .topology-card--expanded .topology-card-meta { display: none; }
7122
+ .topology-card--expanded .topology-card-meta,
7123
+ .topology-card--expanded .topology-pulse { display: none; }
7042
7124
  .topology-card--expanded { gap: 4px; }
7043
7125
 
7044
7126
  /* --- born-from-parent placement (#745, absorbed into the HUD by #780) ---
@@ -7121,6 +7203,21 @@ body.sidebar-pinned { --hud-left: var(--sidebar-width); }
7121
7203
  text-overflow: ellipsis;
7122
7204
  }
7123
7205
 
7206
+ /* Read-only git-status badges (#801) — reuses the sidebar's `.sidebar-git-badge`
7207
+ + `.git-*` classes (sidebar/sessions-section.js's `renderGitBadges`) so a
7208
+ worktree reads identically whether it's a live session or a ghost; only the
7209
+ row layout is ghost-specific. Same [hidden]-override gotcha as
7210
+ `.topology-ghost-actions` below — the JS toggles `hidden` every render. */
7211
+ .topology-ghost-git[hidden] {
7212
+ display: none;
7213
+ }
7214
+ .topology-ghost-git {
7215
+ display: flex;
7216
+ align-items: center;
7217
+ gap: 4px;
7218
+ flex-wrap: wrap;
7219
+ }
7220
+
7124
7221
  /* [hidden] must win over the flex display below (equal specificity, later
7125
7222
  author rule otherwise beats the UA [hidden]{display:none} stylesheet) —
7126
7223
  the JS toggles this element's `hidden` attribute per card every render. */