fix(dog): spawn session when dispatching work to dogs
Some checks failed
CI / Check for .beads changes (push) Has been skipped
CI / Check embedded formulas (push) Successful in 18s
CI / Test (push) Failing after 1m13s
CI / Lint (push) Successful in 21s
CI / Integration Tests (push) Successful in 1m1s
CI / Coverage Report (push) Has been skipped
Windows CI / Windows Build and Unit Tests (push) Has been cancelled
Some checks failed
CI / Check for .beads changes (push) Has been skipped
CI / Check embedded formulas (push) Successful in 18s
CI / Test (push) Failing after 1m13s
CI / Lint (push) Successful in 21s
CI / Integration Tests (push) Successful in 1m1s
CI / Coverage Report (push) Has been skipped
Windows CI / Windows Build and Unit Tests (push) Has been cancelled
Dogs are just directories with state files - they don't have sessions to receive and execute mail. This means `gt dog dispatch --plugin X` would assign work and send mail, but nothing would ever execute. This fix spawns a tmux session for the dog after dispatch, with an initial prompt that tells Claude to check mail and execute the plugin instructions. This makes dog dispatch actually work as intended. The session is named `gt-<town>-deacon-<dogname>` following the pattern from showDogStatus. If session creation fails, we log a warning but don't fail the dispatch (mail was sent, work was assigned, human can manually start the session). Related: mayor guidance to have deacon execute dog work directly. This is a stepping stone - dogs now execute their own work via sessions. Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
This commit is contained in:
@@ -791,6 +791,44 @@ func runDogDispatch(cmd *cobra.Command, args []string) error {
|
||||
return fmt.Errorf("sending plugin mail to dog: %w", err)
|
||||
}
|
||||
|
||||
// Spawn a session for the dog to execute the work.
|
||||
// Without a session, the dog's mail inbox is never checked.
|
||||
// See: https://github.com/steveyegge/gastown/issues/XXX (dog dispatch doesn't execute)
|
||||
t := tmux.NewTmux()
|
||||
townName, err := workspace.GetTownName(townRoot)
|
||||
if err != nil {
|
||||
townName = "gt" // fallback
|
||||
}
|
||||
dogSessionName := fmt.Sprintf("gt-%s-deacon-%s", townName, targetDog.Name)
|
||||
|
||||
// Kill any stale session first
|
||||
if has, _ := t.HasSession(dogSessionName); has {
|
||||
_ = t.KillSessionWithProcesses(dogSessionName)
|
||||
}
|
||||
|
||||
// Build startup command with initial prompt to check mail and execute plugin
|
||||
initialPrompt := fmt.Sprintf("I am dog %s. Check my mail inbox with 'gt mail inbox' and execute the plugin instructions I received.", targetDog.Name)
|
||||
startCmd := config.BuildAgentStartupCommand("dog", "", townRoot, targetDog.Path, initialPrompt)
|
||||
|
||||
// Create session from dog's directory
|
||||
if err := t.NewSessionWithCommand(dogSessionName, targetDog.Path, startCmd); err != nil {
|
||||
if !dogDispatchJSON {
|
||||
fmt.Printf(" Warning: could not spawn dog session: %v\n", err)
|
||||
}
|
||||
// Non-fatal: mail was sent, dog is marked as working, but no session to execute
|
||||
// The deacon or human can manually start the session later
|
||||
} else {
|
||||
// Set environment for the dog session
|
||||
envVars := config.AgentEnv(config.AgentEnvConfig{
|
||||
Role: "dog",
|
||||
AgentName: targetDog.Name,
|
||||
TownRoot: townRoot,
|
||||
})
|
||||
for k, v := range envVars {
|
||||
_ = t.SetEnvironment(dogSessionName, k, v)
|
||||
}
|
||||
}
|
||||
|
||||
// Success - output result
|
||||
if dogDispatchJSON {
|
||||
return json.NewEncoder(os.Stdout).Encode(result)
|
||||
|
||||
Reference in New Issue
Block a user