Message ID | 8de0c0eb228c8d9608d3a78c992cbd6829cb9329.1606173607.git.gitgitgadget@gmail.com (mailing list archive) |
---|---|
State | Superseded |
Headers | show |
Series | Add helpful advice about init.defaultBranch | expand |
"Johannes Schindelin via GitGitGadget" <gitgitgadget@gmail.com> writes: > @@ -538,7 +538,8 @@ static void copy_or_rename_branch(const char *oldname, const char *newname, int > strbuf_addf(&logmsg, "Branch: renamed %s to %s", > oldref.buf, newref.buf); > > - if (!copy && rename_ref(oldref.buf, newref.buf, logmsg.buf)) > + if (!copy && (oldname != head || !is_null_oid(&head_oid)) && It always makes readers uneasy to see pointer comparison of two strings. Does this mean, after "git -c init.defaultbranch=master init", git branch -m master main would not work while git branch -m main would? It would be easy to see with the attached patch to the test, I guess. > + rename_ref(oldref.buf, newref.buf, logmsg.buf)) > die(_("Branch rename failed")); > if (copy && copy_existing_ref(oldref.buf, newref.buf, logmsg.buf)) > die(_("Branch copy failed")); > diff --git a/t/t0001-init.sh b/t/t0001-init.sh > index 69a320489f..69c5ad179c 100755 > --- a/t/t0001-init.sh > +++ b/t/t0001-init.sh > @@ -571,4 +571,10 @@ test_expect_success 'invalid default branch name' ' > test_i18ngrep "invalid branch name" err > ' > > +test_expect_success 'branch -m with the initial branch' ' > + git init rename-initial-branch && > + git -C rename-initial-branch branch -m renamed && > + test renamed = $(git -C rename-initial-branch symbolic-ref --short HEAD) > +' > + > test_done Thanks. t/t0001-init.sh | 6 ++++++ 1 file changed, 6 insertions(+) diff --git c/t/t0001-init.sh w/t/t0001-init.sh index 69c5ad179c..07c34431d9 100755 --- c/t/t0001-init.sh +++ w/t/t0001-init.sh @@ -577,4 +577,10 @@ test_expect_success 'branch -m with the initial branch' ' test renamed = $(git -C rename-initial-branch symbolic-ref --short HEAD) ' +test_expect_success 'branch -m with the initial branch' ' + git -c init.defaultBranch=initial init rename-unborn-branch && + git -C rename-unborn-branch branch -m initial renamed && + test renamed = $(git -C rename-unborn-branch symbolic-ref --short HEAD) +' + test_done
Hi Junio, On Mon, 23 Nov 2020, Junio C Hamano wrote: > "Johannes Schindelin via GitGitGadget" <gitgitgadget@gmail.com> > writes: > > > @@ -538,7 +538,8 @@ static void copy_or_rename_branch(const char *oldname, const char *newname, int > > strbuf_addf(&logmsg, "Branch: renamed %s to %s", > > oldref.buf, newref.buf); > > > > - if (!copy && rename_ref(oldref.buf, newref.buf, logmsg.buf)) > > + if (!copy && (oldname != head || !is_null_oid(&head_oid)) && > > It always makes readers uneasy to see pointer comparison of two > strings. Even if it was on purpose ;-) > Does this mean, after "git -c init.defaultbranch=master init", > > git branch -m master main > > would not work while > > git branch -m main > > would? It would be easy to see with the attached patch to the test, > I guess. At first, I thought that it would be inappropriate to do that because it would not work with unborn branches in a worktree other than the current one. Like, git worktree add --no-checkout --detach other git -C other switch --orphan start-over-again git branch -m start-over-again fresh-new-start On second thought, that's a really obscure use case, anyway. It is not even possible to create a secondary worktree! I started down that rabbit hole, but think I'd better let it be. This is where I stopped: -- snip -- diff --git a/builtin/branch.c b/builtin/branch.c index 200da319f1d..c84bffe9632 100644 --- a/builtin/branch.c +++ b/builtin/branch.c @@ -489,6 +489,16 @@ static void reject_rebase_or_bisect_branch(const char *target) free_worktrees(worktrees); } +static int is_unborn_branch(const char *branch_name, const char *full_ref_name) +{ + int flags; + + return (head && !strcmp(branch_name, head) && is_null_oid(&head_oid)) || + (!resolve_ref_unsafe(full_ref_name, RESOLVE_REF_READING, NULL, + &flags) && + find_shared_symref("HEAD", full_ref)); +} + static void copy_or_rename_branch(const char *oldname, const char *newname, int copy, int force) { struct strbuf oldref = STRBUF_INIT, newref = STRBUF_INIT, logmsg = STRBUF_INIT; @@ -538,8 +548,7 @@ static void copy_or_rename_branch(const char *oldname, const char *newname, int strbuf_addf(&logmsg, "Branch: renamed %s to %s", oldref.buf, newref.buf); - if (!copy && - (!head || strcmp(oldname, head) || !is_null_oid(&head_oid)) && + if (!copy && !is_unborn_branch(oldname, oldref.buf) && rename_ref(oldref.buf, newref.buf, logmsg.buf)) die(_("Branch rename failed")); if (copy && copy_existing_ref(oldref.buf, newref.buf, logmsg.buf)) diff --git a/t/t0001-init.sh b/t/t0001-init.sh index 84047ac64e6..124abeedf19 100755 --- a/t/t0001-init.sh +++ b/t/t0001-init.sh @@ -586,4 +586,12 @@ test_expect_success 'branch -m with the initial branch' ' test again = $(git -C rename-initial symbolic-ref --short HEAD) ' +test_expect_success 'branch -m with the initial branch in another worktree' ' + git -c init.defaultBranch=initial init rename-two && + test_commit -C rename-two initial && + git -C rename-two worktree add --no-checkout ../rename-worktree && + git -C rename-worktree switch --orphan brand-new-day && + git -C rename-two branch -m brand-new-day renamed +' + test_done -- snap -- Having said that, I fixed the `git branch -m <current-unborn> <new-name>` use case; the fix will be part of v3. Ciao, Dscho
Johannes Schindelin <Johannes.Schindelin@gmx.de> writes: >> > - if (!copy && rename_ref(oldref.buf, newref.buf, logmsg.buf)) >> > + if (!copy && (oldname != head || !is_null_oid(&head_oid)) && >> >> It always makes readers uneasy to see pointer comparison of two >> strings. > > Even if it was on purpose ;-) FWIW, for fun I dropped "oldname != head ||" and tried to run the whole testsuite (plus the "branch -m src dst" form test I gave earlier), and it almost passed all of them except one, which was surprising. > + if (!copy && !is_unborn_branch(oldname, oldref.buf) && > rename_ref(oldref.buf, newref.buf, logmsg.buf)) Yeah, a helper function makes it much more clear what is going on. > Having said that, I fixed the `git branch -m <current-unborn> <new-name>` > use case; the fix will be part of v3. ;-)
diff --git a/builtin/branch.c b/builtin/branch.c index efb30b8820..10609981e6 100644 --- a/builtin/branch.c +++ b/builtin/branch.c @@ -538,7 +538,8 @@ static void copy_or_rename_branch(const char *oldname, const char *newname, int strbuf_addf(&logmsg, "Branch: renamed %s to %s", oldref.buf, newref.buf); - if (!copy && rename_ref(oldref.buf, newref.buf, logmsg.buf)) + if (!copy && (oldname != head || !is_null_oid(&head_oid)) && + rename_ref(oldref.buf, newref.buf, logmsg.buf)) die(_("Branch rename failed")); if (copy && copy_existing_ref(oldref.buf, newref.buf, logmsg.buf)) die(_("Branch copy failed")); diff --git a/t/t0001-init.sh b/t/t0001-init.sh index 69a320489f..69c5ad179c 100755 --- a/t/t0001-init.sh +++ b/t/t0001-init.sh @@ -571,4 +571,10 @@ test_expect_success 'invalid default branch name' ' test_i18ngrep "invalid branch name" err ' +test_expect_success 'branch -m with the initial branch' ' + git init rename-initial-branch && + git -C rename-initial-branch branch -m renamed && + test renamed = $(git -C rename-initial-branch symbolic-ref --short HEAD) +' + test_done