split

package
v0.17.14 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: May 11, 2026 License: MIT Imports: 18 Imported by: 0

Documentation

Overview

Package split provides functionality for splitting stacked branches.

Index

Constants

This section is empty.

Variables

This section is empty.

Functions

func Action

func Action(ctx *app.Context, opts Options, handler Handler) error

Action performs the split operation

func RunWizard

func RunWizard(ctx *app.Context, handler InteractiveHandler, opts WizardOptions) error

RunWizard executes the interactive split wizard. It guides the user through selecting split type, direction, and then executes the appropriate split operation.

Types

type ActionResult

type ActionResult struct {
	OriginalBranch string
	NewBranches    []string
	Style          Style
}

ActionResult contains the result of the split action for the handler

type CommitMessageContext

type CommitMessageContext struct {
	// Files being extracted to the new branch
	Files []string
	// Direction of the split (above = child, below = parent)
	Direction Direction
	// CurrentBranch is the name of the branch being split
	CurrentBranch string
	// OriginalCommitMessage is the full message of the first commit on the branch
	// (title + body). Used as the basis for the split commit message.
	OriginalCommitMessage string
}

CommitMessageContext provides context for commit message prompting

type Direction

type Direction string

Direction specifies where the new branch should be placed relative to the current branch

const (
	// DirectionBelow creates a new branch between current and parent (downstack).
	// This is the current/default behavior: the new branch becomes the parent of
	// the current branch.
	DirectionBelow Direction = "below"

	// DirectionAbove creates a new branch as a child of current (upstack).
	// The new branch becomes a child of the current branch, and any existing
	// children of current become children of the new branch.
	DirectionAbove Direction = "above"
)

func (Direction) String

func (d Direction) String() string

String returns the string representation of the direction

type DirectionContext

type DirectionContext struct {
	Engine        engine.BranchReader
	CurrentBranch string
	ParentBranch  string
	Children      []string
}

DirectionContext provides context for the direction selection prompt

type Handler

type Handler interface {
	// Start is called at the beginning of split
	Start(branchName string, style Style)

	// OnStep is called for each step in the split process
	OnStep(step Step, status handler.StepStatus, message string)

	// OnBranchCreated is called when a new branch is created during split
	OnBranchCreated(branchName string)

	// Complete is called when split finishes
	Complete(result ActionResult)

	// Cleanup restores terminal state (may be no-op)
	Cleanup()

	// IsInteractive returns true if the handler supports interactive prompts
	IsInteractive() bool
}

Handler receives events from split action

type InteractiveHandler

type InteractiveHandler interface {
	Handler

	// IsInteractive returns true if this handler supports interactive prompts.
	// Non-interactive handlers return false, and their prompt methods will return errors.
	IsInteractive() bool

	// PromptSplitType asks the user to choose between available split types.
	// availableTypes contains the choices with their availability status.
	// Returns the selected Style or an error if canceled.
	PromptSplitType(availableTypes []TypeChoice) (Style, error)

	// PromptDirection asks the user where to place the new branch.
	// Returns the selected Direction or an error if canceled.
	PromptDirection(ctx DirectionContext) (Direction, error)

	// ShowHunkSummary displays a summary of the remaining changes before staging.
	// This is informational only, no user input required.
	ShowHunkSummary(diff string)

	// PromptCommitMessage asks the user to enter or edit a commit message.
	// defaultMsg is the suggested default (e.g., from original commit).
	// Returns the final message or an error if canceled.
	PromptCommitMessage(defaultMsg string) (string, error)

	// PromptCommitMessageWithContext asks the user to enter a commit message
	// with full context about the split operation displayed.
	// The context includes files being extracted, direction, and current branch.
	// Returns the commit message or an error if canceled.
	PromptCommitMessageWithContext(ctx CommitMessageContext) (string, error)

	// PromptBranchName asks the user to enter a branch name.
	// defaultName is the auto-generated suggestion.
	// sessionNames contains names already used in this split session.
	// allBranchNames contains all existing branch names in the repo (for O(1) lookup).
	// originalBranchName is the name of the branch being split (allowed to reuse).
	// Returns the final name or an error if canceled.
	PromptBranchName(defaultName string, sessionNames []string, allBranchNames *engine.BranchSet, originalBranchName string) (string, error)

	// PromptContinueOrCancel asks user whether to continue after no changes were staged.
	// Returns true to try again, false to cancel.
	PromptContinueOrCancel() (bool, error)

	// PromptEditCommitMessage asks whether the user wants to edit the commit message.
	// Returns true if user wants to edit.
	PromptEditCommitMessage() (bool, error)

	// PromptSelectHunks displays the hunk selector TUI and returns selected hunks.
	// Returns the hunks that the user selected, or an error if canceled.
	PromptSelectHunks(hunks []git.Hunk) ([]git.Hunk, error)
}

