Branch Deletion Phase One (PR Creation) #17
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| name: Branch Cleanup Report (PR Creation) | |
| permissions: | |
| contents: write | |
| pull-requests: write | |
| on: | |
| schedule: | |
| - cron: '00 22 1 */2 *' # 10PM on the 1st every two months | |
| workflow_dispatch: | |
| inputs: | |
| min_age_days: | |
| description: "Minimum age in days since merge" | |
| required: true | |
| default: 60 | |
| type: number | |
| branch_name: | |
| description: "Optional branch name to limit the report to a single branch" | |
| required: false | |
| type: string | |
| jobs: | |
| identify-branches: | |
| if: github.repository_owner == 'mendix' | |
| runs-on: ubuntu-latest | |
| steps: | |
| - name: Checkout code | |
| uses: actions/checkout@v6 | |
| with: | |
| fetch-depth: 0 | |
| token: ${{ secrets.GITHUB_TOKEN }} | |
| persist-credentials: true | |
| - name: Setup jq | |
| run: sudo apt-get install -y jq | |
| - name: Create timestamp file | |
| run: | | |
| echo "Last branch cleanup report: $(TZ='Europe/Amsterdam' date +'%Y-%m-%d %H:%M:%S %Z (UTC%:z)')" > branch-cleanup-timestamp.txt | |
| - name: Fetch all branches | |
| run: | | |
| git fetch origin '+refs/heads/*:refs/remotes/origin/*' --prune | |
| - name: Process branches | |
| id: branch-data | |
| env: | |
| MIN_AGE_DAYS: ${{ github.event.inputs.min_age_days || '60' }} | |
| TARGET_BRANCH: ${{ github.event.inputs.branch_name || '' }} | |
| run: | | |
| set -e | |
| ALL_BRANCHES=$(git branch -r | grep -v "origin/HEAD" | sed 's/origin\///') | |
| MIN_AGE_DAYS=${MIN_AGE_DAYS:-60} | |
| TARGET_BRANCH=${TARGET_BRANCH:-} | |
| echo "MIN_AGE_DAYS=${MIN_AGE_DAYS}" | |
| if [ -n "$TARGET_BRANCH" ]; then | |
| echo "TARGET_BRANCH=${TARGET_BRANCH}" | |
| fi | |
| PROTECTED_COUNT=0 | |
| MERGED_COUNT=0 | |
| UNMERGED_COUNT=0 | |
| PROTECTED_BRANCHES=() | |
| MERGED_BRANCHES_TO_PROCESS=() | |
| BRANCHES_TO_DELETE=() | |
| BRANCHES_TOO_RECENT=() | |
| UNMERGED_BRANCHES=() | |
| CURRENT_DATE=$(date +%Y%m%d) | |
| echo "CURRENT_DATE=$CURRENT_DATE" >> $GITHUB_ENV | |
| for BRANCH in $ALL_BRANCHES; do | |
| if [ -n "$TARGET_BRANCH" ] && [ "$BRANCH" != "$TARGET_BRANCH" ]; then | |
| continue | |
| fi | |
| branch_lower=$(echo "$BRANCH" | tr '[:upper:]' '[:lower:]') | |
| if [[ $branch_lower == *backup* || $branch_lower =~ ^(development|main|master|production)(-[0-9]+)?$ ]]; then | |
| PROTECTED_BRANCHES+=("$BRANCH") | |
| PROTECTED_COUNT=$((PROTECTED_COUNT+1)) | |
| elif git branch -r --merged origin/development | grep -q "origin/$BRANCH"; then | |
| MERGED_BRANCHES_TO_PROCESS+=("$BRANCH") | |
| MERGED_COUNT=$((MERGED_COUNT+1)) | |
| else | |
| UNMERGED_BRANCHES+=("$BRANCH") | |
| UNMERGED_COUNT=$((UNMERGED_COUNT+1)) | |
| fi | |
| done | |
| echo "branch totals: protected=${PROTECTED_COUNT} merged=${MERGED_COUNT} unmerged=${UNMERGED_COUNT}" | |
| for BRANCH in "${MERGED_BRANCHES_TO_PROCESS[@]}"; do | |
| BRANCH_NAME="$BRANCH" | |
| MERGE_HASH=$(git log --grep="Merge branch.*$BRANCH_NAME" origin/development -n 1 --pretty=format:"%H" || true) | |
| if [ -z "$MERGE_HASH" ]; then | |
| MERGE_HASH=$(git log -n 1 "origin/$BRANCH_NAME" --pretty=format:"%H" || true) | |
| fi | |
| if [ -z "$MERGE_HASH" ]; then | |
| echo "WARN: no merge commit found for $BRANCH_NAME — keeping it in the report" | |
| UNMERGED_BRANCHES+=("$BRANCH_NAME (no merge hash)") | |
| UNMERGED_COUNT=$((UNMERGED_COUNT+1)) | |
| continue | |
| fi | |
| MERGE_DATE_EPOCH=$(git show -s --format=%ct $MERGE_HASH 2>/dev/null || true) | |
| MERGE_OWNER=$(git show -s --format='%an' "$MERGE_HASH" 2>/dev/null || true) | |
| if [ -z "$MERGE_OWNER" ]; then | |
| MERGE_OWNER="unknown" | |
| fi | |
| if [ -z "$MERGE_DATE_EPOCH" ]; then | |
| echo "WARN: could not read commit date for $BRANCH_NAME (hash=$MERGE_HASH) — keeping it in the report" | |
| UNMERGED_BRANCHES+=("$BRANCH_NAME (owner: $MERGE_OWNER, no merge date)") | |
| UNMERGED_COUNT=$((UNMERGED_COUNT+1)) | |
| continue | |
| fi | |
| DAYS_AGO=$(( ($(date +%s) - MERGE_DATE_EPOCH) / 86400 )) | |
| if [[ $DAYS_AGO -ge $MIN_AGE_DAYS ]]; then | |
| BRANCHES_TO_DELETE+=("$BRANCH_NAME (owner: $MERGE_OWNER, ${DAYS_AGO}d since merge)") | |
| else | |
| BRANCHES_TOO_RECENT+=("$BRANCH_NAME (owner: $MERGE_OWNER, ${DAYS_AGO}d since merge)") | |
| fi | |
| echo "checked $BRANCH_NAME: hash=$MERGE_HASH date=$MERGE_DATE_EPOCH days=${DAYS_AGO} owner=$MERGE_OWNER" | |
| done | |
| echo "HAS_BRANCHES=true" >> $GITHUB_ENV | |
| echo "BRANCHES_TO_DELETE=$(printf -- '- %s\n' "${BRANCHES_TO_DELETE[@]}" | jq -Rs .)" >> $GITHUB_ENV | |
| echo "PROTECTED_BRANCHES=$(printf -- '- %s\n' "${PROTECTED_BRANCHES[@]}" | jq -Rs .)" >> $GITHUB_ENV | |
| echo "BRANCHES_TOO_RECENT=$(printf -- '- %s\n' "${BRANCHES_TOO_RECENT[@]}" | jq -Rs .)" >> $GITHUB_ENV | |
| echo "UNMERGED_BRANCHES=$(printf -- '- %s\n' "${UNMERGED_BRANCHES[@]}" | jq -Rs .)" >> $GITHUB_ENV | |
| - name: Create Report PR | |
| if: env.HAS_BRANCHES == 'true' | |
| uses: peter-evans/create-pull-request@v8 # NOTE: If you upgrade the version of this action, you must also update the GitHub Actions allowlist in mendix/docs > Settings > Actions > General to permit the new version tag, otherwise the workflow will fail. | |
| with: | |
| token: ${{ secrets.GITHUB_TOKEN }} | |
| title: "[Auto] Branch Cleanup Report - ${{ env.CURRENT_DATE }}" | |
| body: | | |
| ### Branches for Review | |
| ${{ fromJSON(env.BRANCHES_TO_DELETE) }} | |
| ### Protected Branches | |
| ${{ fromJSON(env.PROTECTED_BRANCHES) }} | |
| ### Recent Merges (too recent to delete) | |
| ${{ fromJSON(env.BRANCHES_TOO_RECENT) }} | |
| ### Unmerged Branches | |
| ${{ fromJSON(env.UNMERGED_BRANCHES) }} | |
| base: development | |
| labels: Internal WIP | |
| assignees: MarkvanMents,OlufunkeMoronfolu | |
| commit-message: "Add branch cleanup report for ${{ env.CURRENT_DATE }}" | |
| add-paths: | | |
| branch-cleanup-timestamp.txt | |
| author: "github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com>" | |
| committer: "github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com>" |