On 1/17/2020 2:13 PM, Junio C Hamano wrote: > "Derrick Stolee via GitGitGadget" <gitgitgadget@xxxxxxxxx> writes: > >> From: Derrick Stolee <dstolee@xxxxxxxxxxxxx> >> >> To prevent long blocking time during a 'git fetch' call, a user >> may want to set up a schedule for background 'git fetch' processes. >> However, these runs will update the refs/remotes branches, and >> hence the user will not notice when remote refs are updated during >> their foreground fetches. In fact, they may _want_ those refs to >> stay put so they can work with the refs from their last foreground >> fetch call. > > I've always hated anything that makes the remote-tracking refs > "float" and surprise end users. I even hated that 'git push' that > pretends as if we immediately turned around and fetched from the > remote we just pushed when it was introduced, even though I gave up > by now. > > So I am OK in principle to make it more difficult to update > refs/remotes/* while the end-user is looking the other way, but I > had to wonder why "git fetch" is even being done if it is done to > silently update/catch-up remote-tracking branches automatically in > the first place. > > This is more like a "preload" option---without updating the end-user > visible set of remote-tracking branches, you can make the data > available earlier so that the actual "fetch" the end-user runs in > order to update the remote-tracking branches can complete faster and > become ready to be used more quickly. > > Which makes sense. Yes, we get the pack data earlier, and that's the primary cost of the fetch command. We can also update the commit-graph using the hidden refs. >> Add a --[no-]update-remote-refs option to 'git fetch' which defaults >> to the existing behavior of updating the remote refs. This allows >> a user to run >> >> git fetch <remote> --no-update-remote-refs +refs/heads/*:refs/hidden/* >> >> to populate a custom ref space and download a pack of the new >> reachable objects. > > Hmph. I have to wonder if this should have been the default. That > is, when refs/heads/X on the remote is configured to be copied to > refs/remotes/origin/X on this side, and an explicit refspec says it > should go some other place (i.e. refs/hidden/X), shouldn't that > automatically bypass configured +refs/heads/*:refs/remotes/origin/* > refspec? In any case, it is too late to change that now. > >> This kind of call allows a few things to happen: >> >> 1. We download a new pack if refs have updated. >> 2. Since the refs/hidden branches exist, GC will not remove the >> newly-downloaded data. > > Caution. Since you didn't make it "refs/hidden/<remote>/*", you > just made the data you fetched the same way with this shiny new > "--no-update-remote-tracking-branches" option from another remote > unanchored and susceptible to GCs. You're right. I neglected to say "refs/hidden/<remote>/*" in my message, but it _is_ something I've been doing in my background fetches. >> 3. With fetch.writeCommitGraph enabled, the refs/hidden refs are >> used to update the commit-graph file. > > I have a moderately strong suspicion that it would be better to make > this "--ignore-configured-refspecs" and implemented without special > casign the "refs/remotes/" hierarchy like the code does by > hardcoding. Based on this and Peff's response, I think you are pointing me in a better direction with this. It should make the change less of a hack and also make it more general to users with custom refspecs. > I also wonder if auto-following of tags should be disabled at the > same time. I have no good argument either way (yet). Would ignoring the configured refspecs stop auto-following tags? I'll take a look and see. Otherwise, I'll add --no-tags to my background fetch command. Thanks! -Stolee