feat: add parallel issue implementation capability with worktrees
Add complete capability set for orchestrating parallel issue implementation with automated review cycles using git worktrees. Components: - worktrees skill: Git worktree patterns + bundled scripts for reliable operations - spawn-issues skill: Event-driven orchestrator (Haiku) for parallel workflow - issue-worker agent: Implements issues autonomously (Sonnet) - code-reviewer agent: Reviews PRs with quality checks (Haiku, read-only) - pr-fixer agent: Addresses review feedback automatically (Haiku) Workflow: /spawn-issues creates worktrees → spawns workers → reviews PRs → fixes feedback → iterates until approved → cleans up worktrees Scripts handle error-prone worktree operations. Orchestrator uses event-driven approach with task notifications for efficient parallel execution. Co-Authored-By: Claude Code <noreply@anthropic.com>
This commit is contained in:
56
skills/worktrees/scripts/cleanup-worktrees.sh
Executable file
56
skills/worktrees/scripts/cleanup-worktrees.sh
Executable file
@@ -0,0 +1,56 @@
|
||||
#!/bin/bash
|
||||
set -euo pipefail
|
||||
|
||||
# Clean up git worktrees
|
||||
#
|
||||
# Usage:
|
||||
# ./cleanup-worktrees.sh <path> # Remove specific worktree
|
||||
# ./cleanup-worktrees.sh <directory> # Remove all worktrees in directory
|
||||
# ./cleanup-worktrees.sh --force <path> # Force remove even if dirty
|
||||
|
||||
FORCE=false
|
||||
if [ "$1" = "--force" ]; then
|
||||
FORCE=true
|
||||
shift
|
||||
fi
|
||||
|
||||
TARGET="$1"
|
||||
REPO_PATH=$(git rev-parse --show-toplevel 2>/dev/null || pwd)
|
||||
|
||||
cd "$REPO_PATH"
|
||||
|
||||
remove_worktree() {
|
||||
local worktree_path="$1"
|
||||
|
||||
if [ ! -d "$worktree_path" ]; then
|
||||
return 0
|
||||
fi
|
||||
|
||||
if [ "$FORCE" = true ]; then
|
||||
git worktree remove "$worktree_path" --force 2>/dev/null || true
|
||||
else
|
||||
git worktree remove "$worktree_path" 2>/dev/null || true
|
||||
fi
|
||||
}
|
||||
|
||||
# Check if target is a directory containing multiple worktrees
|
||||
if [ -d "$TARGET" ]; then
|
||||
# Check if it's a worktree itself or a directory of worktrees
|
||||
if git worktree list | grep -q "$TARGET\$"; then
|
||||
# It's a single worktree
|
||||
remove_worktree "$TARGET"
|
||||
else
|
||||
# It's a directory, remove all worktrees inside
|
||||
for worktree in "$TARGET"/*; do
|
||||
if [ -d "$worktree" ]; then
|
||||
remove_worktree "$worktree"
|
||||
fi
|
||||
done
|
||||
|
||||
# Try to remove the directory if empty
|
||||
rmdir "$TARGET" 2>/dev/null || true
|
||||
fi
|
||||
else
|
||||
echo "Error: Path does not exist: $TARGET" >&2
|
||||
exit 1
|
||||
fi
|
||||
74
skills/worktrees/scripts/create-worktree.sh
Executable file
74
skills/worktrees/scripts/create-worktree.sh
Executable file
@@ -0,0 +1,74 @@
|
||||
#!/bin/bash
|
||||
set -euo pipefail
|
||||
|
||||
# Create a git worktree for issue work or PR review
|
||||
#
|
||||
# Usage:
|
||||
# ./create-worktree.sh issue <issue-number>
|
||||
# ./create-worktree.sh review <pr-number> <branch-name>
|
||||
#
|
||||
# Returns: Absolute path to created worktree (stdout)
|
||||
|
||||
MODE="$1"
|
||||
REPO_PATH=$(git rev-parse --show-toplevel 2>/dev/null || pwd)
|
||||
REPO_NAME=$(basename "$REPO_PATH")
|
||||
WORKTREES_DIR="${REPO_PATH}/../worktrees"
|
||||
|
||||
# Ensure worktrees directory exists
|
||||
mkdir -p "$WORKTREES_DIR"
|
||||
|
||||
# Fetch latest from origin
|
||||
cd "$REPO_PATH"
|
||||
git fetch origin >/dev/null 2>&1
|
||||
|
||||
case "$MODE" in
|
||||
issue)
|
||||
ISSUE_NUMBER="$2"
|
||||
WORKTREE_NAME="${REPO_NAME}-issue-${ISSUE_NUMBER}"
|
||||
WORKTREE_PATH="${WORKTREES_DIR}/${WORKTREE_NAME}"
|
||||
|
||||
# Get issue title for branch name
|
||||
ISSUE_TITLE=$(tea issues "$ISSUE_NUMBER" 2>/dev/null | grep -i "title" | head -1 | cut -d: -f2- | xargs || echo "untitled")
|
||||
|
||||
# Create safe branch name
|
||||
BRANCH_NAME="issue-${ISSUE_NUMBER}-$(echo "$ISSUE_TITLE" | tr '[:upper:]' '[:lower:]' | tr ' ' '-' | tr -cd '[:alnum:]-' | cut -c1-50)"
|
||||
|
||||
# Remove worktree if it already exists
|
||||
if [ -d "$WORKTREE_PATH" ]; then
|
||||
git worktree remove "$WORKTREE_PATH" --force 2>/dev/null || true
|
||||
fi
|
||||
|
||||
# Delete branch if it exists
|
||||
git branch -D "$BRANCH_NAME" 2>/dev/null || true
|
||||
|
||||
# Create worktree with new branch from main
|
||||
git worktree add "$WORKTREE_PATH" -b "$BRANCH_NAME" origin/main >/dev/null 2>&1
|
||||
|
||||
echo "$WORKTREE_PATH"
|
||||
;;
|
||||
|
||||
review)
|
||||
PR_NUMBER="$2"
|
||||
BRANCH_NAME="$3"
|
||||
WORKTREE_NAME="${REPO_NAME}-review-${PR_NUMBER}"
|
||||
WORKTREE_PATH="${WORKTREES_DIR}/${WORKTREE_NAME}"
|
||||
|
||||
# Remove worktree if it already exists
|
||||
if [ -d "$WORKTREE_PATH" ]; then
|
||||
git worktree remove "$WORKTREE_PATH" --force 2>/dev/null || true
|
||||
fi
|
||||
|
||||
# Create worktree from existing branch
|
||||
git worktree add "$WORKTREE_PATH" "origin/${BRANCH_NAME}" >/dev/null 2>&1
|
||||
|
||||
echo "$WORKTREE_PATH"
|
||||
;;
|
||||
|
||||
*)
|
||||
echo "Error: Invalid mode '$MODE'. Use 'issue' or 'review'" >&2
|
||||
echo "Usage:" >&2
|
||||
echo " $0 issue <issue-number>" >&2
|
||||
echo " $0 review <pr-number> <branch-name>" >&2
|
||||
exit 1
|
||||
;;
|
||||
esac
|
||||
13
skills/worktrees/scripts/list-worktrees.sh
Executable file
13
skills/worktrees/scripts/list-worktrees.sh
Executable file
@@ -0,0 +1,13 @@
|
||||
#!/bin/bash
|
||||
set -euo pipefail
|
||||
|
||||
# List all active git worktrees
|
||||
#
|
||||
# Usage:
|
||||
# ./list-worktrees.sh
|
||||
|
||||
REPO_PATH=$(git rev-parse --show-toplevel 2>/dev/null || pwd)
|
||||
cd "$REPO_PATH"
|
||||
|
||||
echo "Active worktrees:"
|
||||
git worktree list
|
||||
Reference in New Issue
Block a user