InteractiveHandler extends Handler with interactive prompt capabilities. This allows the action layer to request user input without depending on specific UI implementations (TUI, CLI, etc.).

Error handling: Prompt methods should return sterrors.ErrCanceled when the user cancels (e.g., Ctrl+C, Escape). Other errors indicate actual failures.

type NullHandler

type NullHandler struct {
	handler.NullBase
	handler.NullProgress[Step]
}

NullHandler is a no-op handler for when nil is passed. It embeds handler.NullBase for Cleanup() and IsInteractive().

func (*NullHandler) Complete

func (h *NullHandler) Complete(ActionResult)

Complete implements Handler.

func (*NullHandler) OnBranchCreated

func (h *NullHandler) OnBranchCreated(string)

OnBranchCreated implements Handler.

func (*NullHandler) Start

func (h *NullHandler) Start(string, Style)

Start implements Handler.

type Options

type Options struct {
	Style         Style
	Direction     Direction
	Pathspecs     []string
	BranchPattern config.BranchPattern
	// AsSibling creates split branches as siblings on the same parent instead
	// of creating a linear chain. When true:
	// - StyleFile: Creates sibling branch, original branch unchanged
	// - StyleCommit: All split branches are siblings on the same parent
	// - StyleHunk: All split branches are siblings on the same parent
	AsSibling bool
	// Name specifies a custom name for the split branch (file split only).
	// If empty, auto-generates as "{original}_split".
	Name string
	// Message specifies the commit message for the split operation.
	// Only applies to StyleFile (other styles use existing commit messages).
	Message string
	// UseWizard enables the new wizard-based interactive flow.
	// When true, the wizard will guide through type/direction selection.
	UseWizard bool
	// HunkSelector specifies which hunk selection method to use ("tui" or "git").
	// Only applies to StyleHunk. When "git", uses git add -p instead of the TUI selector.
	HunkSelector string
	// PatchFile specifies a patch file for non-interactive hunk selection.
	// If set, hunks in the patch are staged directly without prompting.
	// Use "-" to read from stdin.
	PatchFile string
	// DryRun shows what would happen without executing the split.
	// When true, the split logic runs but no branches are created or modified.
	DryRun bool
}

Options contains options for the split command

type Result

type Result struct {
	BranchNames  []string // From oldest to newest
	BranchPoints []int    // Commit indices (0 = HEAD, 1 = HEAD~1, etc.)
}

Result contains the result of a split operation

type Step

type Step string

Step represents a step in the split process

const (
	StepValidating        Step = "validating"
	StepSelecting         Step = "selecting"
	StepApplying          Step = "applying"
	StepRestacking        Step = "restacking"
	StepChoosingType      Step = "choosing_type"
	StepChoosingDirection Step = "choosing_direction"
	StepStagingHunks      Step = "staging_hunks"
	StepCommitMessage     Step = "commit_message"
	StepBranchName        Step = "branch_name"
)

Split step constants

type Style

type Style string

Style specifies the split mode

const (
	// StyleCommit splits by selecting commit points
	StyleCommit Style = "commit"
	// StyleHunk splits by interactively staging hunks
	StyleHunk Style = "hunk"
	// StyleFile splits by extracting specified files
	StyleFile Style = "file"
)

type TypeChoice

type TypeChoice struct {
	Style       Style
	Label       string
	Description string
	Available   bool // false if the option is not available (e.g., commit split for single-commit branch)
}

TypeChoice represents an available split type option

type WizardOptions

type WizardOptions struct {
	// Style is pre-selected split style (empty = prompt user)
	Style Style
	// Direction is pre-selected direction (empty = prompt user)
	Direction Direction
	// BranchName is a pre-selected branch name (empty = prompt or auto-generate)
	BranchName string
	// HunkSelector specifies which hunk selection method to use ("tui" or "git")
	HunkSelector string
}

WizardOptions configures the interactive split wizard

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL