Re: Is origin/HEAD only being created on clone a bug? #leftoverbits
On Wed, May 30, 2018 at 11:46:16AM +0900, Junio C Hamano wrote: > Junio C Hamano writes: > > > - When we fetch from a remote that has refs/remotes/$name/HEAD, and > >if the protocol notices that their HEAD today is pointing to a > >branch different from what our side has, should we repoint ours > >to match? > > > >I am leaning against doing this, but mostly out of superstition. > > ... > >interested in". But once fetch starts messing with where > >origin/HEAD points at, that would no longer be the case, which is > >why I am against doing something magical like that. > > Well, I shouldn't say "I am against" on the last line; rather, "I > feel uneasy". I didn't bother to dig up the past discussions, but I am pretty sure we intentionally avoided updating origin/HEAD without an explicit action from the user. Because what the other side considers "the default branch" and what you consider "the default branch" when dealing with the remote are not necessarily the same thing. If we auto-adjust the symref on fetch, we might be undoing the user's previous "git remote set-head" operation. I don't have any real problem with creating it if it _doesn't_ exist, though. (I think ideally it would get created by "remote add", but that command does not always talk to the remote, so this kind of delayed-create is probably the best we can do). -Peff
Re: Is origin/HEAD only being created on clone a bug? #leftoverbits
Ævar Arnfjörð Bjarmason writes: > We already have to deal with this special case of origin/HEAD > being re-pointed in a repository that we "clone", so we would just > do whatever happens to a repository that's cloned. OK. Not visiting that issue while we discuss this "origin/HEAD is useful, so create it even for non-initial-clone case" topic makes it simpler to discuss.
Re: Is origin/HEAD only being created on clone a bug? #leftoverbits
On Wed, May 30 2018, Junio C Hamano wrote: > Ævar Arnfjörð Bjarmason writes: > >> If you make an initial commit and push to a remote repo "origin", you >> don't get a remote origin/HEAD reference, and a "fetch" won't create it >> either. >> ... >> Some code spelunking reveals remote_head_points_at, guess_remote_head() >> etc. in builtin/clone.c. I.e. this is special-cased as part of the >> "clone". > > Correct. Originally, there was *no* way in the protocol to carry > the information, so the code always had to guess. The point of > setting origin/HEAD was mostly so that you can say "log origin.." > and rely on it getting dwimmed down to "refs/remotes/%s/HEAD..", > and it wasn't a common practice to interact with multiple remotes > with remote tracking branches (integrator interacting with dozens > of remotes, responding to pull requests using explicit URL but > without configured remotes was not uncommon), so it was sufficient > for "git clone" to create it, and "git remote add" did not exist > back then anyway. > > There are two aspects in my answer to your question. > > - If we create additional remote (that is, other than the one we >get when we create a repository via "clone", so if your "origin" >is from "git init there && cd there && git remote add origin", it >does count in this category), should we get a remote-tracking >symref $name/HEAD so that we can say "log $name.."? > >We absolutely should. We (eh, rather, those who added "remote >add"; this was not my itch and I am using "royal we" in this >sentence) just did not bother to and I think it is a bug that you >cannot say "log $name.." Of course, it is just a "git symbolic-ref" >away to make it possible locally, so it is understandable if >"remote add" did not bother to. > > - When we fetch from a remote that has refs/remotes/$name/HEAD, and >if the protocol notices that their HEAD today is pointing to a >branch different from what our side has, should we repoint ours >to match? > >I am leaning against doing this, but mostly out of superstition. >Namely, I feel uneasy about the fact that the meaning of "log >..origin" changes across a fetch in this sequence: > > log ..origin && fetch origin && log ..origin > >Without repointing origin/HEAD, two occurrences of "log ..origin" >both means "how much ahead the primary branch we have been >interested in from this remote is, relative to our effort?". >Even though we fully expect that two "log ..origin" would report >different results (after all, that is the whole point of doing >another one after "fetch" in such a sequence like this example), >our question is about the same "primary branch we have been >interested in". But once fetch starts messing with where >origin/HEAD points at, that would no longer be the case, which is >why I am against doing something magical like that. We already have to deal with this special case of origin/HEAD being re-pointed in a repository that we "clone", so we would just do whatever happens to a repository that's cloned. I.e. the "clone" sets the origin/HEAD up as a one-off, and then keeps updating it on the basis of updating existing refs. We'd similarly set it up as a one-off if we ever "fetch" and notice that the ref doesn't exist yet, and then we'd update it in the same way we update it now. So this seems like a non-issue to me as far as me coming up with some patch to one-off write the origin/HEAD on the first "fetch", or am I missing something?
Re: Is origin/HEAD only being created on clone a bug? #leftoverbits
Junio C Hamano writes: > - When we fetch from a remote that has refs/remotes/$name/HEAD, and >if the protocol notices that their HEAD today is pointing to a >branch different from what our side has, should we repoint ours >to match? > >I am leaning against doing this, but mostly out of superstition. > ... >interested in". But once fetch starts messing with where >origin/HEAD points at, that would no longer be the case, which is >why I am against doing something magical like that. Well, I shouldn't say "I am against" on the last line; rather, "I feel uneasy".
Re: Is origin/HEAD only being created on clone a bug? #leftoverbits
Ævar Arnfjörð Bjarmason writes: > If you make an initial commit and push to a remote repo "origin", you > don't get a remote origin/HEAD reference, and a "fetch" won't create it > either. > ... > Some code spelunking reveals remote_head_points_at, guess_remote_head() > etc. in builtin/clone.c. I.e. this is special-cased as part of the > "clone". Correct. Originally, there was *no* way in the protocol to carry the information, so the code always had to guess. The point of setting origin/HEAD was mostly so that you can say "log origin.." and rely on it getting dwimmed down to "refs/remotes/%s/HEAD..", and it wasn't a common practice to interact with multiple remotes with remote tracking branches (integrator interacting with dozens of remotes, responding to pull requests using explicit URL but without configured remotes was not uncommon), so it was sufficient for "git clone" to create it, and "git remote add" did not exist back then anyway. There are two aspects in my answer to your question. - If we create additional remote (that is, other than the one we get when we create a repository via "clone", so if your "origin" is from "git init there && cd there && git remote add origin", it does count in this category), should we get a remote-tracking symref $name/HEAD so that we can say "log $name.."? We absolutely should. We (eh, rather, those who added "remote add"; this was not my itch and I am using "royal we" in this sentence) just did not bother to and I think it is a bug that you cannot say "log $name.." Of course, it is just a "git symbolic-ref" away to make it possible locally, so it is understandable if "remote add" did not bother to. - When we fetch from a remote that has refs/remotes/$name/HEAD, and if the protocol notices that their HEAD today is pointing to a branch different from what our side has, should we repoint ours to match? I am leaning against doing this, but mostly out of superstition. Namely, I feel uneasy about the fact that the meaning of "log ..origin" changes across a fetch in this sequence: log ..origin && fetch origin && log ..origin Without repointing origin/HEAD, two occurrences of "log ..origin" both means "how much ahead the primary branch we have been interested in from this remote is, relative to our effort?". Even though we fully expect that two "log ..origin" would report different results (after all, that is the whole point of doing another one after "fetch" in such a sequence like this example), our question is about the same "primary branch we have been interested in". But once fetch starts messing with where origin/HEAD points at, that would no longer be the case, which is why I am against doing something magical like that.
Re: Is origin/HEAD only being created on clone a bug? #leftoverbits
On 05/29, Ævar Arnfjörð Bjarmason wrote: > Here's some more #leftoverbits where we have a clone/fetch feature > discrepancy and where clone is magical in ways that "fetch" isn't. > > If you make an initial commit and push to a remote repo "origin", you > don't get a remote origin/HEAD reference, and a "fetch" won't create it > either. > > You will get it if you subseuqently "clone" the repo, but not if you use > "git init / remote add / fetch / git checkout -t" which should otherwise > be equivalent. > > If you push to "master" (or whatever HEAD is) from the clone the > origin/HEAD will be updated accordingly, but from the repo you pushed > from & the one you did init+fetch instead of clone you'll never see it. > > Some code spelunking reveals remote_head_points_at, guess_remote_head() > etc. in builtin/clone.c. I.e. this is special-cased as part of the > "clone". > > Can anyone thing of a reason for why this shouldn't be fixed as a bug? > I've tried searching the archives but "origin/HEAD" comes up with too > many > results. > https://public-inbox.org/git/alpine.lsu.1.00.0803020556380.22...@racer.site/#t > seems to be the patch that initially added it, but it is not discussed > why this should be a clone-only special case that doesn't apply to > "fetch". I believe the issue has to deal with how symrefs are handled. I don't think any of the fetch code path does anything special with symrefs. Symref info does get sent over the wire for the HEAD symref but i think its just ignored. You'll see updates for origin/HEAD when you subsequently fetch most likely because its recorded as a symref locally which points at origin/master. This means that when you fetch origin/master, origin/HEAD will also but updated just because its locally a pointer to origin/master. With that said, yes we should probably fix this issue with fetch because I added symref support to protocol v2 so now symref information for refs other than HEAD can be sent across the wire but the client just throws that info away at the moment. -- Brandon Williams