Updating `REQUIRED_BASE_SHA` for master and patch branches to make sure PRs that we merge are rebased after clang 1.4.0 upgrade. PR Close #36547
		
			
				
	
	
		
			236 lines
		
	
	
		
			6.8 KiB
		
	
	
	
		
			Bash
		
	
	
		
			Executable File
		
	
	
	
	
			
		
		
	
	
			236 lines
		
	
	
		
			6.8 KiB
		
	
	
	
		
			Bash
		
	
	
		
			Executable File
		
	
	
	
	
| #!/usr/bin/env bash
 | |
| 
 | |
| # https://www.tldp.org/LDP/abs/html/options.html#AEN19601
 | |
| # https://www.gnu.org/software/bash/manual/html_node/The-Set-Builtin.html
 | |
| set -u -e -E -o pipefail
 | |
| 
 | |
| BOLD='printf \e[1m'
 | |
| RESET_STYLES='printf \e[0m'
 | |
| LIGHT_CYAN='printf \e[96m'
 | |
| LIGHT_MAGENTA='printf \e[95m'
 | |
| GREEN='printf \e[32m'
 | |
| RED='printf \e[31m'
 | |
| 
 | |
| BASEDIR=$(dirname "$0")
 | |
| BASEDIR=`(cd $BASEDIR; pwd)`
 | |
| 
 | |
| PR_NUMBER=0
 | |
| PUSH_UPSTREAM=1
 | |
| FORCE=0
 | |
| while [[ $# -gt 0 ]]
 | |
| do
 | |
|   key="$1"
 | |
| 
 | |
|   case $key in
 | |
|       --dryrun)
 | |
|       PUSH_UPSTREAM=0
 | |
|       shift # past argument
 | |
|       ;;
 | |
|       --force)
 | |
|       FORCE=1
 | |
|       shift # past argument
 | |
|       ;;
 | |
|       *)    # unknown option
 | |
|       PR_NUMBER="$1" # save it in an array for later
 | |
|       shift # past argument
 | |
|       ;;
 | |
|   esac
 | |
| done
 | |
| 
 | |
| if [ "$PR_NUMBER" -eq 0 ]; then
 | |
|   echo "Merge github PR into the target branches if status is green"
 | |
|   echo
 | |
|   echo "$0 PR_NUMBER [--dryrun] [--force]"
 | |
|   echo
 | |
|   echo    --dryrun   Performs all operations but does not push the merge back to git@github.com:angular/angular.git.
 | |
|   echo    --force    Continues even if PR status is not green.
 | |
|   exit 0
 | |
| fi
 | |
| 
 | |
| if [ -z ${TOKEN:-''} ]; then
 | |
|     $RED
 | |
|     echo "############################################################"
 | |
|     echo "############################################################"
 | |
|     echo "WARNING: you should set the TOKEN variable to a github token"
 | |
|     echo "############################################################"
 | |
|     echo "############################################################"
 | |
|     $RESET_STYLES
 | |
|     GH_AUTH=""
 | |
| else
 | |
|     GH_AUTH="Authorization: token $TOKEN"
 | |
| fi
 | |
| 
 | |
| PULL_JSON=`curl -H "$GH_AUTH" -s https://api.github.com/repos/angular/angular/pulls/$PR_NUMBER`
 | |
| PR_SHA_COUNT=`node $BASEDIR/utils/json_extract.js commits <<< """$PULL_JSON"""`
 | |
| STATUS_JSON_URL=`node $BASEDIR/utils/json_extract.js _links.statuses.href <<< """$PULL_JSON"""`
 | |
| STATUS=`curl -H "$GH_AUTH" -s $STATUS_JSON_URL | node $BASEDIR/utils/json_extract.js description | cut -d '|' -f1`
 | |
| PR_LABELS=`curl -H "$GH_AUTH" -s https://api.github.com/repos/angular/angular/issues/$PR_NUMBER/labels`
 | |
| PR_ACTION=`echo "$PR_LABELS" | node $BASEDIR/utils/json_extract.js "name=^PR action:"`
 | |
| PR_TARGET=`echo "$PR_LABELS"  | node $BASEDIR/utils/json_extract.js "name=^PR target:"`
 | |
| PR_CLA=`echo "$PR_LABELS"  | node $BASEDIR/utils/json_extract.js "name=^cla"`
 | |
| MASTER_BRANCH='master'
 | |
| 
 | |
| if [[ ! "$PR_ACTION" =~ "PR action: merge" ]]; then
 | |
|   $RED
 | |
