From b4a90ead723028032db645d44f45cfd9ecd6cea8 Mon Sep 17 00:00:00 2001 From: Steve Yegge Date: Thu, 25 Dec 2025 13:41:49 -0800 Subject: [PATCH] feat: Add gt crew start command as alias for gt start crew MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Users naturally expect "gt crew start " to work alongside "gt start crew ". This adds the alias, handling all input formats: "name", "rig/name", and "rig/crew/name". 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude Opus 4.5 --- internal/cmd/crew.go | 24 ++++++++++++++++++++++++ internal/cmd/crew_lifecycle.go | 21 +++++++++++++++++++++ 2 files changed, 45 insertions(+) diff --git a/internal/cmd/crew.go b/internal/cmd/crew.go index bcb6408f..2b8eb2e5 100644 --- a/internal/cmd/crew.go +++ b/internal/cmd/crew.go @@ -30,6 +30,7 @@ Unlike polecats which are witness-managed and transient, crew workers are: - Tmux optional: Can work in terminal directly Commands: + gt crew start Start a crew workspace (creates if needed) gt crew add Create a new crew workspace gt crew list List crew workspaces with status gt crew at Attach to crew workspace session @@ -211,6 +212,25 @@ var crewPrevCmd = &cobra.Command{ RunE: runCrewPrev, } +var crewStartCmd = &cobra.Command{ + Use: "start ", + Short: "Start a crew workspace (creates if needed)", + Long: `Start a crew workspace, creating it if it doesn't exist. + +This is an alias for 'gt start crew'. It combines 'gt crew add' and 'gt crew at --detached'. +The crew session starts in the background with Claude running and ready. + +The name can include the rig in slash format (e.g., gastown/joe). +If not specified, the rig is inferred from the current directory. + +Examples: + gt crew start joe # Start joe in current rig + gt crew start gastown/joe # Start joe in gastown rig + gt crew start joe --rig beads # Start joe in beads rig`, + Args: cobra.ExactArgs(1), + RunE: runCrewStart, +} + func init() { // Add flags crewAddCmd.Flags().StringVar(&crewRig, "rig", "", "Rig to create crew workspace in") @@ -240,6 +260,9 @@ func init() { crewRestartCmd.Flags().StringVar(&crewRig, "rig", "", "Rig to use") + crewStartCmd.Flags().StringVar(&crewRig, "rig", "", "Rig to use") + crewStartCmd.Flags().StringVar(&crewAccount, "account", "", "Claude Code account handle to use") + // Add subcommands crewCmd.AddCommand(crewAddCmd) crewCmd.AddCommand(crewListCmd) @@ -252,6 +275,7 @@ func init() { crewCmd.AddCommand(crewRestartCmd) crewCmd.AddCommand(crewNextCmd) crewCmd.AddCommand(crewPrevCmd) + crewCmd.AddCommand(crewStartCmd) rootCmd.AddCommand(crewCmd) } diff --git a/internal/cmd/crew_lifecycle.go b/internal/cmd/crew_lifecycle.go index c8dd68d8..f6bef9b0 100644 --- a/internal/cmd/crew_lifecycle.go +++ b/internal/cmd/crew_lifecycle.go @@ -4,6 +4,7 @@ import ( "fmt" "os" "path/filepath" + "strings" "time" "github.com/spf13/cobra" @@ -155,6 +156,26 @@ func runCrewRefresh(cmd *cobra.Command, args []string) error { return nil } +// runCrewStart is an alias for runStartCrew, handling multiple input formats. +// It supports: "name", "rig/name", and "rig/crew/name" formats. +func runCrewStart(cmd *cobra.Command, args []string) error { + name := args[0] + + // Handle rig/crew/name format (e.g., "gastown/crew/joe" -> "gastown/joe") + if strings.Contains(name, "/crew/") { + parts := strings.SplitN(name, "/crew/", 2) + if len(parts) == 2 && parts[0] != "" && parts[1] != "" { + name = parts[0] + "/" + parts[1] + } + } + + // Set the start.go flags from crew.go flags before calling + startCrewRig = crewRig + startCrewAccount = crewAccount + + return runStartCrew(cmd, []string{name}) +} + func runCrewRestart(cmd *cobra.Command, args []string) error { name := args[0] // Parse rig/name format (e.g., "beads/emma" -> rig=beads, name=emma)