npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

worktree-swap-cli

v1.10.1

Published

Run N feature branches in parallel git worktrees while one main checkout runs the dev servers; swap a worktree's files into the main checkout on demand.

Readme

worktree-swap-cli

Run several feature branches in parallel, each in its own git worktree, while only one heavy dev-server process runs — in your main checkout, which acts as a "testbase". worktree apply <name> swaps a feature worktree's files into the main checkout so your already-running dev/watch servers pick up the change (hot reload), without restarting anything or touching git branches.

Install

npm install -g worktree-swap-cli

Installs the worktree command (and a trimmed wt alias — same binary, either name works). Requires git and rsync on PATH (both ship with macOS and most Linux distros). If the code CLI (VS Code) is on PATH, worktree create opens each new worktree in VS Code automatically — skipped silently if it isn't installed.

Setup

Run these from your main checkout (e.g. ~/code/myapp). Sibling worktrees are created next to it as ../myapp-<name>.

myapp/            <- main checkout, runs npm run dev, stays put
myapp-feat-1/     <- worktree, branch "feat-1"
myapp-feat-2/     <- worktree, branch "feat-2"

Commands

worktree create <name> [from-branch] [--carry-changes] [--staged | --unstaged]
                          create ../<repo>-<name> worktree + branch <name>,
                          based on [from-branch] (default: repo's default branch);
                          --carry-changes moves main's current uncommitted changes into it
                          (--staged/--unstaged narrow which; require --carry-changes)
worktree apply <name>    load <name>'s files into the main checkout
worktree copy <from> <to> [--staged | --unstaged]
                          move uncommitted changes from one worktree to another
worktree status          show which worktree is currently loaded
worktree list            wraps `git worktree list`
worktree remove <name>   remove the worktree and delete its branch
worktree reset           unload any applied worktree, restore main to its own HEAD

How apply works

  1. If the main checkout currently holds another worktree's content (tracked via a .active-worktree marker file), that worktree's files are rsynced back into its own directory first — preserving any uncommitted changes there. Nothing is auto-committed.
  2. <name>'s worktree files are rsynced into the main checkout, deleting anything not present in <name> (excludes .git, node_modules, .env, .codegraph).
  3. Your dev-watch process in the main checkout detects the file changes and hot-reloads.
  4. The .active-worktree marker is updated to <name>.

Gitignored files on create

git worktree add never copies untracked/gitignored files. worktree create backfills two things from the main checkout: node_modules is symlinked (one shared install), and every CLAUDE.md file — at any depth — plus .env is copied in by name (via a targeted git ls-files pathspec, not a full gitignored-file scan — that was tried and reverted for being slow on repos with large ignored build directories). Nothing else gitignored is carried automatically.

.codegraph

codegraph keeps a per-directory, gitignored index (.codegraph/). Since git worktree add never copies untracked files, a fresh worktree starts without one — and since it's gitignored, apply/reset never touch it either, so each worktree (and the main checkout) keeps its own independent index, never shared, overwritten, or deleted by this tool.

If the codegraph CLI is on PATH, worktree create builds that index automatically with codegraph init. Skipped silently if codegraph isn't installed. No symlinking is used — each worktree gets its own real index.

Moving uncommitted changes with copy

worktree copy feat-1 feat-2               # move all uncommitted changes
worktree copy feat-1 feat-2 --staged      # move only staged changes
worktree copy feat-1 feat-2 --unstaged    # move only unstaged changes (incl. untracked)

Reads git status in <from>, copies the matching files into <to>, then reverts those same files in <from> (restored from HEAD, or deleted if they were new/untracked). It's a move — after running, the changes exist only in <to>. Nothing is committed on either side.

Unloading a worktree with reset

apply never changes the main checkout's branch — only its working-tree files. worktree reset unloads whatever's currently applied, in one of two modes:

worktree reset                          # soft: carry back, clear marker, keep main's files as-is
worktree reset --force                  # hard: soft reset, then also wipe main back to its own branch HEAD
worktree reset --no-carry-back          # skip the copy-back step
worktree reset --force --no-carry-back  # discard current changes for good — not saved anywhere

Both modes carry the main checkout's current files back into the previously loaded worktree's directory first — nothing is lost — unless you pass --no-carry-back to skip that copy. Combined with --force, --no-carry-back permanently deletes the current changes.

  • Soft (no flag): after this, the same changes exist in both the worktree directory and the main checkout. Use this when you just want to stop tracking a worktree as "applied" without touching what's currently on disk in the main checkout.
  • Hard (--force): additionally runs git checkout -- . and git clean -fd (excluding node_modules/.env) to restore the main checkout to a clean copy of its own branch. Safe because the carry-back already happened first.

Rules this tool follows

  • The main checkout's git branch (HEAD) never changes during apply — only its working-tree files are overwritten. git status afterwards will show the applied worktree's diff against whatever branch the main checkout is on. This is intentional.
  • Nothing is ever auto-committed. Uncommitted changes only ever move between directories via rsync, left uncommitted for you to review.
  • The very first apply has no prior marker. If the main checkout has uncommitted changes at that point, the command refuses to run — commit/stash first, or pass --force.
  • If the target worktree's package.json differs from what's currently loaded, the tool prints a reminder to run npm install and restart your dev servers — this is not automatic.
  • worktree remove never touches the main checkout itself.
  • .active-worktree is auto-added to the main checkout's .gitignore.

Configuration

By default the "main checkout" is the git toplevel of your current directory. Override with:

WORKTREE_MAIN_ROOT=/path/to/main/checkout worktree apply feat-1