Kindra is a CLI tool for managing stacked git branches. Its kin command automates the tedious parts of working with dependent branches, such as rebasing descendants after a commit or moving an entire stack of work to a new base.
-
Stacked Commits: Automatically rebase all descendant branches when you commit in the middle of a stack.
-
Atomic Stack Moves: Move a branch and all its descendants onto a new base branch in one pass using
--update-refs. -
Fork-Aware Reordering: Edit branch parent relationships in your
$EDITOR, including creating or preserving forks. -
Smart Sync: Rebase the current stack onto
main/masterin one pass using--update-refs, while skipping already-landed lower PRs. -
Auto-Restack: Automatically identify and repair "floating" branches that were based on an old version of the current branch (e.g., after an
amendorrebase). -
Interactive Navigation: Quickly hop between branches in your stack with
up,down, andtopcommands. -
Visual Branch Splitting: Assign branches to specific commits in a linear history using your favorite
$EDITOR. -
Atomic Pushes: Push all branches in your stack simultaneously with
force-with-leasesafety. -
Run Commands Across Stack: Execute shell commands on each branch in your stack with
kin run. -
PR Workflow Helpers: Create/update stack PRs with automatic flatten/push preflight, flatten stack PR bases to upstream, open PRs in your browser, edit PR metadata, inspect review/check status, export threaded review comments as markdown, and merge stack PRs with readiness checks.
Kindra can be installed directly from GitHub:
cargo install --git https://github.com/Pajn/kindra.git kindra --bin kinIf you already use cargo-binstall, the git-based install works there too:
cargo binstall --git https://github.com/Pajn/kindra.git kindraYou can also install it from source:
# Clone the repository
git clone https://github.com/Pajn/kindra.git
cd kindra
# Build and install
cargo install --path .- Start a stack: Create several branches, each building on the previous one.
- Make a change: Checkout a branch in the middle of the stack and run
kin commit. - Watch the magic: Kindra will automatically rebase all branches that depend on your change.
- Move the stack: Ready to target a different feature?
kin move --onto mainto relocate the entire stack. - Sync after merges: If lower PRs landed, run
kin syncto rebase the remaining stack onto latestmain. - Reorder the stack: Need to reshuffle or fork branches? Run
kin reorderand edit the parent map in your editor. - Repair broken stacks: Amended a commit and left dependent branches "floating"? Run
kin restackto fix them. - Manage PRs in stack:
kin prto create/update PRs, automatically flattening mismatched PR bases and pushing firstkin pr --no-pushto skip that preflight and use the old create/update behaviorkin pr opento open a PR from the stackkin pr editto edit title/body/labels/reviewerskin pr flattento retarget all open stack PRs to the resolved upstream base branch on GitHubkin pr statusto inspect reviewers, unresolved comments, and failing/running checkskin pr reviewto render PR review threads as markdown, optionally write them to a file, or copy them via OSC 52kin pr mergeto merge a stack PR only when reviews/checks are ready, or clearly explain/prompt when GitHub would still allow an override
- Run across stack:
kin run -c "cargo test"to run tests on each branch in the stack.
For a full list of commands and detailed examples, see the CLI Reference.
kin reorder opens a file with one row per branch:
branch feature-c parent main
branch feature-a
branch feature-b
branch <name> parent <parent>sets the branch parent explicitly.branch <name>means "make the branch on the previous line the parent".- The first row must have an explicit parent, usually your upstream branch.
- Forks are created by repeating the same explicit parent on multiple rows.
Example fork:
branch feature-c parent main
branch feature-a parent feature-c
branch feature-b parent feature-c
Commands that need an upstream/base branch (for example sync, split, push, commit, and move) resolve it in this order:
-
Repository override in
.git/kindra.toml:upstream_branch = "branch-name"
-
git config init.defaultBranch -
Built-in defaults:
main,master,trunk -
Remote fallbacks:
origin/<branch>
Kindra now includes an opinionated kin wt workflow for managed git worktrees:
kin wt mainensures a stable trunk worktree exists.kin wt review [branch]creates or reuses a fixed review worktree and repoints it safely.kin wt temp [branch]creates or reuses a branch-scoped disposable worktree, andkin wt temp -b <new-branch> [start-point]creates a new branch in one.kin wt listshows all Kindra-managed worktrees and their current state.kin wt path <target>prints just the managed path for shell/editor integrations.kin wt remove <target>removes an explicit managed worktree with confirmation by default.kin wt cleanupremoves merged or stale Kindra-managed temp worktrees.
By default Kindra stores managed worktrees under:
.git/kindra-worktrees/
That keeps extra working trees out of the repo root while still making them easy to find and clean up.
# Ensure a persistent trunk worktree exists
kin wt main
# Reuse a stable review workspace for the current branch
kin wt review
# Switch the review workspace to another branch
kin wt review feature/auth
# Create or reuse a temp worktree for a branch
kin wt temp feature/auth
# Create a new temp worktree branch from the current branch
kin wt temp -b feature/spike
# Create a new temp worktree branch from origin/main
kin wt temp -b hotfix/main origin/main
# Use the resolved path in shell tooling
cd "$(kin wt path review)"
# Remove a single managed temp worktree
kin wt remove feature/auth
# Clean up merged temp worktrees
kin wt cleanupManaged worktrees use repo-local config in .git/kindra.toml:
[worktrees]
trunk = "main"
[worktrees.hooks]
on_create = []
on_checkout = []
on_remove = []
[worktrees.main]
path = ".git/kindra-worktrees/main"
[worktrees.review]
path = ".git/kindra-worktrees/review"
[worktrees.temp]
path_template = ".git/kindra-worktrees/temp/{branch}"
delete_merged = trueNotes:
mainis pinned to the configured trunk branch.reviewreuses a fixed path and refuses to discard local changes unless you confirm or pass--force.cleanuponly targets Kindra-managedtempworktrees, nevermainorreview.kin wt pathis the script-friendly command: it prints only the resolved path on success.- Use
branch:<name>withkin wt pathorkin wt removeto target a temp branch literally namedmainorreview. - Hooks run in the managed worktree directory and stop the action if they fail.
kin restack bounds floating-branch discovery by default so very deep repositories do not pay for an unbounded first-parent scan.
Resolution order:
- CLI override:
kin restack --history-limit <n> - Repository config in
.git/kindra.toml - Global config in the standard platform config directory as
kindra/config.toml - Built-in default:
100
Use 0 to disable the bound and scan the full first-parent history.
Example repository config:
[restack]
history_limit = 250Commands that start a Git rebase (commit, move, sync, and restack) default to --no-autostash so dirty tracked changes do not get hidden implicitly.
Resolution order:
- CLI override:
--autostashor--no-autostash - Repository config in
.git/kindra.toml - Global config in the standard platform config directory as
kindra/config.toml - Built-in default:
false
Example config:
[rebase]
autostash = trueRun the permanent Criterion benchmarks for stack navigation (checkout top, co up, co down) across two repository shapes:
- 5,000 commits on
main+ 10,000 noise branches - 50,000 commits on
main+ 1,000 noise branches
cargo bench --bench checkout_topTraditional git workflows often involve large, monolithic Pull Requests or manual, error-prone rebasing when trying to keep multiple small, dependent PRs in sync. Kindra treats your branches as a stack, allowing you to focus on small, reviewable increments of code while it handles the plumbing.