surshar / claude-code
Claude Code is an agentic coding tool that lives in your terminal, understands your codebase, and helps you code faster by executing routine tasks, explaining complex code, and handling git workflows - all through natural language commands.
Built by Anthropic · github.com/anthropics
Improve gh.sh wrapper: stricter validation and better error messages
| @@ -11,6 +11,15 @@ | ||
| 11 | 11 | # ./scripts/gh.sh search issues "search query" --limit 10 |
| 12 | 12 | # ./scripts/gh.sh label list --limit 100 |
| 13 | 13 | |
| 14 | +export GH_HOST=github.com | |
| 15 | + | |
| 16 | +REPO="${GH_REPO:-${GITHUB_REPOSITORY:-}}" | |
| 17 | +if [[ -z "$REPO" || "$REPO" == */*/* || "$REPO" != */* ]]; then | |
| 18 | + echo "Error: GH_REPO or GITHUB_REPOSITORY must be set to owner/repo format (e.g., GITHUB_REPOSITORY=anthropics/claude-code)" >&2 | |
| 19 | + exit 1 | |
| 20 | +fi | |
| 21 | +export GH_REPO="$REPO" | |
| 22 | + | |
| 14 | 23 | ALLOWED_FLAGS=(--comments --state --limit --label) |
| 15 | 24 | FLAGS_WITH_VALUES=(--state --limit --label) |
| 16 | 25 | |
| @@ -21,6 +30,7 @@ | ||
| 21 | 30 | "issue view"|"issue list"|"search issues"|"label list") |
| 22 | 31 | ;; |
| 23 | 32 | *) |
| 33 | + echo "Error: only 'issue view', 'issue list', 'search issues', 'label list' are allowed (e.g., ./scripts/gh.sh issue view 123)" >&2 | |
| 24 | 34 | exit 1 |
| 25 | 35 | ;; |
| 26 | 36 | esac |
| @@ -45,6 +55,7 @@ | ||
| 45 | 55 | fi |
| 46 | 56 | done |
| 47 | 57 | if [[ "$matched" == false ]]; then |
| 58 | + echo "Error: only --comments, --state, --limit, --label flags are allowed (e.g., ./scripts/gh.sh issue list --state open --limit 20)" >&2 | |
| 48 | 59 | exit 1 |
| 49 | 60 | fi |
| 50 | 61 | FLAGS+=("$arg") |
| @@ -62,24 +73,24 @@ | ||
| 62 | 73 | fi |
| 63 | 74 | done |
| 64 | 75 | |
| 65 | -REPO="${GH_REPO:-${GITHUB_REPOSITORY:-}}" | |
| 66 | - | |
| 67 | 76 | if [[ "$CMD" == "search issues" ]]; then |
| 68 | - if [[ -z "$REPO" ]]; then | |
| 69 | - exit 1 | |
| 70 | - fi | |
| 71 | 77 | QUERY="${POSITIONAL[0]:-}" |
| 72 | 78 | QUERY_LOWER=$(echo "$QUERY" | tr '[:upper:]' '[:lower:]') |
| 73 | 79 | if [[ "$QUERY_LOWER" == *"repo:"* || "$QUERY_LOWER" == *"org:"* || "$QUERY_LOWER" == *"user:"* ]]; then |
| 80 | + echo "Error: search query must not contain repo:, org:, or user: qualifiers (e.g., ./scripts/gh.sh search issues \"bug report\" --limit 10)" >&2 | |
| 74 | 81 | exit 1 |
| 75 | 82 | fi |
| 76 | 83 | gh "$SUB1" "$SUB2" "$QUERY" --repo "$REPO" "${FLAGS[@]}" |
| 84 | +elif [[ "$CMD" == "issue view" ]]; then | |
| 85 | + if [[ ${#POSITIONAL[@]} -ne 1 ]] || ! [[ "${POSITIONAL[0]}" =~ ^[0-9]+$ ]]; then | |
| 86 | + echo "Error: issue view requires exactly one numeric issue number (e.g., ./scripts/gh.sh issue view 123)" >&2 | |
| 87 | + exit 1 | |
| 88 | + fi | |
| 89 | + gh "$SUB1" "$SUB2" "${POSITIONAL[0]}" "${FLAGS[@]}" | |
| 77 | 90 | else |
| 78 | - # Reject URLs in positional args to prevent cross-repo access | |
| 79 | - for pos in "${POSITIONAL[@]}"; do | |
| 80 | - if [[ "$pos" == http://* || "$pos" == https://* ]]; then | |
| 81 | - exit 1 | |
| 82 | - fi | |
| 83 | - done | |
| 84 | - gh "$SUB1" "$SUB2" "${POSITIONAL[@]}" "${FLAGS[@]}" | |
| 91 | + if [[ ${#POSITIONAL[@]} -ne 0 ]]; then | |
| 92 | + echo "Error: issue list and label list do not accept positional arguments (e.g., ./scripts/gh.sh issue list --state open, ./scripts/gh.sh label list --limit 100)" >&2 | |
| 93 | + exit 1 | |
| 94 | + fi | |
| 95 | + gh "$SUB1" "$SUB2" "${FLAGS[@]}" | |
| 85 | 96 | fi |