From 7ba2ed27eead40cb54f3a7c2baaac5084cec4e94 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Lionel=20Gibern=C3=A9?= Date: Fri, 4 Sep 2026 14:07:27 +0200 Subject: [PATCH] docs: reorder the README around what it is for MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The old order asked the reader to earn the pitch. Three sections in, before a single example of `gwt add`, came twenty-six lines on oh-my-zsh alias conflicts and PATH ordering — a wall at the entrance. The one thing no competing tool does, per-worktree colour, sat at line 372 of 466, four fifths of the way down and with no picture. Reordered so that what earns attention comes first, what reassures comes next, and what troubleshoots comes last: - the pitch names the gap it fills, against `git worktree add` rather than against another tool - the screenshot sits under it, two windows and two colours - commands, then configuration, then shell integration - `gwt doctor` moves under Troubleshooting, where it belongs - Development and Releasing move to the end under 'For maintainers': a user of the package has no use for how it gets published Usage keeps the warning the old order carried by accident: `gwt` needs the shell integration, and without it oh-my-zsh answers instead. Six lines and a link rather than a section. The image is referenced by absolute URL. npmjs.com renders this README too, and `files` does not ship docs/, so a relative path would render broken there. --- README.md | 202 +++++++++++++++++++++++++++++------------------------- 1 file changed, 109 insertions(+), 93 deletions(-) diff --git a/README.md b/README.md index 02371fe..caa21a4 100644 --- a/README.md +++ b/README.md @@ -1,8 +1,16 @@ # git-wtree -> Git worktree manager with .env syncing and IDE integration +> Worktrees that are ready to work in. -Streamline your git worktree workflow: create isolated branches, sync environment files, install dependencies, give each worktree its own editor color, and — with `--open` — launch your IDE, all in one command. +**`git worktree add` gives you an empty directory. `gwt add` gives you a working +one** — your `.env` files copied, your dependencies installed, and its own colour in +VS Code so you can tell your windows apart. + +![Two VS Code windows, one with a slate title bar and one amber, each showing its +own worktree and branch](https://raw.githubusercontent.com/liogi/git-wtree/main/docs/worktree-colours.png) + +The colour comes from the branch name, so the same branch always looks the same. +Nothing to configure, and nothing to pick. ## Install @@ -13,38 +21,16 @@ npm install -g git-wtree ## Usage ```bash -gitwtree -# or -gwt -``` - -## Shell integration (recommended) - -Run this once — it enables `gwt switch` (jumping between worktrees) and, on zsh + oh-my-zsh, frees the `gwt` name from the git plugin's alias: - -```bash -gitwtree shell-init --install -``` - -It detects your shell, writes three lines to your rc (`~/.zshrc`, `~/.bashrc`, or -`~/.config/fish/config.fish`) and the wrapper itself to -`~/.config/git-wtree/init.`. Then **open a new terminal**. - -**You should only ever need to run this once.** The rc line is a loader — the same shape nvm and -bun use — so upgrading git-wtree never touches it. When a new version changes the wrapper, the -next `gwt` command rewrites it and the next terminal picks it up. - -> **Why `gitwtree` and not `gwt`?** oh-my-zsh's git plugin aliases `gwt` (and `gwta`, `gwtls`, …) to `git worktree`, which shadows this CLI. `gitwtree` is never aliased, so it always works; the block it installs clears those aliases and defines a `gwt` function that wins. If `gwt` runs `git worktree`, you haven't run the integration yet — run `gitwtree shell-init --install`, or use `gitwtree` directly. - -**Manual alternative.** If you'd rather not let a command edit your rc, append the block yourself (put it **after** any PATH setup, e.g. nvm/fnm, so `gitwtree` resolves) and open a new terminal: - -```bash -gitwtree shell-init zsh >> ~/.zshrc # or: bash | fish +gitwtree add my-feature # always works +gwt add my-feature # the same, shorter ``` -That prints the loader and writes the wrapper file, so it is `--install` minus the rc edit. Neither form calls `gitwtree` at shell startup, so both are robust regardless of where your PATH is configured. To remove everything later: `gitwtree shell-init --uninstall`. +`gitwtree` is the name nothing else claims. `gwt` is the same command plus +`gwt switch`, and needs the one-time +[shell integration](#shell-integration-recommended) — which also frees the name +from oh-my-zsh's git plugin, where `gwt` is an alias for `git worktree`. -### Commands +## Commands | Command | Description | | ----------------------------------- | ------------------------------------------------------------- | @@ -176,28 +162,6 @@ Removing the worktree you are standing in returns you to the main worktree rathe `query` is a substring match on the branch name. If it matches exactly one worktree you go straight there; if it's ambiguous or omitted, you get an arrow-key picker (same style as the rest of the prompts). (`gwt path [query]` is the underlying primitive the wrapper calls — it resolves the worktree and writes the path back to the wrapper.) -### `gwt doctor` - -Checks the install: `git` availability, the `gitwtree` version, and whether the shell-integration block is present in your rc (and whether its version matches — if not, it tells you to re-run `gitwtree shell-init --install`). - -```bash -gwt doctor -``` - -It answers two separate questions, and the second is the one that usually matters: - -1. **Is the block written to your rc?** — read from the file. -2. **Is it active in *this* shell?** — the block exports `GWT_SHELL_INTEGRATION`, which every command it launches inherits. - -A block that is installed but never sourced, or shadowed by oh-my-zsh's `gwt` alias, looks exactly like a missing one from the outside. `doctor` tells them apart: - -``` -◆ Shell integration installed in ~/.zshrc (v1.2.3) -▲ Installed, but not active in this shell — GWT_SHELL_INTEGRATION is unset. - Either you haven't opened a new terminal since installing, or something - (oh-my-zsh's git plugin aliases gwt) is shadowing it. -``` - ### `gwt prune` — clean up finished work The problem the tool creates by working well: after a few months you have a dozen @@ -247,6 +211,29 @@ run before each removal, subject to the same `gwt trust` approval. branch discards history. `gwt rm` asks you about the second one at a time — a bulk command is the wrong place to decide it for you. +### How the colours work + +To make parallel windows easy to tell apart, `gwt add` gives each worktree its own visual identity, and `gwt open` re-applies it — so a worktree created with a bare `git worktree add` gets colored too: + +- A **deterministic color**, derived from the branch name, is applied to the VS Code / Cursor title bar and activity bar, plus a worktree-aware `window.title`. Written to the worktree's `.vscode/settings.json` and merged into any existing settings without dropping your keys or comments. +- A **branch statusline** is written to `.claude/settings.local.json` so each Claude Code session shows its branch. +- `"workbench.experimental.modernUI": false` is pinned in the same file. VS Code's Modern UI experiment paints workbench `.part` backgrounds `transparent !important`, which silently nullifies the colors above ([microsoft/vscode#326126](https://github.com/microsoft/vscode/issues/326126)). It ships as a staged rollout, so it can switch on without you changing a setting. Pinning it per worktree keeps the colors working without touching your global settings. + +Colours come from the branch name alone, so the same branch always looks the same +and no two machines disagree. Hue, lightness and saturation all vary, which keeps +four open worktrees visually distinct about thirteen times in fourteen. The flip +side of deriving from the name is that colours cannot be coordinated: if two ever +do land close, renaming one branch separates them. + +Both files are kept out of `git status` automatically — `skip-worktree` when the file is tracked, the worktree's local `info/exclude` otherwise. Your shared `.gitignore` is never touched. + +Toggle either feature (both on by default): + +```bash +gwt config theme off # disable color + window title +gwt config statusline off # disable the Claude statusline +``` + ### `.env` syncing By default, `gwt add` recursively scans the repo for `.env*` files (excluding `node_modules`, `.git`, `dist`, etc.) and copies them into the new worktree. @@ -369,30 +356,83 @@ gwt rm my-feature gwt rm my-feature --force ``` -### Worktree theming +## Worktree location -To make parallel windows easy to tell apart, `gwt add` gives each worktree its own visual identity, and `gwt open` re-applies it — so a worktree created with a bare `git worktree add` gets colored too: +Worktrees are created as siblings of your repo directory: -- A **deterministic color**, derived from the branch name, is applied to the VS Code / Cursor title bar and activity bar, plus a worktree-aware `window.title`. Written to the worktree's `.vscode/settings.json` and merged into any existing settings without dropping your keys or comments. -- A **branch statusline** is written to `.claude/settings.local.json` so each Claude Code session shows its branch. -- `"workbench.experimental.modernUI": false` is pinned in the same file. VS Code's Modern UI experiment paints workbench `.part` backgrounds `transparent !important`, which silently nullifies the colors above ([microsoft/vscode#326126](https://github.com/microsoft/vscode/issues/326126)). It ships as a staged rollout, so it can switch on without you changing a setting. Pinning it per worktree keeps the colors working without touching your global settings. +``` +~/projects/ + myrepo/ ← main repo + myrepo-my-feature ← worktree created by gwt +``` -Colours come from the branch name alone, so the same branch always looks the same -and no two machines disagree. Hue, lightness and saturation all vary, which keeps -four open worktrees visually distinct about thirteen times in fourteen. The flip -side of deriving from the name is that colours cannot be coordinated: if two ever -do land close, renaming one branch separates them. +## Shell integration (recommended) -Both files are kept out of `git status` automatically — `skip-worktree` when the file is tracked, the worktree's local `info/exclude` otherwise. Your shared `.gitignore` is never touched. +Run this once — it enables `gwt switch` (jumping between worktrees) and, on zsh + oh-my-zsh, frees the `gwt` name from the git plugin's alias: -Toggle either feature (both on by default): +```bash +gitwtree shell-init --install +``` + +It detects your shell, writes three lines to your rc (`~/.zshrc`, `~/.bashrc`, or +`~/.config/fish/config.fish`) and the wrapper itself to +`~/.config/git-wtree/init.`. Then **open a new terminal**. + +**You should only ever need to run this once.** The rc line is a loader — the same shape nvm and +bun use — so upgrading git-wtree never touches it. When a new version changes the wrapper, the +next `gwt` command rewrites it and the next terminal picks it up. + +> **Why `gitwtree` and not `gwt`?** oh-my-zsh's git plugin aliases `gwt` (and `gwta`, `gwtls`, …) to `git worktree`, which shadows this CLI. `gitwtree` is never aliased, so it always works; the block it installs clears those aliases and defines a `gwt` function that wins. If `gwt` runs `git worktree`, you haven't run the integration yet — run `gitwtree shell-init --install`, or use `gitwtree` directly. + +**Manual alternative.** If you'd rather not let a command edit your rc, append the block yourself (put it **after** any PATH setup, e.g. nvm/fnm, so `gitwtree` resolves) and open a new terminal: ```bash -gwt config theme off # disable color + window title -gwt config statusline off # disable the Claude statusline +gitwtree shell-init zsh >> ~/.zshrc # or: bash | fish +``` + +That prints the loader and writes the wrapper file, so it is `--install` minus the rc edit. Neither form calls `gitwtree` at shell startup, so both are robust regardless of where your PATH is configured. To remove everything later: `gitwtree shell-init --uninstall`. + +## Troubleshooting + +### `gwt doctor` + +Checks the install: `git` availability, the `gitwtree` version, and whether the shell-integration block is present in your rc (and whether its version matches — if not, it tells you to re-run `gitwtree shell-init --install`). + +```bash +gwt doctor +``` + +It answers two separate questions, and the second is the one that usually matters: + +1. **Is the block written to your rc?** — read from the file. +2. **Is it active in *this* shell?** — the block exports `GWT_SHELL_INTEGRATION`, which every command it launches inherits. + +A block that is installed but never sourced, or shadowed by oh-my-zsh's `gwt` alias, looks exactly like a missing one from the outside. `doctor` tells them apart: + +``` +◆ Shell integration installed in ~/.zshrc (v1.2.3) +▲ Installed, but not active in this shell — GWT_SHELL_INTEGRATION is unset. + Either you haven't opened a new terminal since installing, or something + (oh-my-zsh's git plugin aliases gwt) is shadowing it. ``` -## Development +## Supported IDEs + +VS Code, Cursor, Zed, WebStorm, IntelliJ IDEA, PyCharm, GoLand, Vim, Neovim, Sublime Text — or any custom IDE via the "Other" option in the wizard. + +## Requirements + +- Node.js >= 22.12 +- Git >= 2.5 +- `gitwtree` on your `PATH`. `npm install -g` handles this normally. If you use a **lazy-loaded nvm** (or similar), make sure your global npm bin directory is exported on shell startup — otherwise `gitwtree`/`gwt` won't resolve in a new shell. git-wtree assumes it's runnable; it deliberately doesn't touch your `PATH`. + +## License + +MIT + +## For maintainers + +### Development ```bash npm test # builds, type-checks the tests, runs them @@ -408,17 +448,7 @@ cannot execute a shell command, an unapproved `.gitwtree.json` cannot run its commands, `gwt add` cannot discard unpushed commits, and `shellQuote` round-trips every metacharacter a git refname allows. -## Worktree location - -Worktrees are created as siblings of your repo directory: - -``` -~/projects/ - myrepo/ ← main repo - myrepo-my-feature ← worktree created by gwt -``` - -## Releasing +### Releasing Ask Claude Code for `/release patch` (or `minor`, `major`). It checks the tree, bumps the version, reads the pull requests merged since the last tag, writes the @@ -456,17 +486,3 @@ npm stage approve # asks for 2FA Provenance is attached automatically, so npmjs.com shows which commit and which workflow produced the tarball. - -## Supported IDEs - -VS Code, Cursor, Zed, WebStorm, IntelliJ IDEA, PyCharm, GoLand, Vim, Neovim, Sublime Text — or any custom IDE via the "Other" option in the wizard. - -## Requirements - -- Node.js >= 22.12 -- Git >= 2.5 -- `gitwtree` on your `PATH`. `npm install -g` handles this normally. If you use a **lazy-loaded nvm** (or similar), make sure your global npm bin directory is exported on shell startup — otherwise `gitwtree`/`gwt` won't resolve in a new shell. git-wtree assumes it's runnable; it deliberately doesn't touch your `PATH`. - -## License - -MIT