fix(done,mayor): push branch before MR creation, restart runtime on attach
done.go: Push branch to origin BEFORE creating MR bead (hq-6dk53, hq-a4ksk) - The MR bead triggers Refinery to process the branch - If branch isnt pushed, Refinery finds nothing to merge - The worktree gets nuked at end of gt done, losing commits forever - This is why polecats kept submitting MRs with empty branches mayor.go: Restart runtime with context when attaching (hq-95xfq) - When runtime has exited, gt may at now respawns with startup beacon - Previously, attaching to dead session left agent with no context - Now matches gt handoff behavior: hook check, inbox check, full prime Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
This commit is contained in:
@@ -264,6 +264,16 @@ func runDone(cmd *cobra.Command, args []string) error {
|
||||
return fmt.Errorf("branch '%s' has 0 commits ahead of %s; nothing to merge\nMake and commit changes first, or use --status DEFERRED to exit without completing", branch, originDefault)
|
||||
}
|
||||
|
||||
// CRITICAL: Push branch BEFORE creating MR bead (hq-6dk53, hq-a4ksk)
|
||||
// The MR bead triggers Refinery to process this branch. If the branch
|
||||
// isn't pushed yet, Refinery finds nothing to merge. The worktree gets
|
||||
// nuked at the end of gt done, so the commits are lost forever.
|
||||
fmt.Printf("Pushing branch to remote...\n")
|
||||
if err := g.Push("origin", branch, false); err != nil {
|
||||
return fmt.Errorf("pushing branch '%s' to origin: %w\nCommits exist locally but failed to push. Fix the issue and retry.", branch, err)
|
||||
}
|
||||
fmt.Printf("%s Branch pushed to origin\n", style.Bold.Render("✓"))
|
||||
|
||||
if issueID == "" {
|
||||
return fmt.Errorf("cannot determine source issue from branch '%s'; use --issue to specify", branch)
|
||||
}
|
||||
|
||||
@@ -4,8 +4,11 @@ import (
|
||||
"fmt"
|
||||
|
||||
"github.com/spf13/cobra"
|
||||
"github.com/steveyegge/gastown/internal/config"
|
||||
"github.com/steveyegge/gastown/internal/mayor"
|
||||
"github.com/steveyegge/gastown/internal/session"
|
||||
"github.com/steveyegge/gastown/internal/style"
|
||||
"github.com/steveyegge/gastown/internal/tmux"
|
||||
"github.com/steveyegge/gastown/internal/workspace"
|
||||
)
|
||||
|
||||
@@ -142,6 +145,14 @@ func runMayorAttach(cmd *cobra.Command, args []string) error {
|
||||
return err
|
||||
}
|
||||
|
||||
townRoot, err := workspace.FindFromCwdOrError()
|
||||
if err != nil {
|
||||
return fmt.Errorf("finding workspace: %w", err)
|
||||
}
|
||||
|
||||
t := tmux.NewTmux()
|
||||
sessionID := mgr.SessionName()
|
||||
|
||||
running, err := mgr.IsRunning()
|
||||
if err != nil {
|
||||
return fmt.Errorf("checking session: %w", err)
|
||||
@@ -152,10 +163,45 @@ func runMayorAttach(cmd *cobra.Command, args []string) error {
|
||||
if err := mgr.Start(mayorAgentOverride); err != nil {
|
||||
return err
|
||||
}
|
||||
} else {
|
||||
// Session exists - check if runtime is still running (hq-95xfq)
|
||||
// If runtime exited or sitting at shell, restart with proper context
|
||||
agentCfg, _, err := config.ResolveAgentConfigWithOverride(townRoot, townRoot, mayorAgentOverride)
|
||||
if err != nil {
|
||||
return fmt.Errorf("resolving agent: %w", err)
|
||||
}
|
||||
if !t.IsAgentRunning(sessionID, config.ExpectedPaneCommands(agentCfg)...) {
|
||||
// Runtime has exited, restart it with proper context
|
||||
fmt.Println("Runtime exited, restarting with context...")
|
||||
|
||||
paneID, err := t.GetPaneID(sessionID)
|
||||
if err != nil {
|
||||
return fmt.Errorf("getting pane ID: %w", err)
|
||||
}
|
||||
|
||||
// Build startup beacon for context (like gt handoff does)
|
||||
beacon := session.FormatStartupNudge(session.StartupNudgeConfig{
|
||||
Recipient: "mayor",
|
||||
Sender: "human",
|
||||
Topic: "attach",
|
||||
})
|
||||
|
||||
// Build startup command with beacon
|
||||
startupCmd, err := config.BuildAgentStartupCommandWithAgentOverride("mayor", "mayor", "", beacon, mayorAgentOverride)
|
||||
if err != nil {
|
||||
return fmt.Errorf("building startup command: %w", err)
|
||||
}
|
||||
|
||||
if err := t.RespawnPane(paneID, startupCmd); err != nil {
|
||||
return fmt.Errorf("restarting runtime: %w", err)
|
||||
}
|
||||
|
||||
fmt.Printf("%s Mayor restarted with context\n", style.Bold.Render("✓"))
|
||||
}
|
||||
}
|
||||
|
||||
// Use shared attach helper (smart: links if inside tmux, attaches if outside)
|
||||
return attachToTmuxSession(mgr.SessionName())
|
||||
return attachToTmuxSession(sessionID)
|
||||
}
|
||||
|
||||
func runMayorStatus(cmd *cobra.Command, args []string) error {
|
||||
|
||||
Reference in New Issue
Block a user