worktree-manager
Create, manage, and cleanup git worktrees with Claude Code agents across all projects. USE THIS SKILL when user says "create worktree", "spin up worktrees", "new worktree for X", "worktree status", "cleanup worktrees", "sync worktrees", or wants parallel development branches. Also use when creating PRs from a worktree branch (to update registry with PR number). Handles worktree creation, dependency installation, validation, agent launching in Ghostty, and global registry management.
来源信息
- 仓库
- Wirasm/worktree-manager-skill
- 最近来源活动
- 2026年1月7日 11:16
- 检测到的 SKILL.md 语言
- 英语
- 星标
- 139
- 分支
- 32
安装方式
默认使用会先检查来源的 Prompt;你也可以切换为直接命令,或下载本地副本。
检查来源文件
决定是否安装前,请先阅读 SKILL.md,以及 SkillsMP 当前展示的配套文件。
文件资源管理器
10 个文件正在显示 SKILL.md
SKILL.md
来源说明 · 只读预览- name
- worktree-manager
- description
- Create, manage, and cleanup git worktrees with Claude Code agents across all projects. USE THIS SKILL when user says "create worktree", "spin up worktrees", "new worktree for X", "worktree status", "cleanup worktrees", "sync worktrees", or wants parallel development branches. Also use when creating PRs from a worktree branch (to update registry with PR number). Handles worktree creation, dependency installation, validation, agent launching in Ghostty, and global registry management.
# Global Worktree Manager
Manage parallel development across ALL projects using git worktrees with Claude Code agents. Each worktree is an isolated copy of the repo on a different branch, stored centrally at `~/tmp/worktrees/`.
**IMPORTANT**: You (Claude) can perform ALL operations manually using standard tools (jq, git, bash). Scripts are helpers, not requirements. If a script fails, fall back to manual operations described in this document.
## When This Skill Activates
**Trigger phrases:**
- "spin up worktrees for X, Y, Z"
- "create 3 worktrees for features A, B, C"
- "new worktree for feature/auth"
- "what's the status of my worktrees?"
- "show all worktrees" / "show worktrees for this project"
- "clean up merged worktrees"
- "clean up the auth worktree"
- "launch agent in worktree X"
- "sync worktrees" / "sync worktree registry"
- "create PR" (when in a worktree - updates registry with PR number)
---
## File Locations
| File | Purpose |
|------|---------|
| `~/.claude/worktree-registry.json` | **Global registry** - tracks all worktrees across all projects |
| `~/.claude/skills/worktree-manager/config.json` | **Skill config** - terminal, shell, port range settings |
| `~/.claude/skills/worktree-manager/scripts/` | **Helper scripts** - optional, can do everything manually |
| `~/tmp/worktrees/` | **Worktree storage** - all worktrees live here |
| `.claude/worktree.json` (per-project) | **Project config** - optional custom settings |
---
## Core Concepts
### Centralized Worktree Storage
All worktrees live in `~/tmp/worktrees/<project-name>/<branch-slug>/`
```
~/tmp/worktrees/
├── obsidian-ai-agent/
│ ├── feature-auth/ # branch: feature/auth
│ ├── feature-payments/ # branch: feature/payments
│ └── fix-login-bug/ # branch: fix/login-bug
└── another-project/
└── feature-dark-mode/
```
### Branch Slug Convention
Branch names are slugified for filesystem safety by replacing `/` with `-`:
- `feature/auth` → `feature-auth`
- `fix/login-bug` → `fix-login-bug`
- `feat/user-profile` → `feat-user-profile`
**Slugify manually:** `echo "feature/auth" | tr '/' '-'` → `feature-auth`
### Port Allocation Rules
- **Global pool**: 8100-8199 (100 ports total)
- **Per worktree**: 2 ports allocated (for API + frontend patterns)
- **Globally unique**: Ports are tracked globally to avoid conflicts across projects
- **Check before use**: Always verify port isn't in use by system: `lsof -i :<port>`
---
## Global Registry
### Location
`~/.claude/worktree-registry.json`
### Schema
```json
{
"worktrees": [
{
"id": "unique-uuid",
"project": "obsidian-ai-agent",
"repoPath": "/Users/rasmus/Projects/obsidian-ai-agent",
"branch": "feature/auth",
"branchSlug": "feature-auth",
"worktreePath": "/Users/rasmus/tmp/worktrees/obsidian-ai-agent/feature-auth",
"ports": [8100, 8101],
"createdAt": "2025-12-04T10:00:00Z",
"validatedAt": "2025-12-04T10:02:00Z",
"agentLaunchedAt": "2025-12-04T10:03:00Z",
"task": "Implement OAuth login",
"prNumber": null,
"status": "active"
}
],
"portPool": {
"start": 8100,
"end": 8199,
"allocated": [8100, 8101]
}
}
```
### Field Descriptions
**Worktree entry fields:**
| Field | Type | Description |
|-------|------|-------------|
| `id` | string | Unique identifier (UUID) |
| `project` | string | Project name (from git remote or directory) |
| `repoPath` | string | Absolute path to original repository |
| `branch` | string | Full branch name (e.g., `feature/auth`) |
| `branchSlug` | string | Filesystem-safe name (e.g., `feature-auth`) |
| `worktreePath` | string | Absolute path to worktree |
| `ports` | number[] | Allocated port numbers (usually 2) |
| `createdAt` | string | ISO 8601 timestamp |
| `validatedAt` | string\|null | When validation passed |
| `agentLaunchedAt` | string\|null | When agent was launched |
| `task` | string\|null | Task description for the agent |
| `prNumber` | number\|null | Associated PR number if exists |
| `status` | string | `active`, `orphaned`, or `merged` |
**Port pool fields:**
| Field | Type | Description |
|-------|------|-------------|
| `start` | number | First port in pool (default: 8100) |
| `end` | number | Last port in pool (default: 8199) |
| `allocated` | number[] | Currently allocated ports |
### Manual Registry Operations
**Read entire registry:**
```bash
cat ~/.claude/worktree-registry.json | jq '.'
```
**List all worktrees:**
```bash
cat ~/.claude/worktree-registry.json | jq '.worktrees[]'
```
**List worktrees for specific project:**
```bash
cat ~/.claude/worktree-registry.json | jq '.worktrees[] | select(.project == "my-project")'
```
**Get allocated ports:**
```bash
cat ~/.claude/worktree-registry.json | jq '.portPool.allocated'
```
**Find worktree by branch (partial match):**
```bash
cat ~/.claude/worktree-registry.json | jq '.worktrees[] | select(.branch | contains("auth"))'
```
**Add worktree entry manually:**
```bash
TMP=$(mktemp)
jq '.worktrees += [{
"id": "'$(uuidgen)'",
"project": "my-project",
"repoPath": "/path/to/repo",
"branch": "feature/auth",
"branchSlug": "feature-auth",
"worktreePath": "/Users/me/tmp/worktrees/my-project/feature-auth",
"ports": [8100, 8101],
"createdAt": "'$(date -u +%Y-%m-%dT%H:%M:%SZ)'",
"validatedAt": null,
"agentLaunchedAt": null,
"task": "My task",
"prNumber": null,
"status": "active"
}]' ~/.claude/worktree-registry.json > "$TMP" && mv "$TMP" ~/.claude/worktree-registry.json
```
**Add ports to allocated pool:**
```bash
TMP=$(mktemp)
jq '.portPool.allocated += [8100, 8101] | .portPool.allocated |= unique | .portPool.allocated |= sort_by(.)' \
~/.claude/worktree-registry.json > "$TMP" && mv "$TMP" ~/.claude/worktree-registry.json
```
**Remove worktree entry:**
```bash
TMP=$(mktemp)
jq 'del(.worktrees[] | select(.project == "my-project" and .branch == "feature/auth"))' \
~/.claude/worktree-registry.json > "$TMP" && mv "$TMP" ~/.claude/worktree-registry.json
```
**Release ports from pool:**
```bash
TMP=$(mktemp)
jq '.portPool.allocated = (.portPool.allocated | map(select(. != 8100 and . != 8101)))' \
~/.claude/worktree-registry.json > "$TMP" && mv "$TMP" ~/.claude/worktree-registry.json
```
**Initialize empty registry (if missing):**
```bash
mkdir -p ~/.claude
cat > ~/.claude/worktree-registry.json << 'EOF'
{
"worktrees": [],
"portPool": {
"start": 8100,
"end": 8199,
"allocated": []
}
}
EOF
```
---
## Manual Port Allocation
If `scripts/allocate-ports.sh` fails, allocate ports manually:
**Step 1: Get currently allocated ports**
```bash
ALLOCATED=$(cat ~/.claude/worktree-registry.json | jq -r '.portPool.allocated[]' | sort -n)
echo "Currently allocated: $ALLOCATED"
```
**Step 2: Find first available port (not in allocated list AND not in use by system)**
```bash
for PORT in $(seq 8100 8199); do
# Check if in registry
if ! echo "$ALLOCATED" | grep -q "^${PORT}$"; then
# Check if in use by system
if ! lsof -i :"$PORT" &>/dev/null; then
echo "Available: $PORT"
break
fi
fi
done
```
**Step 3: Add to allocated pool**
```bash
TMP=$(mktemp)
jq '.portPool.allocated += [8100] | .portPool.allocated |= unique | .portPool.allocated |= sort_by(.)' \
~/.claude/worktree-registry.json > "$TMP" && mv "$TMP" ~/.claude/worktree-registry.json
```
---
## What You (Claude) Do vs What Scripts Do
| Task | Script Available | Manual Fallback |
|------|------------------|-----------------|
| Determine project name | No | Parse `git remote get-url origin` or `basename $(pwd)` |
| Detect package manager | No | Check for lockfiles (see Detection section) |
| Create git worktree | No | `git worktree add <path> -b <branch>` |
| Copy .agents/ directory | No | `cp -r .agents <worktree-path>/` |
| Install dependencies | No | Run detected install command |
| Validate (health check) | No | Start server, curl endpoint, stop server |
| Allocate ports | `scripts/allocate-ports.sh 2` | Manual (see above) |
| Register worktree | `scripts/register.sh` | Manual jq (see above) |
| Launch agent in terminal | `scripts/launch-agent.sh` | Manual (see below) |
| Show status | `scripts/status.sh` | `cat ~/.claude/worktree-registry.json \| jq ...` |
| Cleanup worktree | `scripts/cleanup.sh` | Manual (see Cleanup section) |
---
## Workflows
### 1. Create Multiple Worktrees with Agents
**User says:** "Spin up 3 worktrees for feature/auth, feature/payments, and fix/login-bug"
**You do (can parallelize with subagents):**
```
For EACH branch (can run in parallel):
1. SETUP
a. Get project name:
PROJECT=$(basename $(git remote get-url origin 2>/dev/null | sed 's/\.git$//') 2>/dev/null || basename $(pwd))
b. Get repo root:
REPO_ROOT=$(git rev-parse --show-toplevel)
c. Slugify branch:
BRANCH_SLUG=$(echo "feature/auth" | tr '/' '-')
d. Determine worktree path:
WORKTREE_PATH=~/tmp/worktrees/$PROJECT/$BRANCH_SLUG
2. ALLOCATE PORTS
Option A (script): ~/.claude/skills/worktree-manager/scripts/allocate-ports.sh 2
Option B (manual): Find 2 unused ports from 8100-8199, add to registry
3. CREATE WORKTREE
mkdir -p ~/tmp/worktrees/$PROJECT
在 GitHub 查看这个 SKILL.md 很大,SkillsMP 这里只预览前一段内容。 在 GitHub 查看