Code

filter-branch: Add more error-handling
authorEric Kidd <git@randomhacks.net>
Wed, 11 Feb 2009 21:10:41 +0000 (16:10 -0500)
committerJunio C Hamano <gitster@pobox.com>
Thu, 12 Feb 2009 02:26:52 +0000 (18:26 -0800)
9273b56 (filter-branch: Fix fatal error on bare repositories, 2009-02-03)
fixed a missing check of return status from an underlying command in
git-filter-branch, but there still are places that do not check errors.
For example, the command does not pay attention to the exit status of the
command given by --commit-filter.  It should abort in such a case.

This attempts to fix all the remaining places that fails to checks errors.

In two places, I've had to break apart pipelines in order to check the
error code for the first stage of the pipeline, as discussed here:

  http://kerneltrap.org/mailarchive/git/2009/1/28/4835614

Feedback on this patch was provided by Johannes Sixt, Johannes Schindelin
and Junio C Hamano.  Thomas Rast helped with pipeline error handling.

Signed-off-by: Eric Kidd <git@randomhacks.net>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
git-filter-branch.sh
t/t7003-filter-branch.sh

index 86eef562978f331f1d6e8f187dfc44e3fdd03e16..27b57b826a26d80551169b355a5e8fc1a35de994 100755 (executable)
@@ -221,7 +221,7 @@ die ""
 trap 'cd ../..; rm -rf "$tempdir"' 0
 
 # Make sure refs/original is empty
-git for-each-ref > "$tempdir"/backup-refs
+git for-each-ref > "$tempdir"/backup-refs || exit
 while read sha1 type name
 do
        case "$force,$name" in
@@ -241,8 +241,9 @@ GIT_WORK_TREE=.
 export GIT_DIR GIT_WORK_TREE
 
 # The refs should be updated if their heads were rewritten
-git rev-parse --no-flags --revs-only --symbolic-full-name --default HEAD "$@" |
-sed -e '/^^/d' >"$tempdir"/heads
+git rev-parse --no-flags --revs-only --symbolic-full-name \
+       --default HEAD "$@" > "$tempdir"/raw-heads || exit
+sed -e '/^^/d' "$tempdir"/raw-heads >"$tempdir"/heads
 
 test -s "$tempdir"/heads ||
        die "Which ref do you want to rewrite?"
@@ -251,8 +252,6 @@ GIT_INDEX_FILE="$(pwd)/../index"
 export GIT_INDEX_FILE
 git read-tree || die "Could not seed the index"
 
-ret=0
-
 # map old->new commit ids for rewriting parents
 mkdir ../map || die "Could not create map/ directory"
 
@@ -315,10 +314,11 @@ while read commit parents; do
                        die "tree filter failed: $filter_tree"
 
                (
-                       git diff-index -r --name-only $commit
+                       git diff-index -r --name-only $commit &&
                        git ls-files --others
-               ) |
-               git update-index --add --replace --remove --stdin
+               ) > "$tempdir"/tree-state || exit
+               git update-index --add --replace --remove --stdin \
+                       < "$tempdir"/tree-state || exit
        fi
 
        eval "$filter_index" < /dev/null ||
@@ -339,7 +339,8 @@ while read commit parents; do
                eval "$filter_msg" > ../message ||
                        die "msg filter failed: $filter_msg"
        @SHELL_PATH@ -c "$filter_commit" "git commit-tree" \
-               $(git write-tree) $parentstr < ../message > ../map/$commit
+               $(git write-tree) $parentstr < ../message > ../map/$commit ||
+                       die "could not write rewritten commit"
 done <../revs
 
 # In case of a subdirectory filter, it is possible that a specified head
@@ -407,7 +408,8 @@ do
                        die "Could not rewrite $ref"
        ;;
        esac
-       git update-ref -m "filter-branch: backup" "$orig_namespace$ref" $sha1
+       git update-ref -m "filter-branch: backup" "$orig_namespace$ref" $sha1 ||
+                exit
 done < "$tempdir"/heads
 
 # TODO: This should possibly go, with the semantics that all positive given
@@ -483,7 +485,7 @@ test -z "$ORIG_GIT_INDEX_FILE" || {
 }
 
 if [ "$(is_bare_repository)" = false ]; then
-       git read-tree -u -m HEAD
+       git read-tree -u -m HEAD || exit
 fi
 
-exit $ret
+exit 0
index cb0474336d66302d9c7cf003bcdeadacb789aa8a..56b5eccdb4a0563b4df22e2af679b08b66ef6ae1 100755 (executable)
@@ -48,6 +48,10 @@ test_expect_success 'result is really identical' '
        test $H = $(git rev-parse HEAD)
 '
 
+test_expect_success 'Fail if commit filter fails' '
+       test_must_fail git filter-branch -f --commit-filter "exit 1" HEAD
+'
+
 test_expect_success 'rewrite, renaming a specific file' '
        git filter-branch -f --tree-filter "mv d doh || :" HEAD
 '