From ccb704cd4335635cd794b8b26cc6abc5e6574b3f Mon Sep 17 00:00:00 2001 From: "Melvin D. Protacio" Date: Tue, 2 Dec 2025 08:31:31 +0800 Subject: [PATCH 1/5] trying to fix --- .github/workflows/github-cache-cleanup.yml | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/.github/workflows/github-cache-cleanup.yml b/.github/workflows/github-cache-cleanup.yml index 4b371f9..b5e376b 100644 --- a/.github/workflows/github-cache-cleanup.yml +++ b/.github/workflows/github-cache-cleanup.yml @@ -31,9 +31,9 @@ jobs: echo "🔄 Iteration $ITERATION" echo "=========================================" - # Get cache IDs using API (no git repo needed) + # Get cache IDs using API with explicit repo path echo "Fetching cache IDs via API..." - CACHE_IDS=$(gh api "repos/{owner}/{repo}/actions/caches?per_page=100" --jq '.actions_caches[].id' 2>&1) + CACHE_IDS=$(gh api "repos/$GITHUB_REPOSITORY/actions/caches?per_page=100" --jq '.actions_caches[].id' 2>&1) LIST_EXIT_CODE=$? if [ $LIST_EXIT_CODE -ne 0 ]; then @@ -55,7 +55,7 @@ jobs: # Show cache details echo "📋 Cache details:" - gh api "repos/{owner}/{repo}/actions/caches?per_page=20" --jq '.actions_caches[] | "ID: \(.id) | Key: \(.key) | Size: \(.size_in_bytes) bytes"' 2>&1 | head -20 + gh api "repos/$GITHUB_REPOSITORY/actions/caches?per_page=20" --jq '.actions_caches[] | "ID: \(.id) | Key: \(.key) | Size: \(.size_in_bytes) bytes"' 2>&1 | head -20 echo "" # Delete each cache @@ -64,7 +64,7 @@ jobs: ((COUNTER++)) echo "[$COUNTER/$CACHE_COUNT] Deleting cache ID: $cache_id" - if gh api --method DELETE "repos/{owner}/{repo}/actions/caches/$cache_id" 2>&1; then + if gh api --method DELETE "repos/$GITHUB_REPOSITORY/actions/caches/$cache_id" 2>&1; then echo " ✅ Deleted" ((TOTAL_DELETED++)) else @@ -107,13 +107,13 @@ jobs: run: | echo "" echo "🔍 Verification:" - REMAINING=$(gh api "repos/{owner}/{repo}/actions/caches?per_page=10" --jq '.actions_caches | length' 2>&1) + REMAINING=$(gh api "repos/$GITHUB_REPOSITORY/actions/caches?per_page=10" --jq '.actions_caches | length' 2>&1) if [ "$REMAINING" -eq 0 ]; then echo "✅ All caches purged successfully!" else echo "⚠️ $REMAINING cache(es) still remain" - gh api "repos/{owner}/{repo}/actions/caches?per_page=10" --jq '.actions_caches[] | "ID: \(.id) | Key: \(.key)"' + gh api "repos/$GITHUB_REPOSITORY/actions/caches?per_page=10" --jq '.actions_caches[] | "ID: \(.id) | Key: \(.key)"' fi env: GH_TOKEN: ${{ github.token }} \ No newline at end of file From dd1c0bd25f9821ea10371bcfa560f582748edaf3 Mon Sep 17 00:00:00 2001 From: "Melvin D. Protacio" Date: Tue, 2 Dec 2025 08:42:55 +0800 Subject: [PATCH 2/5] try fixing from copilot --- .github/workflows/github-cache-cleanup.yml | 58 +++++++++++++--------- 1 file changed, 35 insertions(+), 23 deletions(-) diff --git a/.github/workflows/github-cache-cleanup.yml b/.github/workflows/github-cache-cleanup.yml index b5e376b..68f3fa8 100644 --- a/.github/workflows/github-cache-cleanup.yml +++ b/.github/workflows/github-cache-cleanup.yml @@ -14,56 +14,68 @@ jobs: - name: Purge all caches run: | set -x - + echo "=========================================" echo "🗑️ Purging All GitHub Caches" echo "=========================================" echo "Repository: $GITHUB_REPOSITORY" echo "Started at: $(date -u '+%Y-%m-%d %H:%M:%S UTC')" echo "" - + TOTAL_DELETED=0 TOTAL_FAILED=0 ITERATION=1 - + while true; do echo "=========================================" echo "🔄 Iteration $ITERATION" echo "=========================================" - + # Get cache IDs using API with explicit repo path echo "Fetching cache IDs via API..." - CACHE_IDS=$(gh api "repos/$GITHUB_REPOSITORY/actions/caches?per_page=100" --jq '.actions_caches[].id' 2>&1) + OUTPUT=$(gh api "repos/$GITHUB_REPOSITORY/actions/caches?per_page=100" --jq '.actions_caches[].id' 2>&1) LIST_EXIT_CODE=$? - + if [ $LIST_EXIT_CODE -ne 0 ]; then echo "❌ Failed to list caches" - echo "Output: $CACHE_IDS" + echo "Output: $OUTPUT" exit 1 fi - + + # Read output into an array to preserve one ID per element (handles newlines/spaces) + mapfile -t CACHE_IDS <<< "$OUTPUT" + + # Remove any empty elements (if any) + FILTERED_CACHE_IDS=() + for id in "${CACHE_IDS[@]}"; do + if [ -n "$id" ]; then + FILTERED_CACHE_IDS+=("$id") + fi + done + CACHE_IDS=("${FILTERED_CACHE_IDS[@]}") + # Check if empty - if [ -z "$CACHE_IDS" ]; then + if [ ${#CACHE_IDS[@]} -eq 0 ]; then echo "No more caches found. Done!" break fi - + # Count caches - CACHE_COUNT=$(echo "$CACHE_IDS" | wc -l) + CACHE_COUNT=${#CACHE_IDS[@]} echo "Found $CACHE_COUNT caches to delete" echo "" - + # Show cache details echo "📋 Cache details:" gh api "repos/$GITHUB_REPOSITORY/actions/caches?per_page=20" --jq '.actions_caches[] | "ID: \(.id) | Key: \(.key) | Size: \(.size_in_bytes) bytes"' 2>&1 | head -20 echo "" - + # Delete each cache COUNTER=0 - for cache_id in $CACHE_IDS; do + for cache_id in "${CACHE_IDS[@]}"; do ((COUNTER++)) echo "[$COUNTER/$CACHE_COUNT] Deleting cache ID: $cache_id" - + if gh api --method DELETE "repos/$GITHUB_REPOSITORY/actions/caches/$cache_id" 2>&1; then echo " ✅ Deleted" ((TOTAL_DELETED++)) @@ -72,24 +84,24 @@ jobs: ((TOTAL_FAILED++)) fi done - + echo "" echo "📊 Iteration $ITERATION Summary:" echo " Deleted: $COUNTER caches" echo " Total deleted: $TOTAL_DELETED" echo " Total failed: $TOTAL_FAILED" echo "" - + ((ITERATION++)) - + if [ $ITERATION -gt 50 ]; then echo "⚠️ Reached 50 iterations. Stopping." break fi - + sleep 1 done - + echo "" echo "=========================================" echo "✅ Purge Completed!" @@ -98,7 +110,7 @@ jobs: echo "Total deleted: $TOTAL_DELETED" echo "Total failed: $TOTAL_FAILED" echo "=========================================" - + set +x env: GH_TOKEN: ${{ github.token }} @@ -108,7 +120,7 @@ jobs: echo "" echo "🔍 Verification:" REMAINING=$(gh api "repos/$GITHUB_REPOSITORY/actions/caches?per_page=10" --jq '.actions_caches | length' 2>&1) - + if [ "$REMAINING" -eq 0 ]; then echo "✅ All caches purged successfully!" else @@ -116,4 +128,4 @@ jobs: gh api "repos/$GITHUB_REPOSITORY/actions/caches?per_page=10" --jq '.actions_caches[] | "ID: \(.id) | Key: \(.key)"' fi env: - GH_TOKEN: ${{ github.token }} \ No newline at end of file + GH_TOKEN: ${{ github.token }} From fa15fa5aa70ab78498908fca109d58f9757fe24b Mon Sep 17 00:00:00 2001 From: "Melvin D. Protacio" Date: Tue, 2 Dec 2025 08:47:39 +0800 Subject: [PATCH 3/5] trying again --- .github/workflows/github-cache-cleanup.yml | 158 ++++++++++++--------- 1 file changed, 87 insertions(+), 71 deletions(-) diff --git a/.github/workflows/github-cache-cleanup.yml b/.github/workflows/github-cache-cleanup.yml index 68f3fa8..26bf41c 100644 --- a/.github/workflows/github-cache-cleanup.yml +++ b/.github/workflows/github-cache-cleanup.yml @@ -3,129 +3,145 @@ name: Purge All GitHub Caches on: workflow_dispatch: +permissions: + actions: write + contents: read + jobs: purge-cache: runs-on: ubuntu-latest - permissions: - actions: write - contents: read steps: - - name: Purge all caches + - name: Verify GH CLI run: | - set -x + set -euo pipefail + if ! command -v gh >/dev/null 2>&1; then + echo "gh CLI not found. Installing..." + curl -fsSL https://github.com/cli/cli/releases/latest/download/gh_$(uname -s)_amd64.tar.gz -o /tmp/gh.tar.gz + tar -xzf /tmp/gh.tar.gz -C /tmp + sudo /tmp/gh_*/bin/gh --version || true + fi + gh --version + - name: Purge all caches + env: + GH_TOKEN: ${{ secrets.GITHUB_TOKEN }} + run: | + set -euo pipefail echo "=========================================" echo "🗑️ Purging All GitHub Caches" - echo "=========================================" echo "Repository: $GITHUB_REPOSITORY" echo "Started at: $(date -u '+%Y-%m-%d %H:%M:%S UTC')" - echo "" - + echo "=========================================" + TOTAL_DELETED=0 TOTAL_FAILED=0 ITERATION=1 - + MAX_ITERATIONS=50 + + # Helper: delete single cache id with retries + delete_cache() { + local id="$1" + local attempt=1 + local max_attempts=3 + while [ "$attempt" -le "$max_attempts" ]; do + if gh api --method DELETE "repos/$GITHUB_REPOSITORY/actions/caches/$id" --silent >/dev/null 2>&1; then + return 0 + fi + sleep $((attempt * 2)) + attempt=$((attempt + 1)) + done + return 1 + } + while true; do - echo "=========================================" + echo "-----------------------------------------" echo "🔄 Iteration $ITERATION" - echo "=========================================" - - # Get cache IDs using API with explicit repo path - echo "Fetching cache IDs via API..." - OUTPUT=$(gh api "repos/$GITHUB_REPOSITORY/actions/caches?per_page=100" --jq '.actions_caches[].id' 2>&1) - LIST_EXIT_CODE=$? - - if [ $LIST_EXIT_CODE -ne 0 ]; then + echo "-----------------------------------------" + + # Fetch all cache ids using pagination; output one id per line + if ! OUTPUT=$(gh api --paginate "repos/$GITHUB_REPOSITORY/actions/caches" --jq '.actions_caches[].id' 2>&1); then echo "❌ Failed to list caches" echo "Output: $OUTPUT" exit 1 fi - - # Read output into an array to preserve one ID per element (handles newlines/spaces) - mapfile -t CACHE_IDS <<< "$OUTPUT" - - # Remove any empty elements (if any) - FILTERED_CACHE_IDS=() + + # Read into array safely + mapfile -t CACHE_IDS < <(printf '%s\n' "$OUTPUT") + + # Trim and filter empties + FILTERED=() for id in "${CACHE_IDS[@]}"; do - if [ -n "$id" ]; then - FILTERED_CACHE_IDS+=("$id") + id_trimmed="$(printf '%s' "$id" | tr -d '[:space:]')" + if [ -n "$id_trimmed" ]; then + FILTERED+=("$id_trimmed") fi done - CACHE_IDS=("${FILTERED_CACHE_IDS[@]}") - - # Check if empty + CACHE_IDS=("${FILTERED[@]}") + if [ ${#CACHE_IDS[@]} -eq 0 ]; then echo "No more caches found. Done!" break fi - - # Count caches - CACHE_COUNT=${#CACHE_IDS[@]} - echo "Found $CACHE_COUNT caches to delete" - echo "" - - # Show cache details - echo "📋 Cache details:" - gh api "repos/$GITHUB_REPOSITORY/actions/caches?per_page=20" --jq '.actions_caches[] | "ID: \(.id) | Key: \(.key) | Size: \(.size_in_bytes) bytes"' 2>&1 | head -20 + + echo "Found ${#CACHE_IDS[@]} cache(s) to delete" echo "" - - # Delete each cache + COUNTER=0 for cache_id in "${CACHE_IDS[@]}"; do - ((COUNTER++)) - echo "[$COUNTER/$CACHE_COUNT] Deleting cache ID: $cache_id" - - if gh api --method DELETE "repos/$GITHUB_REPOSITORY/actions/caches/$cache_id" 2>&1; then - echo " ✅ Deleted" - ((TOTAL_DELETED++)) + COUNTER=$((COUNTER+1)) + echo "[$COUNTER/${#CACHE_IDS[@]}] Deleting cache ID: $cache_id" + if delete_cache "$cache_id"; then + echo " ✅ Deleted $cache_id" + TOTAL_DELETED=$((TOTAL_DELETED+1)) else - echo " ❌ Failed" - ((TOTAL_FAILED++)) + echo " ❌ Failed to delete $cache_id" + TOTAL_FAILED=$((TOTAL_FAILED+1)) fi done - + echo "" - echo "📊 Iteration $ITERATION Summary:" - echo " Deleted: $COUNTER caches" - echo " Total deleted: $TOTAL_DELETED" - echo " Total failed: $TOTAL_FAILED" + echo "Iteration $ITERATION summary: deleted $COUNTER this pass" + echo "Total deleted so far: $TOTAL_DELETED" + echo "Total failed so far: $TOTAL_FAILED" echo "" - - ((ITERATION++)) - - if [ $ITERATION -gt 50 ]; then - echo "⚠️ Reached 50 iterations. Stopping." + + ITERATION=$((ITERATION+1)) + if [ "$ITERATION" -gt "$MAX_ITERATIONS" ]; then + echo "⚠️ Reached max iterations ($MAX_ITERATIONS). Stopping." break fi - + + # Small pause to avoid hitting rate limits sleep 1 done - + echo "" echo "=========================================" echo "✅ Purge Completed!" - echo "=========================================" echo "Ended at: $(date -u '+%Y-%m-%d %H:%M:%S UTC')" echo "Total deleted: $TOTAL_DELETED" echo "Total failed: $TOTAL_FAILED" echo "=========================================" - set +x + - name: Verify caches cleared env: - GH_TOKEN: ${{ github.token }} - - - name: Verify + GH_TOKEN: ${{ secrets.GITHUB_TOKEN }} run: | + set -euo pipefail echo "" echo "🔍 Verification:" - REMAINING=$(gh api "repos/$GITHUB_REPOSITORY/actions/caches?per_page=10" --jq '.actions_caches | length' 2>&1) - + # Query a small page to check presence quickly + if ! REMAINING=$(gh api "repos/$GITHUB_REPOSITORY/actions/caches?per_page=1" --jq '.actions_caches | length' --silent 2>&1); then + echo "❌ Verification query failed. Output:" + echo "$REMAINING" + exit 1 + fi if [ "$REMAINING" -eq 0 ]; then echo "✅ All caches purged successfully!" + exit 0 else - echo "⚠️ $REMAINING cache(es) still remain" - gh api "repos/$GITHUB_REPOSITORY/actions/caches?per_page=10" --jq '.actions_caches[] | "ID: \(.id) | Key: \(.key)"' + echo "⚠️ Some caches still remain. Listing up to 20:" + gh api "repos/$GITHUB_REPOSITORY/actions/caches?per_page=20" --jq '.actions_caches[] | "ID: \(.id) | Key: \(.key) | Size: \(.size_in_bytes) bytes"' || true + exit 2 fi - env: - GH_TOKEN: ${{ github.token }} From 3250f61cc39054c47f3fccc16b51c9abda0c9602 Mon Sep 17 00:00:00 2001 From: "Melvin D. Protacio" Date: Tue, 2 Dec 2025 09:00:48 +0800 Subject: [PATCH 4/5] remove verification --- .github/workflows/github-cache-cleanup.yml | 22 ---------------------- 1 file changed, 22 deletions(-) diff --git a/.github/workflows/github-cache-cleanup.yml b/.github/workflows/github-cache-cleanup.yml index 26bf41c..bba94de 100644 --- a/.github/workflows/github-cache-cleanup.yml +++ b/.github/workflows/github-cache-cleanup.yml @@ -123,25 +123,3 @@ jobs: echo "Total deleted: $TOTAL_DELETED" echo "Total failed: $TOTAL_FAILED" echo "=========================================" - - - name: Verify caches cleared - env: - GH_TOKEN: ${{ secrets.GITHUB_TOKEN }} - run: | - set -euo pipefail - echo "" - echo "🔍 Verification:" - # Query a small page to check presence quickly - if ! REMAINING=$(gh api "repos/$GITHUB_REPOSITORY/actions/caches?per_page=1" --jq '.actions_caches | length' --silent 2>&1); then - echo "❌ Verification query failed. Output:" - echo "$REMAINING" - exit 1 - fi - if [ "$REMAINING" -eq 0 ]; then - echo "✅ All caches purged successfully!" - exit 0 - else - echo "⚠️ Some caches still remain. Listing up to 20:" - gh api "repos/$GITHUB_REPOSITORY/actions/caches?per_page=20" --jq '.actions_caches[] | "ID: \(.id) | Key: \(.key) | Size: \(.size_in_bytes) bytes"' || true - exit 2 - fi From 9bcac68ccd3f822553ca4f1099ee6755f321ca1a Mon Sep 17 00:00:00 2001 From: "Melvin D. Protacio" Date: Tue, 2 Dec 2025 09:15:08 +0800 Subject: [PATCH 5/5] delete caches on pull request --- .github/workflows/dockerhub.yml | 6 ++++++ .github/workflows/github-cache-cleanup.yml | 1 + 2 files changed, 7 insertions(+) diff --git a/.github/workflows/dockerhub.yml b/.github/workflows/dockerhub.yml index 149b30f..4dce295 100644 --- a/.github/workflows/dockerhub.yml +++ b/.github/workflows/dockerhub.yml @@ -68,6 +68,12 @@ jobs: version: ${{ matrix.version }} variant: ${{ matrix.variant }} latest: '8.4.15' + # Cleanup github caches on PRs + cleanup-cache: + needs: build-images + if: github.event_name == 'pull_request' + uses: ./.github/workflows/github-cache-cleanup.yml + secrets: inherit # Add this new summary job build-complete: needs: build-images diff --git a/.github/workflows/github-cache-cleanup.yml b/.github/workflows/github-cache-cleanup.yml index bba94de..138a8bf 100644 --- a/.github/workflows/github-cache-cleanup.yml +++ b/.github/workflows/github-cache-cleanup.yml @@ -2,6 +2,7 @@ name: Purge All GitHub Caches on: workflow_dispatch: + workflow_call: permissions: actions: write