|   echo The PR is missing 'PR action: merge(-assistance)' label, found: $PR_ACTION
 | |
|   $RESET_STYLES
 | |
|   exit 1
 | |
| fi
 | |
| 
 | |
| if [[ "$PR_CLA" != "cla: yes" ]]; then
 | |
|   $RED
 | |
|   echo The PR is missing 'cla: Yes' label, found: $PR_CLA
 | |
|   $RESET_STYLES
 | |
|   exit 1
 | |
| fi
 | |
| 
 | |
| if [[ "$STATUS" != "All checks passed!" ]]; then
 | |
|   echo PR $PR_NUMBER is failing with: $STATUS
 | |
|   if [[ $FORCE == 1 ]]; then
 | |
|     $BOLD
 | |
|     $LIGHT_MAGENTA
 | |
|     echo FORCING: --force flag used to ignore PR status.
 | |
|     $RESET_STYLES
 | |
|   else
 | |
|     echo Exiting...
 | |
|     exit 1
 | |
|   fi
 | |
| fi
 | |
| 
 | |
| if [[ $PR_TARGET == "PR target: master & patch" ]]; then
 | |
|   MERGE_MASTER=1
 | |
|   MERGE_PATCH=1
 | |
| elif [[ $PR_TARGET == "PR target: master-only" ]]; then
 | |
|   MERGE_MASTER=1
 | |
|   MERGE_PATCH=0
 | |
| elif [[ $PR_TARGET == "PR target: patch-only" ]]; then
 | |
|   MERGE_MASTER=0
 | |
|   MERGE_PATCH=1
 | |
| else
 | |
|   $RED
 | |
|   echo "Unknown PR target format: $PR_TARGET"
 | |
|   $RESET_STYLES
 | |
|   exit 1;
 | |
| fi
 | |
| 
 | |
| CURRENT_BRANCH=`git rev-parse --abbrev-ref HEAD`
 | |
| PATCH_BRANCH=`git ls-remote --heads  git@github.com:angular/angular.git | grep -E 'refs\/heads\/[0-9]+\.[0-9]+\.x' | cut -d '/' -f3 | sort -r | head -n1`
 | |
| 
 | |
| CHECKOUT_MASTER="git checkout merge_pr_master"
 | |
| CHECKOUT_PATCH="git checkout merge_pr_patch"
 | |
| RESTORE_BRANCH="git checkout $CURRENT_BRANCH"
 | |
| 
 | |
| FETCH_PR="git fetch git@github.com:angular/angular.git pull/$PR_NUMBER/head:merge_pr heads/$MASTER_BRANCH:merge_pr_master heads/$PATCH_BRANCH:merge_pr_patch -f"
 | |
| BASE_PR="git checkout merge_pr~$PR_SHA_COUNT -B merge_pr_base"
 | |
| SQUASH_PR="git rebase --autosquash --interactive merge_pr_base merge_pr"
 | |
| REWRITE_MESSAGE="git filter-branch -f --msg-filter \"$BASEDIR/utils/github_closes.js $PR_NUMBER\" merge_pr_base..merge_pr"
 | |
| PUSH_BRANCHES="git push git@github.com:angular/angular.git merge_pr_master:$MASTER_BRANCH merge_pr_patch:$PATCH_BRANCH"
 | |
| CHERRY_PICK_PR="git cherry-pick merge_pr_base..merge_pr"
 | |
| 
 | |
| # Checks that each PR branch to be merged upstream contains SHAs of commits that significantly changed our CI infrastructure.
 | |
| #
 | |
| # This check is used to enforce that we don't merge PRs that have not been rebased recently and could result in merging
 | |
| # of non-approved or otherwise bad changes.
 | |
| REQUIRED_BASE_SHA_MASTER="c5c57f673745e9b66a771c49e778a7d2e8d8c56a" # clang 1.4.0 update
 | |
| REQUIRED_BASE_SHA_PATCH="f4681b6e407c0f518bc4a27ca04ca60d8eff8a69"  # clang 1.4.0 update
 | |
| if [[ $MERGE_MASTER == 1 ]]; then
 | |
|   REQUIRED_BASE_SHA="$REQUIRED_BASE_SHA_MASTER"
 | |
| # check patch only if patch-only PR
 | |
| elif [[ $MERGE_PATCH == 1 ]]; then
 | |
|   REQUIRED_BASE_SHA="$REQUIRED_BASE_SHA_PATCH"
 | |
| fi
 | |
