Skip to content

tatum/wt

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

8 Commits
 
 
 
 
 
 
 
 

Repository files navigation

wt - Git Worktree Manager

A simple shell script for managing git worktrees, designed for agentic coding workflows where multiple agents work on different branches simultaneously.

Features

  • Create worktrees in a sibling directory (../<repo>-worktrees/)
  • List all worktrees with dirty state indicators
  • View git status across all worktrees at once
  • Safe removal with uncommitted change warnings
  • Prune worktrees for merged branches
  • Shell integration for seamless directory navigation
  • Tab completion for bash and zsh
  • .worktreeinclude support to copy untracked files (.env, config, etc.) into new worktrees

Installation

1. Install the script

Copy wt to a directory in your PATH:

# Option A: User-local install
mkdir -p ~/.local/bin
cp wt ~/.local/bin/
chmod +x ~/.local/bin/wt

# Option B: System-wide install
sudo cp wt /usr/local/bin/
sudo chmod +x /usr/local/bin/wt

Make sure ~/.local/bin is in your PATH. Add this to your ~/.zshrc if needed:

export PATH="$HOME/.local/bin:$PATH"

2. Add shell integration

The wt cd command needs a shell function wrapper to actually change directories. Add this to your ~/.zshrc (or ~/.bashrc for bash):

# Git worktree manager
wt() {
  if [[ "$1" == "cd" && -n "$2" ]]; then
    local dir
    dir="$(command wt cd "$2")" && cd "$dir"
  else
    command wt "$@"
  fi
}

3. Enable tab completion (optional)

Tab completion lets you autocomplete worktree names when using wt cd or wt remove.

Bash - add to ~/.bashrc:

eval "$(wt completions bash)"

Zsh - add to ~/.zshrc:

eval "$(wt completions zsh)"

4. Reload your shell

source ~/.zshrc  # or: source ~/.bashrc

Now you can use tab completion:

wt cd <TAB>        # Lists available worktrees
wt remove <TAB>    # Lists available worktrees
wt new feature <TAB>  # Lists branches for base branch

5. Prompt customization (optional)

Show the current worktree in your prompt with a dirty indicator:

# Show "project (worktree)*" in worktree, or just current dir name otherwise
wt_prompt() {
    local git_root wt_name repo_name dirty=""

    git_root="$(git rev-parse --show-toplevel 2>/dev/null)"

    if [[ "$git_root" == *-worktrees/* ]]; then
        wt_name="$(basename "$git_root")"
        repo_name="$(basename "$(dirname "$git_root")" | sed 's/-worktrees$//')"
        [[ -n "$(git status --porcelain 2>/dev/null)" ]] && dirty="*"
        echo "${repo_name} (${wt_name})${dirty}"
    else
        echo "${PWD##*/}"
    fi
}

Then use it in your prompt (zsh):

setopt PROMPT_SUBST
PROMPT='$(wt_prompt) $ '

Example output:

myproject (feature-auth)   # clean worktree
myproject (feature-auth)*  # dirty worktree
Documents                  # not in a worktree

Usage

Create a new worktree

wt new feature-auth          # Branch from main/master
wt new bugfix-123 develop    # Branch from develop

This creates:

  • A new branch named feature-auth
  • A worktree at ../<repo>-worktrees/feature-auth/
  • Copies any files matching .worktreeinclude patterns (see below)

List worktrees

wt list    # or: wt ls

Shows all worktrees with their branches, paths, and dirty status.

Check status across all worktrees

wt status    # or: wt st

Displays git status --short output for every worktree.

Navigate to a worktree

wt cd feature-auth

Changes your current directory to that worktree (requires shell integration).

Remove a worktree

wt remove feature-auth       # or: wt rm feature-auth
wt remove feature-auth -f    # Force remove with uncommitted changes

You'll be prompted to delete the associated branch.

Clean up merged worktrees

wt prune            # Remove worktrees with merged branches
wt prune --dry-run  # Preview what would be removed

.worktreeinclude

When creating a new worktree, you often need untracked files like .env or local config that aren't in source control. Place a .worktreeinclude file in your repo root to automatically copy these files into new worktrees.

The file uses .gitignore syntax — glob patterns, directory patterns, negation (!), and comments (#) all work:

# Environment files
.env
.env.local

# Local IDE/tool config
.claude/settings.local.json
.vscode/settings.json

# Everything in a directory
secrets/

When you run wt new, any untracked files matching these patterns are copied from the main repo into the new worktree, preserving directory structure. Tracked files are skipped since git already includes them.

Directory Structure

When you use wt in a repository, worktrees are created in a sibling directory:

~/code/
|-- myproject/                    # Your main repository
|   |-- .git/
|   +-- ...
+-- myproject-worktrees/          # Worktrees directory (auto-created)
    |-- feature-auth/             # Worktree 1
    |-- feature-api/              # Worktree 2
    +-- bugfix-123/               # Worktree 3

Agentic Coding Workflow

This tool is designed for workflows where multiple AI agents work on different features simultaneously:

  1. Spin up a worktree per agent:

    wt new agent-1-auth
    wt new agent-2-api
    wt new agent-3-tests
  2. Each agent works in isolation - no merge conflicts or interference

  3. Monitor progress:

    wt status    # See what each agent has changed
  4. Clean up when done:

    wt prune     # Remove merged worktrees

Command Reference

Command Alias Description
wt new <name> [base] Create worktree with new branch
wt list wt ls List all worktrees
wt status wt st Status across all worktrees
wt cd <name> Navigate to worktree
wt remove <name> wt rm Remove worktree
wt prune Remove merged worktrees
wt completions [shell] Output shell completion script (bash/zsh)
wt help Show help
wt version Show version

License

MIT

About

No description, website, or topics provided.

Resources

Stars

Watchers

Forks

Releases

Packages

Contributors

Languages