Skip to content

Instantly share code, notes, and snippets.

@3v1n0
Last active October 4, 2018 18:54
Show Gist options
  • Save 3v1n0/63ea0c9f08d10bee9e50 to your computer and use it in GitHub Desktop.
Save 3v1n0/63ea0c9f08d10bee9e50 to your computer and use it in GitHub Desktop.
A tool for cherry-picking revisions from bazaar repositories
#!/bin/bash
#
# Simply cherry picks a revision from a bazaar branch, cloning its metadata
#
# Usage:
# bzr-cherry-pick lp:unity 1234
if ! (bzr root &> /dev/null); then
echo "It seems you're not in a bazaar branch directory"
exit 1
fi
if [ -z "$1" ]; then
echo "$(basename $0) <branch location> <revision number> [--debchange] [--no-commit] [--use-merge]"
exit 1
fi
if ! [[ $2 =~ ^-?[0-9]+$ ]]; then
echo "You need to provide the revision number you want to pick"
exit 1
fi
if [ "$(bzr diff | head -n1 | wc -l)" -gt 0 ]; then
echo "Impossible to work in a branch which has uncommitted changes"
exit 1
fi
branch=$1
shift
rev=$1
shift
cmdline_args=$*
use_debchange=false
no_commit=false
use_merge=false
if (echo "$cmdline_args" | grep -q -w -- "--debchange"); then
cmdline_args="${cmdline_args//--debchange/}"
if [ -f debian/changelog ]; then
use_debchange=true
fi
fi
if (echo "$cmdline_args" | grep -q -w -- "--no-commit"); then
cmdline_args="${cmdline_args//--no-commit/}"
no_commit=true
fi
if (echo "$cmdline_args" | grep -q -w -- "--use-merge"); then
cmdline_args="${cmdline_args//--use-merge/}"
use_merge=true
fi
export LC_ALL=C.UTF-8
log="$(bzr log -n1 -r $rev $branch $cmdline_args)"
log_msg="$(echo "$log" | sed '0,/^message:$/d' | tail -n +1 | sed -e 's/^\s*//' | sed '/^Approved by: /d')"
log_author="$(echo "$log" | sed -n 's/^author: //p')"
log_time="$(echo "$log" | sed -n 's/^timestamp: \([A-Za-z]\+ \)\?//p')"
log_bugs="$(echo "$log" | sed -n 's/^fixes bugs\?: //p' | sed 's,https://launchpad.net/bugs/,,g')"
if [ -z "$log_author" ]; then
log_author="$(echo "$log" | sed -n 's/^committer: //p')"
fi
if [ -z "$log_author" ]; then log_author="$(bzr whoami)"; fi
if [ -z "$log_bugs" ]; then log_bugs="$(echo "$log_msg" | sed '/Fixes: #[0-9]\+/!d' | sed 's/.*Fixes: #\([0-9#, ]\+\).*/\1/m' | sed 's/[,#]//g')"; fi
if [ -z "$log_bugs" ]; then log_bugs="$(echo "$log_msg" | sed '/(LP: [^)]\+)/!d' | sed 's/.*(LP: \([^)]\+\)).*/\1/m' | sed 's/[,#]//g')"; fi
log_msg=$(echo "$log_msg" | sed 's/Fixes: #[0-9, #]\+//')
log_msg=$(echo "$log_msg" | sed 's/(LP: [^)]\+)//')
if [ "$log_author" == "Bileto Bot <[email protected]>" ]; then
echo "Ignoring release commit..."
exit 0
fi
echo "Author: $log_author"
echo "Time: $log_time"
for bug in $log_bugs; do echo "Bug: https://launchpad.net/bugs/$bug"; done;
echo -e "Message:\n$log_msg\n"
if [ "$use_merge" == true ]; then
bzr merge --no-remember -c $rev $branch $cmdline_args
merged=$?
else
bzr di -c $rev $branch $cmdline_args | patch -p0
merged=$?
for i in $(bzr di -c $rev $branch $cmdline_args | lsdiff); do
bzr add $i
done
fi
if [ "$merged" == 0 ] && [ "$(bzr di | head -n1 | wc -l)" == 0 ]; then
echo "Revision $rev has no changes to merge, ignoring it..."
exit 0
fi
# msg_file=$(mktemp /tmp/bzr-cherry-pick.XXXXXXX)
# echo "$log_msg" > $msg_file
args="--message=\"${log_msg//\"/\\\"}\" --author=\"${log_author//\"/\\\"}\" --commit-time=\"$log_time\""
for bug in $log_bugs; do args="$args --fixes=\"lp:$bug\""; done;
if [ $use_debchange == true ]; then
change="$(echo "$log_msg" | head -n1)"
if [ -n "$log_bugs" ]; then
read -r -a bugs_array <<< "$log_bugs"
change="$change ($(printf "LP: #%s, " "${bugs_array[@]}")"
change=${change%, }")"
fi
unset DEBFULLNAME DEBEMAIL NAME EMAIL
export DEBFULLNAME="$(echo "$log_author" | sed "s/\([^<]*\)<\([^>]\+\)>/\1/g" | sed -e 's/ *$//')"
export DEBEMAIL="$(echo "$log_author" | sed "s/[^<]*<\([^>]\+\)>/\1/g" | sed -e 's/ *$//')"
debchange --multimaint-merge --release-heuristic changelog -- $change
fi
if [ $no_commit == true ]; then
echo -e "No committing, you can do this manually by using\n bzr commit $args"
exit $merged
fi
if [ $merged == 0 ]; then
if [ "$(bzr di | head -n1 | wc -l)" -gt 0 ]; then
#echo bzr commit "$args"
eval "$(echo bzr commit "$args")"
fi
else
if [ "$(bzr conflicts -q | head -n1 | wc -l)" -gt 0 ]; then
echo -e "\nMerging of version $rev failed, impossible to commit. Please use 'bzr resolve' to fix the issues and then commit with\n bzr commit $args"
exit 1
fi
fi
# rm -f $msg_file
@3v1n0
Copy link
Author

3v1n0 commented Jun 27, 2017

Thanks @Ede123, I've added it

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment