github.com/noironetworks/cilium-net@v1.6.12/contrib/backporting/check-stable (about) 1 #!/bin/bash 2 # 3 # Copyright 2016 The Kubernetes Authors All rights reserved. 4 # Copyright 2019 Authors of Cilium 5 # 6 # Licensed under the Apache License, Version 2.0 (the "License"); 7 # you may not use this file except in compliance with the License. 8 # You may obtain a copy of the License at 9 # 10 # http://www.apache.org/licenses/LICENSE-2.0 11 # 12 # Unless required by applicable law or agreed to in writing, software 13 # distributed under the License is distributed on an "AS IS" BASIS, 14 # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 15 # See the License for the specific language governing permissions and 16 # limitations under the License. 17 # 18 # Set PROGram name 19 PROG=${0##*/} 20 STABLE_BRANCH=${1:-} 21 SUMMARY_LOG=${2:-} 22 23 source $(dirname $(readlink -ne $BASH_SOURCE))/../release/lib/common.sh 24 source $TOOL_LIB_PATH/gitlib.sh 25 source $(dirname $(readlink -ne $BASH_SOURCE))/common.sh 26 27 # Validate command-line 28 common::argc_validate 2 29 30 if [[ -z $STABLE_BRANCH ]]; then 31 logecho "usage: $0 <branch> [summary-file]" >&2 32 common::exit 1 33 fi 34 35 ############################################################################### 36 # FUNCTIONS 37 ############################################################################### 38 ############################################################################### 39 # Get titles from a list of PRs 40 # @param prs - A space separated list of PRs to extract 41 # 42 extract_pr_title () { 43 local prs="$*" 44 local pr 45 local content 46 local body 47 local author 48 local pull_json 49 50 for pr in $prs; do 51 pull_json="$($GHCURL $CILIUM_GITHUB_API/pulls/$pr)" 52 [[ -z "$pull_json" ]] && return 1 53 body="$(echo "$pull_json" |jq -r '.body' |tr -d '\r')" 54 55 content=$(echo "$pull_json" | jq -r '.title') 56 author=$(echo "$pull_json" | jq -r '.user.login') 57 content=$(echo "$content" |sed -e '1s/^ *\** *//g' \ 58 -e "1s/$/ (@$author)/g") 59 60 logecho -r "$content" 61 done 62 } 63 64 ############################################################################### 65 # Get merged PRs that match a specified label and exclude a specified label 66 # 67 # Each returned array entry is in the form "$merged_at#$prnumber" 68 get_prs () { 69 local label=$1 70 local label_exclude=$2 71 local -a prs 72 local total 73 local current_page 74 local num_pages 75 local prs_per_page 76 local url 77 78 prs_per_page=100 79 80 label_opt="%20label:$label" 81 label_exclude_opt="%20-label:$label_exclude" 82 url="${CILIUM_GITHUB_SEARCHAPI}$label_opt$label_exclude_opt" 83 total="$($GHCURL $url | jq -r '.total_count')" 84 85 # Calculate number of pages, rounding up 86 num_pages=$(((total + prs_per_page - 1) / prs_per_page )) 87 88 for current_page in `seq 1 $num_pages`; do 89 local page_json 90 local merged_at 91 local pr_url 92 local pr_list 93 94 page_json=$($GHCURL "$url&page=$current_page") 95 pr_list=$(echo -n $page_json | jq -r '.items[] | (.number | tostring)') 96 for pr in $pr_list; do 97 pr_url="https://api.github.com/repos/cilium/cilium/pulls/$pr" 98 merged_at=$($GHCURL "$pr_url" | jq -r '.merged_at') 99 100 # Never merged ... 101 if [[ "$merged_at" = "null" ]]; then 102 continue 103 fi 104 prs+=("$merged_at#$pr ") 105 done 106 done 107 108 echo "${prs[@]}" 109 } 110 111 ############################################################################### 112 # Generates the release notes for one particular PR 113 generate_commit_list_for_pr () { 114 local pr=$1 115 local merged_at=$2 116 local url 117 local pr_json 118 local merge_sha 119 local commits 120 local branch 121 local tmp_file 122 local patchid 123 local subject 124 local tmp_file 125 local entry_array 126 local entry_id 127 local entry_sha 128 local entry_sub 129 local upstream 130 131 url="https://api.github.com/repos/cilium/cilium/pulls/$pr/commits" 132 pr_json="$($GHCURL $url)" 133 n_commits="$(echo -n $pr_json | jq -r '. | length')" 134 135 tmp_file=`mktemp pr-correlation.XXXXXX` 136 branch="check-for-stable-$pr" 137 git fetch -q $REMOTE pull/$pr/head:$branch 138 # Use GitHub to determine the number of commits to list, but then query 139 # the branch directly to determine the canonical order of the commits. 140 for commit in $(git rev-list --reverse -$n_commits $branch); do 141 patchid="$(git show $commit | git patch-id)" 142 subject="$(git show -s --pretty="%s" $commit)" 143 echo "$patchid $subject" >> $tmp_file 144 done 145 git branch -q -D $branch 146 echo " Merge with $n_commits commit(s) merged at: `date -R -d "$(echo $merged_at | sed 's/T/ /')"`!" 147 echo " Branch: master (!) refs/pull/$pr/head" 148 echo " ---------- -------------------" 149 echo " v (start)" 150 while read entry; do 151 entry_array=($entry) 152 entry_id=${entry_array[0]} 153 entry_sha=${entry_array[1]} 154 entry_sub=${entry_array[@]:2} 155 upstream="$(git log -F --since="1year" --pretty="%H" --no-merges --grep "$entry_sub" $REMOTE/master)" 156 upstream="$(git show $upstream | git patch-id)" 157 upstream=($upstream) 158 if [ "$entry_id" == "${upstream[0]}" ]; then 159 echo -e " | ${upstream[1]} via $entry_sha (\"$entry_sub\")" 160 else 161 echo -e " | Warning: No commit correlation found! via $entry_sha (\"$entry_sub\")" 162 fi 163 done < $tmp_file 164 echo " v (end)" 165 rm -f $tmp_file 166 } 167 168 ############################################################################### 169 # MAIN 170 ############################################################################### 171 # Initialize and save up to 10 (rotated logs) 172 MYLOG=/tmp/$PROG.log 173 REMOTE="$(get_remote)" 174 # Check token 175 gitlib::github_api_token 176 177 echo "Checking for backports on branch '${STABLE_BRANCH}'" 178 179 stable_prs=($(get_prs "needs-backport/${STABLE_BRANCH}" "backport-done/${STABLE_BRANCH}")) 180 echo -e "v$STABLE_BRANCH backports $(date +%Y-%m-%d)\n" | tee $SUMMARY_LOG 181 echo -e "PRs for stable backporting: ${#stable_prs[@]}\n" 182 183 if [[ ${#stable_prs[@]} > 0 ]]; then 184 SAVEIFS=$IFS 185 IFS=$'\n' sorted_prs=($(sort <<<"${stable_prs[*]}")) 186 IFS=$'\n' stable_prs=($(cut -d'#' -f 2 <<<"${sorted_prs[*]}")) 187 IFS=$SAVEIFS 188 189 for dated_pr in "${sorted_prs[@]}"; do 190 merged_at=$(echo "$dated_pr" | cut -d'#' -f 1) 191 pr=$(echo "$dated_pr" | cut -d'#' -f 2) 192 title=$(extract_pr_title "$pr") 193 echo " * PR: $pr -- $title -- https://github.com/cilium/cilium/pull/$pr" 194 if [[ ! -z $SUMMARY_LOG ]]; then 195 echo " * #$pr -- $title" >> $SUMMARY_LOG 196 fi 197 generate_commit_list_for_pr $pr $merged_at 198 echo "" 199 done 200 echo "When you have backported the above commits, you can update the PR labels via this command:" 201 echo "$ for pr in ${stable_prs[@]}; do contrib/backporting/set-labels.py \$pr pending ${STABLE_BRANCH}; done" 202 if [[ ! -z $SUMMARY_LOG ]]; then 203 echo -e "\nOnce this PR is merged, you can update the PR labels via:" >> $SUMMARY_LOG 204 echo "\`\`\`upstream-prs" >> $SUMMARY_LOG 205 echo "$ for pr in ${stable_prs[@]}; do contrib/backporting/set-labels.py \$pr done ${STABLE_BRANCH}; done" >> $SUMMARY_LOG 206 echo "\`\`\`" >> $SUMMARY_LOG 207 fi 208 fi