mirror of
https://github.com/humanlayer/humanlayer.git
synced 2025-08-20 19:01:22 +03:00
110 lines
3.4 KiB
Bash
Executable File
110 lines
3.4 KiB
Bash
Executable File
#!/bin/bash
|
|
|
|
# create_worktree.sh - Create a new worktree for development work
|
|
# Usage: ./create_worktree.sh [worktree_name]
|
|
# If no name provided, generates a unique human-readable one
|
|
|
|
set -e # Exit on any error
|
|
|
|
|
|
# Function to generate a unique worktree name
|
|
generate_unique_name() {
|
|
local adjectives=("swift" "bright" "clever" "smooth" "quick" "clean" "sharp" "neat" "cool" "fast")
|
|
local nouns=("fix" "task" "work" "dev" "patch" "branch" "code" "build" "test" "run")
|
|
|
|
local adj=${adjectives[$RANDOM % ${#adjectives[@]}]}
|
|
local noun=${nouns[$RANDOM % ${#nouns[@]}]}
|
|
local timestamp=$(date +%H%M)
|
|
|
|
echo "${adj}_${noun}_${timestamp}"
|
|
}
|
|
|
|
# Get worktree name from parameter or generate one
|
|
WORKTREE_NAME=${1:-$(generate_unique_name)}
|
|
|
|
# Get base directory name (should be 'humanlayer')
|
|
REPO_BASE_NAME=$(basename "$(pwd)")
|
|
|
|
# Construct paths
|
|
WORKTREE_DIR_NAME="${REPO_BASE_NAME}_${WORKTREE_NAME}"
|
|
WORKTREES_BASE="$HOME/.humanlayer/worktrees"
|
|
WORKTREE_PATH="${WORKTREES_BASE}/${WORKTREE_DIR_NAME}"
|
|
|
|
echo "🌳 Creating worktree: ${WORKTREE_NAME}"
|
|
echo "📁 Location: ${WORKTREE_PATH}"
|
|
|
|
# Check if worktrees base directory exists
|
|
if [ ! -d "$WORKTREES_BASE" ]; then
|
|
echo "❌ Error: Directory $WORKTREES_BASE does not exist."
|
|
echo " Please create it first: mkdir -p $WORKTREES_BASE"
|
|
exit 1
|
|
fi
|
|
|
|
# Check if worktree already exists
|
|
if [ -d "$WORKTREE_PATH" ]; then
|
|
echo "❌ Error: Worktree directory already exists: $WORKTREE_PATH"
|
|
exit 1
|
|
fi
|
|
|
|
# Get current branch
|
|
CURRENT_BRANCH=$(git branch --show-current)
|
|
echo "🔀 Creating from branch: ${CURRENT_BRANCH}"
|
|
|
|
# Create worktree (creates branch if it doesn't exist)
|
|
if git show-ref --verify --quiet "refs/heads/${WORKTREE_NAME}"; then
|
|
echo "📋 Using existing branch: ${WORKTREE_NAME}"
|
|
git worktree add "$WORKTREE_PATH" "$WORKTREE_NAME"
|
|
else
|
|
echo "🆕 Creating new branch: ${WORKTREE_NAME}"
|
|
git worktree add -b "$WORKTREE_NAME" "$WORKTREE_PATH" "$CURRENT_BRANCH"
|
|
fi
|
|
|
|
# Copy .claude directory if it exists
|
|
if [ -d ".claude" ]; then
|
|
echo "📋 Copying .claude directory..."
|
|
cp -r .claude "$WORKTREE_PATH/"
|
|
fi
|
|
|
|
# Change to worktree directory
|
|
cd "$WORKTREE_PATH"
|
|
|
|
echo "🔧 Setting up worktree dependencies..."
|
|
if ! make setup; then
|
|
echo "❌ Setup failed. Cleaning up worktree..."
|
|
cd - > /dev/null
|
|
git worktree remove --force "$WORKTREE_PATH"
|
|
git branch -D "$WORKTREE_NAME" 2>/dev/null || true
|
|
echo "❌ Not allowed to create worktree from a branch that isn't passing setup."
|
|
exit 1
|
|
fi
|
|
|
|
echo "🧪 Verifying worktree with checks and tests..."
|
|
temp_output=$(mktemp)
|
|
if make check test > "$temp_output" 2>&1; then
|
|
rm "$temp_output"
|
|
echo "✅ All checks and tests pass!"
|
|
else
|
|
cat "$temp_output"
|
|
rm "$temp_output"
|
|
echo "❌ Checks and tests failed. Cleaning up worktree..."
|
|
cd - > /dev/null
|
|
git worktree remove --force "$WORKTREE_PATH"
|
|
git branch -D "$WORKTREE_NAME" 2>/dev/null || true
|
|
echo "❌ Not allowed to create worktree from a branch that isn't passing checks and tests."
|
|
exit 1
|
|
fi
|
|
|
|
# Return to original directory
|
|
cd - > /dev/null
|
|
|
|
echo "✅ Worktree created successfully!"
|
|
echo "📁 Path: ${WORKTREE_PATH}"
|
|
echo "🔀 Branch: ${WORKTREE_NAME}"
|
|
echo ""
|
|
echo "To work in this worktree:"
|
|
echo " cd ${WORKTREE_PATH}"
|
|
echo ""
|
|
echo "To remove this worktree later:"
|
|
echo " git worktree remove ${WORKTREE_PATH}"
|
|
echo " git branch -D ${WORKTREE_NAME}"
|