-
-
Save z0u/1740799 to your computer and use it in GitHub Desktop.
Creates a patch file between svn branch and git branch
This file contains 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
#!/bin/bash | |
# | |
# git-svn-diff originally by (http://mojodna.net/2009/02/24/my-work-git-workflow.html) | |
# modified by mike@mikepearce.net | |
# modified by aconway@[redacted] - handle diffs that introduce new files | |
# modified by t.broyer@ltgt.net - fixes diffs that introduce new files | |
# modified by m@rkj.me - fix sed syntax issue in OS X | |
# modified by alex@phatcore.com - search for last SVN commit; allow diff | |
# against non-tracking branch; remove function names on @@ lines. | |
# | |
# SYNOPSIS | |
# git-svn-diff.sh [commit] | |
# | |
# Generate an SVN-compatible diff. If no arguments are provided, the diff will | |
# be against the most recent SVN revision on this branch. Otherwise, the diff | |
# will be against the specified commit (or branch). This is handy in the | |
# situation where you have a local base branch containing commits that will | |
# never be pushed to SVN, like so: | |
# | |
# ---A---B---C origin/master or remotes/git-svn | |
# \ \ | |
# D---E---F master | |
# \ | |
# G---H---I feature | |
# | |
# In this case, use `git checkout feature; git-svn-diff.sh master`. The patch | |
# will apply against commit B (and will be annotated with the SVN revision of | |
# B), but won't include D, E and F. After committing the patch to SVN, merge | |
# the remote into master and forget the feature branch. | |
# | |
# ---A---B---C---I' origin/master or remotes/git-svn | |
# \ \ \ | |
# D---E---F---I" master | |
# \ | |
# G---H---I (deleted) | |
# | |
convert-to-svn-rev() { | |
echo -n "Searching for SVN revision" >&2 | |
while read rev; do | |
echo -n . >&2 | |
svnRev=$(git svn find-rev $rev) | |
if [ "x$svnRev" != x ]; then | |
echo >&2 | |
echo "git:$rev svn:$svnRev" >&2 | |
echo $rev $svnRev | |
break | |
fi | |
done | |
} | |
# Walk through commits in reverse date order, looking for the most recent | |
# commit that came from SVN. The SVN revision of that commit is returned. | |
find-svn-rev() { | |
git rev-list --date-order --max-count=200 HEAD | convert-to-svn-rev | |
} | |
# Get the highest revision number | |
REVS=( $(find-svn-rev) ) | |
GITREV=${REVS[0]} | |
SVNREV=${REVS[1]} | |
if [ $# -gt 0 ]; then | |
REF=$* | |
else | |
REF=$GITREV | |
fi | |
# Then do the diff from the highest revision on the current branch | |
# and masssage into SVN format | |
git diff --no-prefix $REF | | |
sed -e "/--- \/dev\/null/{ N; s|^--- /dev/null\n+++ \(.*\)|--- \1 (revision 0)\n+++ \1 (revision 0)|;}" \ | |
-e "s/^--- .*/& (revision $SVNREV)/" \ | |
-e "s/^+++ .*/& (working copy)/" \ | |
-e "s/^diff --git [^[:space:]]*/Index:/" \ | |
-e "s/^\(@@ .* .* @@\).*/\1/" \ | |
-e "s/^index.*/===================================================================/" |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
This version works even when not using git-svn, e.g. when the remote repository is a clone of an SVN repository (instead of the remote actually being an SVN repository). The script does not use the tip of the tracking branch to get the SVN revision; instead, it searches for the most recent commit that was sourced from SVN. Also, this version allows making a diff against a branch other than the tracking branch.