Fix mail read auto-ack and add Mayor startup directive
- Remove auto-ack on mail read so handoff messages persist - Add STARTUP PROTOCOL directive for Mayor and Polecat roles - Agents now get explicit instructions to check in on startup 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
This commit is contained in:
@@ -7,7 +7,7 @@
|
||||
{"id":"gt-0pc","title":"Document Overseer role (human operator)","description":"Document the Overseer role in Gas Town architecture.\n\n## The Overseer\n\nThe **Overseer** is the human operator of Gas Town. Not an agent - a person.\n\n## Responsibilities\n\n| Area | Overseer Does | Mayor/Agents Do |\n|------|---------------|-----------------|\n| Strategy | Define project goals | Execute toward goals |\n| Priorities | Set priority order | Work in priority order |\n| Escalations | Final decision on stuck work | Escalate to Overseer |\n| Resources | Provision machines | Use allocated resources |\n| Quality | Review \u0026 approve swarm output | Produce output |\n| Operations | Run gt commands, monitor dashboards | Do the work |\n\n## Key Interactions\n\n### Overseer → Mayor\n- Start/stop Mayor sessions\n- Direct Mayor via conversation\n- Review Mayor recommendations\n- Approve cross-rig decisions\n\n### Mayor → Overseer (Escalations)\n- Stuck workers after retries\n- Resource decisions (add machines, polecats)\n- Ambiguous requirements\n- Architecture decisions\n\n## Operating Cadence\n\nTypical Overseer workflow:\n1. Morning: Check status, review overnight work\n2. During day: Monitor, respond to escalations, adjust priorities\n3. End of day: Review progress, plan next batch\n\n## Commands for Overseers\n\n```bash\ngt status # Quick health check\ngt doctor # Detailed diagnostics \ngt doctor --fix # Auto-repair issues\ngt inbox # Messages from agents\ngt stop --all # Emergency halt\n```\n\n## Documentation Updates\n\nAdd to docs/architecture.md:\n- Overseer section under Agent Roles\n- Clarify Mayor reports to Overseer\n- Add Overseer to workflow diagrams","status":"closed","priority":1,"issue_type":"task","created_at":"2025-12-15T23:18:03.177633-08:00","updated_at":"2025-12-15T23:22:51.477786-08:00","closed_at":"2025-12-15T23:22:51.477786-08:00"}
|
||||
{"id":"gt-0pl","title":"Polecat CLAUDE.md: configure auto-approve for bd and gt commands","description":"Polecats get stuck waiting for bash command approval when running\nbd and gt commands. Need to configure Claude Code to auto-approve these.\n\nOptions:\n1. Add allowedTools to polecat CLAUDE.md\n2. Configure .claude/settings.json in polecat directory\n3. Use --dangerously-skip-permissions flag (not recommended)\n\nShould auto-approve:\n- bd (beads commands)\n- gt (gastown commands)\n- go build/test\n- git status/add/commit/push\n\nShould still require approval:\n- rm -rf\n- Arbitrary commands outside project\n\nRelated to polecat prompting (gt-e1y, gt-sd6).","status":"closed","priority":1,"issue_type":"task","created_at":"2025-12-17T14:10:27.611612-08:00","updated_at":"2025-12-17T14:22:00.715979-08:00","closed_at":"2025-12-17T14:22:00.715979-08:00"}
|
||||
{"id":"gt-0qki","title":"Refinery-Witness communication protocol","description":"Define mail protocol between Refinery and Witness:\n\nFROM Witness → Refinery:\n- 'Polecat ready': polecat X completed work, ready for merge\n- 'Rework complete': polecat Y finished requested rework\n\nFROM Refinery → Witness:\n- 'Merge success': polecat X merged, can be cleaned up\n- 'Merge failed': polecat X needs rework on \u003creason\u003e\n- 'Rework request': please have a polecat rebase X on current main\n\nImplement as structured mail with parseable format.","status":"open","priority":2,"issue_type":"task","created_at":"2025-12-19T18:09:27.451344-08:00","updated_at":"2025-12-19T18:09:27.451344-08:00","dependencies":[{"issue_id":"gt-0qki","depends_on_id":"gt-ktal","type":"blocks","created_at":"2025-12-19T18:09:39.58445-08:00","created_by":"daemon"}]}
|
||||
{"id":"gt-14hd","title":"Work on ga-xxp: Define mol-polecat-work standard molecule...","description":"Work on ga-xxp: Define mol-polecat-work standard molecule. See bd show ga-xxp for full details.","status":"in_progress","priority":2,"issue_type":"task","assignee":"gastown/polecat-01","created_at":"2025-12-19T21:49:14.070072-08:00","updated_at":"2025-12-19T21:49:14.140363-08:00"}
|
||||
{"id":"gt-14hd","title":"Work on ga-xxp: Define mol-polecat-work standard molecule...","description":"Work on ga-xxp: Define mol-polecat-work standard molecule. See bd show ga-xxp for full details.","status":"closed","priority":2,"issue_type":"task","assignee":"gastown/polecat-01","created_at":"2025-12-19T21:49:14.070072-08:00","updated_at":"2025-12-19T22:01:24.336471-08:00","closed_at":"2025-12-19T22:01:24.336471-08:00","close_reason":"Added mol-polecat-work built-in molecule with 8 steps for full polecat lifecycle"}
|
||||
{"id":"gt-17r","title":"Doctor check: Zombie session cleanup","description":"Detect and clean up zombie tmux sessions via gt doctor.\n\n## Problem\n\nZombie sessions occur when:\n- Agent crashes without cleanup\n- gt kill fails mid-operation\n- System restart leaves orphan sessions\n- Session naming collision\n\n## Checks\n\n### ZombieSessionCheck\n- List all tmux sessions matching gt-* pattern\n- Cross-reference with known polecats\n- Flag sessions with no corresponding polecat state\n- Flag sessions for removed polecats\n- Check session age vs polecat creation time\n\n### Detection Criteria\n- Session exists but polecat directory doesn't\n- Session name doesn't match any registered polecat\n- Polecat state=idle but session running\n- Multiple sessions for same polecat\n\n## Output\n\n```\n[WARN] Zombie tmux sessions detected:\n - gt-wyvern-OldPolecat (polecat removed)\n - gt-beads-Unknown (no matching polecat)\n - gt-wyvern-Toast (duplicate session)\n\n Run 'gt doctor --fix' to clean up\n```\n\n## Auto-Fix (--fix flag)\n\n- Kill orphan tmux sessions\n- Update polecat state to match reality\n- Log all cleanup actions\n\n## Safety\n\n- Never kill sessions where polecat state=working\n- Prompt before killing if --fix used without --force\n- Create audit log of killed sessions","status":"open","priority":1,"issue_type":"task","created_at":"2025-12-15T23:18:01.446702-08:00","updated_at":"2025-12-15T23:18:39.517644-08:00","dependencies":[{"issue_id":"gt-17r","depends_on_id":"gt-f9x.4","type":"blocks","created_at":"2025-12-15T23:19:05.66301-08:00","created_by":"daemon"},{"issue_id":"gt-17r","depends_on_id":"gt-7ik","type":"blocks","created_at":"2025-12-17T15:44:41.945064-08:00","created_by":"daemon"}]}
|
||||
{"id":"gt-17zr","title":"gt refinery start: doesn't actually start a session","description":"## Problem\n\n`gt refinery start gastown` reports success but doesn't start a tmux session.\n\n## Evidence\n\n```\n$ gt refinery start gastown\nStarting refinery for gastown...\n✓ Refinery started for gastown\n\n$ tmux list-sessions | grep refinery\n(nothing)\n\n$ gt refinery status gastown\nState: ○ stopped\n```\n\n## Expected\n\nShould start a tmux session (e.g., gt-gastown-refinery) with Claude processing the merge queue.\n\n## Related\n\n- gt-kcee: Witness commands also need implementation\n- The refinery 'start' may just be updating state.json without spawning a session","status":"closed","priority":1,"issue_type":"bug","created_at":"2025-12-18T21:58:57.188389-08:00","updated_at":"2025-12-19T01:33:49.858934-08:00","closed_at":"2025-12-19T01:33:49.858934-08:00"}
|
||||
{"id":"gt-1cuq","title":"Merge: gt-svi.1","description":"type: merge-request\nbranch: polecat/Max\ntarget: main\nsource_issue: gt-svi.1\nrig: gastown","status":"closed","priority":0,"issue_type":"task","created_at":"2025-12-18T20:15:31.738938-08:00","updated_at":"2025-12-18T20:15:49.759778-08:00","closed_at":"2025-12-18T20:15:49.759778-08:00"}
|
||||
|
||||
@@ -373,8 +373,9 @@ func runMailRead(cmd *cobra.Command, args []string) error {
|
||||
return fmt.Errorf("getting message: %w", err)
|
||||
}
|
||||
|
||||
// Mark as read
|
||||
_ = mailbox.MarkRead(msgID)
|
||||
// Note: We intentionally do NOT mark as read/ack on read.
|
||||
// User must explicitly delete/ack the message.
|
||||
// This preserves handoff messages for reference.
|
||||
|
||||
// JSON output
|
||||
if mailReadJSON {
|
||||
|
||||
@@ -88,6 +88,9 @@ func runPrime(cmd *cobra.Command, args []string) error {
|
||||
// Run gt mail check --inject to inject any pending mail
|
||||
runMailCheckInject(cwd)
|
||||
|
||||
// Output startup directive for roles that should announce themselves
|
||||
outputStartupDirective(ctx)
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
@@ -385,6 +388,30 @@ func runBdPrime(workDir string) {
|
||||
}
|
||||
}
|
||||
|
||||
// outputStartupDirective outputs role-specific instructions for the agent.
|
||||
// This tells agents like Mayor to announce themselves on startup.
|
||||
func outputStartupDirective(ctx RoleContext) {
|
||||
switch ctx.Role {
|
||||
case RoleMayor:
|
||||
fmt.Println()
|
||||
fmt.Println("---")
|
||||
fmt.Println()
|
||||
fmt.Println("**STARTUP PROTOCOL**: You are the Mayor. Please:")
|
||||
fmt.Println("1. Announce: \"Mayor, checking in.\"")
|
||||
fmt.Println("2. Check mail: `gt mail inbox`")
|
||||
fmt.Println("3. If there's a 🤝 HANDOFF message, read it and summarize")
|
||||
fmt.Println("4. If no mail, await user instruction")
|
||||
case RolePolecat:
|
||||
fmt.Println()
|
||||
fmt.Println("---")
|
||||
fmt.Println()
|
||||
fmt.Println("**STARTUP PROTOCOL**: You are a polecat. Please:")
|
||||
fmt.Println("1. Check mail: `gt mail inbox`")
|
||||
fmt.Println("2. If assigned work, begin immediately")
|
||||
fmt.Println("3. If no work, announce ready and await assignment")
|
||||
}
|
||||
}
|
||||
|
||||
// runMailCheckInject runs `gt mail check --inject` and outputs the result.
|
||||
// This injects any pending mail into the agent's context.
|
||||
func runMailCheckInject(workDir string) {
|
||||
|
||||
Reference in New Issue
Block a user