#!/bin/bash # # Copyright 2016 The Kubernetes Authors All rights reserved. # # Licensed under the Apache License, Version 2.0 (the "License"); # you may not use this file except in compliance with the License. # You may obtain a copy of the License at # # http://www.apache.org/licenses/LICENSE-2.0 # # Unless required by applicable law or agreed to in writing, software # distributed under the License is distributed on an "AS IS" BASIS, # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. # See the License for the specific language governing permissions and # limitations under the License. # # Set PROGram name PROG=${0##*/} ######################################################################## #+ #+ NAME #+ $PROG - Fast forward a branch to master via merge #+ #+ SYNOPSIS #+ $PROG [--nomock] <branch> [master object] #+ $PROG [--helpshort|--usage|-?] #+ $PROG [--help|-man] #+ #+ DESCRIPTION #+ $PROG fast forwards a K8s release branch to [master object] (defaults to #+ HEAD and then prepares the branch as a K8s release branch: #+ * Run hack/update-all.sh to ensure compliance of generated files #+ #+ #+ OPTIONS #+ [--nomock] - Actually push this upstream #+ [--help | -man] - display man page for this script #+ [--usage | -?] - display in-line usage #+ #+ EXAMPLES #+ $PROG release-1.3 - Resync master@HEAD onto release-1.3 branch #+ $PROG release-1.3 39d0135e - Resync master@39d0135e onto release-1.3 #+ branch #+ #+ FILES #+ #+ SEE ALSO #+ lib/common.sh - base function definitions #+ lib/gitlib.sh - git function definitions #+ #+ BUGS/TODO #+ ######################################################################## # If NO ARGUMENTS should return *usage*, uncomment the following line: usage=${1:-yes} source $(dirname $(readlink -ne $BASH_SOURCE))/lib/common.sh source $TOOL_LIB_PATH/gitlib.sh # Set positional args RELEASE_BRANCH=${POSITIONAL_ARGV[0]} MASTER_OBJECT=${POSITIONAL_ARGV[1]:-"origin/master"} # Check branch format [[ $RELEASE_BRANCH =~ $BRANCH_REGEX ]] || common::exit 1 "Invalid branch name!" # Branch Exists gitlib::branch_exists $RELEASE_BRANCH \ || common::exit 1 "$RELEASE_BRANCH doesn't exist. Exiting..." ############################################################################## # Initialize logs ############################################################################## # Initialize and save up to 10 (rotated logs) MYLOG=/tmp/$PROG.log common::logfileinit $MYLOG 10 # BEGIN script common::timestamp begin gitlib::repo_state || common::exit 1 ############################################################################### # MAIN ############################################################################### BASEDIR="/usr/local/google/$USER" # WORK/BUILD area WORKDIR=$BASEDIR/$PROG-$RELEASE_BRANCH # Go tools expect the kubernetes src to be under $GOPATH export GOPATH=$WORKDIR # TREE_ROOT is working branch/tree TREE_ROOT=$WORKDIR/src/k8s.io/kubernetes # The real deal? if ((FLAGS_nomock)); then DRYRUN_FLAG="" else DRYRUN_FLAG=" --dry-run" fi logecho logecho "Follow along in detail: tailf $MYLOG" ############################################################################## common::stepheader "SESSION DETAILS" ############################################################################## logecho "$ATTENTION: This is a${DRYRUN_FLAG:-"n ACTUAL"} run!" ############################################################################## common::stepheader "SYNC A WORKING REPO" ############################################################################## if [[ -d $WORKDIR ]]; then common::askyorn "$WORKDIR exists. Delete" || common::exit 1 "Exiting..." logrun rm -rf $WORKDIR || common::exit 1 "Exiting..." fi logrun mkdir -p $WORKDIR gitlib::sync_repo $K8S_GITHUB_SSH $TREE_ROOT || common::exit 1 "Exiting..." logrun cd $TREE_ROOT # Is the master branch in a reasonable state to fast forward over the branch? # When git merges from master to branch, the list of tags is overlaid and # sorted chronologically. # MERGE_BASE: Show common ancestor object/tag # MASTER_DESCRIBE: Show the latest tag on origin/master # ANCESTOR_DESCRIBE: Show the tag associated with MERGE_BASE MERGE_BASE=$(git merge-base origin/master origin/$RELEASE_BRANCH) ANCESTOR_DESCRIBE=$(git describe --abbrev=0 --tags $MERGE_BASE) MASTER_DESCRIBE=$(git describe --abbrev=0 --tags origin/master) # If these are different, there's a newer (than the branch) tag on master # and we cannot do a FF if [[ ! $MASTER_DESCRIBE == $ANCESTOR_DESCRIBE ]]; then logecho logecho "$FATAL! master branch has been tagged to a newer version" \ "($MASTER_DESCRIBE)." \ "Unable to fast-forward $RELEASE_BRANCH branch to master." common::exit 1 fi ############################################################################## common::stepheader "CHECK GIT PUSH ACCESS" ############################################################################## # TODO: capture state of access without forcing us into a prompt I have to # expose. logecho -n "Checking git push access (verbosely to accept password if needed)" logrun -v git push -q --dry-run $K8S_GITHUB_SSH || common::exit 1 "Exiting..." ############################################################################## common::stepheader "CHECK OUT BRANCH" ############################################################################## logecho -n "Checking out $RELEASE_BRANCH: " logrun -s git checkout -b $RELEASE_BRANCH origin/$RELEASE_BRANCH \ || common::exit 1 "Exiting..." ############################################################################## common::stepheader "MERGE AND UPDATE" ############################################################################## logecho -n "Merging $MASTER_OBJECT into $RELEASE_BRANCH branch: " logrun -s git merge -X ours $MASTER_OBJECT # TODO: This should use update-all again when run-time returns to reasonable levels logecho -n "Run useful hack/update* scripts: " logecho -n "The list of scripts might be stale. If not sure, run update-all.sh:" for script in openapi-spec generated-docs federation-openapi-spec; do logecho -n "Running $script: " logrun -s "hack/update-$script.sh" done if [[ -n "$(git status -s)" ]]; then logecho -n "Commit changes: " logrun git add -A logrun -s git commit -am "update-all.sh." \ || common::exit 1 "Exiting..." fi ############################################################################## common::stepheader "PUSH UPSTREAM" ############################################################################## logecho "Go look around in $TREE_ROOT to make sure things look ok:" logecho "# Any files left uncommitted?" logecho "* git status -s" logecho "# What does the commit look like?" logecho "* git show" logecho if common::askyorn -e "OK to push now"; then # Finally push it upstream logecho -n "Pushing$DRYRUN_FLAG $RELEASE_BRANCH branch upstream: " logrun -s git push $DRYRUN_FLAG origin $RELEASE_BRANCH:$RELEASE_BRANCH fi logecho logecho "$WORKDIR left intact for reviewing" # END script common::timestamp end