aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDaniel Barkalow <barkalow@iabervon.org>2008-09-21 14:36:06 -0400
committerJunio C Hamano <gitster@pobox.com>2008-09-21 23:17:06 -0700
commit352eadc40024b141e1295693654ec20cc123844f (patch)
tree240eec2143c0d447bcea9aec3a56323abe4d909e
parentcc185a6a8ac24737a26ec4b40cc401c2db8b2e97 (diff)
downloadgit-352eadc40024b141e1295693654ec20cc123844f.tar.gz
git-352eadc40024b141e1295693654ec20cc123844f.tar.xz
Check early that a new branch is new and valid
If you fail to update refs to change branches in checkout, your index and working tree are left already updated. We don't have an easy way to undo this, but at least we can check things that would make the creation of a new branch fail. These checks were in the shell version, and were lost in the C conversion. The messages are from the shell version, and should probably be made nicer. [jc: added test to t7201] Signed-off-by: Daniel Barkalow <barkalow@iabervon.org> Signed-off-by: Junio C Hamano <gitster@pobox.com>
-rw-r--r--builtin-checkout.c12
-rwxr-xr-xt/t7201-co.sh10
2 files changed, 22 insertions, 0 deletions
diff --git a/builtin-checkout.c b/builtin-checkout.c
index 08c6d8614..1ee23468f 100644
--- a/builtin-checkout.c
+++ b/builtin-checkout.c
@@ -565,6 +565,18 @@ no_reference:
return checkout_paths(source_tree, pathspec);
}
+ if (opts.new_branch) {
+ struct strbuf buf;
+ strbuf_init(&buf, 0);
+ strbuf_addstr(&buf, "refs/heads/");
+ strbuf_addstr(&buf, opts.new_branch);
+ if (!get_sha1(buf.buf, rev))
+ die("git checkout: branch %s already exists", opts.new_branch);
+ if (check_ref_format(buf.buf))
+ die("git checkout: we do not like '%s' as a branch name.", opts.new_branch);
+ strbuf_release(&buf);
+ }
+
if (new.name && !new.commit) {
die("Cannot switch branch to a non-commit.");
}
diff --git a/t/t7201-co.sh b/t/t7201-co.sh
index fbec70d3c..0679abd29 100755
--- a/t/t7201-co.sh
+++ b/t/t7201-co.sh
@@ -359,4 +359,14 @@ test_expect_success 'checkout an unmerged path should fail' '
test_cmp sample file
'
+test_expect_success 'failing checkout -b should not break working tree' '
+ git reset --hard master &&
+ git symbolic-ref HEAD refs/heads/master &&
+ test_must_fail git checkout -b renamer side^ &&
+ test $(git symbolic-ref HEAD) = refs/heads/master &&
+ git diff --exit-code &&
+ git diff --cached --exit-code
+
+'
+
test_done