| CHECK_IF_PR_REBASED="git branch --quiet merge_pr --contains $REQUIRED_BASE_SHA"
 | |
| 
 | |
| $BOLD
 | |
| $LIGHT_CYAN
 | |
| echo "======================"
 | |
| echo "GitHub Merge PR Steps"
 | |
| echo "======================"
 | |
| echo "   $FETCH_PR"
 | |
| echo "   $BASE_PR"
 | |
| echo "   $CHECK_IF_PR_REBASED"
 | |
| echo "   $SQUASH_PR"
 | |
| echo "   $REWRITE_MESSAGE"
 | |
| if [[ $MERGE_MASTER == 1 ]]; then
 | |
|   echo "   $CHECKOUT_MASTER && $CHERRY_PICK_PR"
 | |
| fi
 | |
| if [[ $MERGE_PATCH == 1 ]]; then
 | |
|   echo "   $CHECKOUT_PATCH && $CHERRY_PICK_PR"
 | |
| fi
 | |
| echo "   $PUSH_BRANCHES"
 | |
| echo "   $RESTORE_BRANCH"
 | |
| echo "----------------------"
 | |
| $RESET_STYLES
 | |
| $BOLD
 | |
| echo ""
 | |
| echo ">>> Fetch PR: $FETCH_PR"
 | |
| $RESET_STYLES
 | |
| $FETCH_PR
 | |
| $BOLD
 | |
| echo ""
 | |
| echo ">>> Mark base: $BASE_PR"
 | |
| $RESET_STYLES
 | |
| $BASE_PR
 | |
| $BOLD
 | |
| echo ""
 | |
| echo ">>> Check if PR rebased: $CHECK_IF_PR_REBASED"
 | |
| $RESET_STYLES
 | |
| if [[ $($CHECK_IF_PR_REBASED) != "" ]]; then
 | |
|   $GREEN
 | |
|   echo "The PR is sufficiently rebased!"
 | |
|   $RESET_STYLES
 | |
| else
 | |
|   $RED
 | |
|   echo ""
 | |
|   echo ""
 | |
|   echo "Failed to merge pull request #${PR_NUMBER} because it hasn't been rebased recently and could be bypassing new or updated CI checks!"
 | |
|   echo ""
 | |
|   echo "Please rebase the PR and try again."
 | |
|   echo ""|
 | |
|   $RESET_STYLES
 | |
|   $RESTORE_BRANCH
 | |
|   exit 1
 | |
| fi
 | |
| $BOLD
 | |
| echo ""
 | |
| echo ">>> Autosquash: $SQUASH_PR"
 | |
| $RESET_STYLES
 | |
| GIT_EDITOR=echo $SQUASH_PR
 | |
| $BOLD
 | |
| echo ""
 | |
| echo ">>> Rewrite message: $REWRITE_MESSAGE"
 | |
| # Next line should work, but it errors, hence copy paste the command.
 | |
| # $REWRITE_MESSAGE
 | |
| $RESET_STYLES
 | |
| git filter-branch -f --msg-filter "$BASEDIR/utils/github_closes.js $PR_NUMBER" merge_pr_base..merge_pr
 | |
| if [[ $MERGE_MASTER == 1 ]]; then
 | |
|   $BOLD
 | |
|   echo
 | |
|   echo ">>> Cherry pick to master: $CHECKOUT_MASTER && $CHERRY_PICK_PR"
 | |
|   $RESET_STYLES
 | |
|   $CHECKOUT_MASTER
 | |
|   $CHERRY_PICK_PR
 | |
| fi
 | |
| if [[ $MERGE_PATCH == 1 ]]; then
 | |
|   $BOLD
 | |
|   echo
 | |
|   echo ">>> Cherry pick to patch: $CHECKOUT_PATCH && $CHERRY_PICK_PR"
 | |
|   $RESET_STYLES
 | |
|   $CHECKOUT_PATCH
 | |
|   $CHERRY_PICK_PR
 | |
| fi
 | |
| $RESTORE_BRANCH
 | |
| 
 | |
| if [[ $PUSH_UPSTREAM == 1 ]]; then
 | |
|   $BOLD
 | |
|   echo
 | |
|   echo ">>> Push branches to angular repo"
 | |
|   $RESET_STYLES
 | |
|   $PUSH_BRANCHES
 | |
| fi
 | |
| $BOLD
 | |
| $GREEN
 | |
| echo
 | |
| echo ">>>>>> SUCCESS <<<<<< PR#$PR_NUMBER merged."
 | |
| $RESET_STYLES
 |