#!/usr/bin/env bash set -euo pipefail REPO_ROOT="$(cd "$(dirname "${BASH_SOURCE[0]}")/.." && pwd)" SCRIPT="$REPO_ROOT/scripts/check-manifests.sh" PASS=0 FAIL=0 pass() { echo " PASS: $1"; PASS=$((PASS + 1)); } fail() { echo " FAIL: $1"; FAIL=$((FAIL + 1)); } # Helper: make a minimal valid repo fixture with marketplace + plugin structure make_valid_fixture() { local dir dir="$(mktemp -d)" mkdir -p "$dir/.claude-plugin" mkdir -p "$dir/plugins/myplugin/skills/my-skill" mkdir -p "$dir/plugins/myplugin/agents" cat > "$dir/.claude-plugin/marketplace.json" <<'JSON' { "name": "test-marketplace", "plugins": [ { "name": "myplugin", "source": "./plugins/myplugin" } ] } JSON cat > "$dir/plugins/myplugin/plugin.json" <<'JSON' { "name": "myplugin", "skills": ["skills/"], "agents": "agents/", "hooks": "hooks.json" } JSON touch "$dir/plugins/myplugin/hooks.json" echo "$dir" } # --- 1. Exits 0 against valid repo structure --- echo "" echo "--- exits 0 when all references are valid ---" FIXTURE="$(make_valid_fixture)" trap 'rm -rf "$FIXTURE"' EXIT if bash "$SCRIPT" "$FIXTURE" > /dev/null 2>&1; then pass "exits 0 when all manifest references resolve" else fail "exited non-zero against a valid fixture" fi # --- 2. Exits 1 when plugin source dir is missing --- echo "" echo "--- exits 1 when plugin source directory missing ---" FIXTURE2="$(mktemp -d)" trap 'rm -rf "$FIXTURE2"' EXIT mkdir -p "$FIXTURE2/.claude-plugin" cat > "$FIXTURE2/.claude-plugin/marketplace.json" <<'JSON' { "name": "test-marketplace", "plugins": [ { "name": "ghost", "source": "./plugins/ghost" } ] } JSON if bash "$SCRIPT" "$FIXTURE2" > /dev/null 2>&1; then fail "exited 0 when plugin source dir is missing — expected exit 1" else pass "exits non-zero when plugin source directory does not exist" fi # --- 3. Exits 1 when plugin.json is missing from plugin dir --- echo "" echo "--- exits 1 when plugin.json missing from plugin directory ---" FIXTURE3="$(mktemp -d)" trap 'rm -rf "$FIXTURE3"' EXIT mkdir -p "$FIXTURE3/.claude-plugin" mkdir -p "$FIXTURE3/plugins/nomanifest" cat > "$FIXTURE3/.claude-plugin/marketplace.json" <<'JSON' { "name": "test-marketplace", "plugins": [ { "name": "nomanifest", "source": "./plugins/nomanifest" } ] } JSON if bash "$SCRIPT" "$FIXTURE3" > /dev/null 2>&1; then fail "exited 0 when plugin.json is missing — expected exit 1" else pass "exits non-zero when plugin.json is missing from plugin directory" fi # --- 4. Exits 1 when a skills directory listed in plugin.json does not exist --- echo "" echo "--- exits 1 when skills directory missing ---" FIXTURE4="$(mktemp -d)" trap 'rm -rf "$FIXTURE4"' EXIT mkdir -p "$FIXTURE4/.claude-plugin" mkdir -p "$FIXTURE4/plugins/myplugin" cat > "$FIXTURE4/.claude-plugin/marketplace.json" <<'JSON' { "name": "test-marketplace", "plugins": [ { "name": "myplugin", "source": "./plugins/myplugin" } ] } JSON cat > "$FIXTURE4/plugins/myplugin/plugin.json" <<'JSON' { "name": "myplugin", "skills": ["skills/"] } JSON if bash "$SCRIPT" "$FIXTURE4" > /dev/null 2>&1; then fail "exited 0 when skills dir missing — expected exit 1" else pass "exits non-zero when skills directory referenced in plugin.json does not exist" fi # --- 5. Exits 1 when a file referenced in plugin.json (hooks) does not exist --- echo "" echo "--- exits 1 when referenced hooks file missing ---" FIXTURE5="$(mktemp -d)" trap 'rm -rf "$FIXTURE5"' EXIT mkdir -p "$FIXTURE5/.claude-plugin" mkdir -p "$FIXTURE5/plugins/myplugin/skills" cat > "$FIXTURE5/.claude-plugin/marketplace.json" <<'JSON' { "name": "test-marketplace", "plugins": [ { "name": "myplugin", "source": "./plugins/myplugin" } ] } JSON cat > "$FIXTURE5/plugins/myplugin/plugin.json" <<'JSON' { "name": "myplugin", "hooks": "hooks.json" } JSON if bash "$SCRIPT" "$FIXTURE5" > /dev/null 2>&1; then fail "exited 0 when hooks file missing — expected exit 1" else pass "exits non-zero when file referenced in plugin.json does not exist" fi echo "" echo "Results: $PASS passed, $FAIL failed" [[ $FAIL -eq 0 ]]