git/list[1] front-page[2] threads[3] people[4] search[5] about
 

Re: [RFD/PATCH 3/5] checkout: Use remote refspecs when DWIMming tracking branches

From
Junio C Hamano <gitster@pobox.com>
Date
Apr 19, 2013, 19:44 UTC
Message-ID
<7vzjwuz4ov.fsf@alter.siamese.dyndns.org>
In-Reply-To
<1366352442-501-4-git-send-email-johan@herland.net>
Johan Herland <johan@herland.net> writes:
Show 22 quoted lines
> The DWIM mode of checkout allows you to run "git checkout foo" when there is
> no existing local ref or path called "foo", and there is exactly one remote
> with a remote-tracking branch called "foo". Git will then automatically
> create a new local branch called "foo" using the remote-tracking "foo" as
> its starting point and configured upstream.
>
> However, the current code hardcodes the assumption that all remote-tracking
> branches are located at refs/remotes/$remote/*, and that "git checkout foo"
> must find exactly one ref matching "refs/remotes/*/foo" to succeed.
> This approach fails if a user has customized the refspec of a given remote to
> place remote-tracking branches elsewhere.
>
> The better way to find a tracking branch is to use the fetch refspecs for the
> configured remotes to deduce the available candidate remote-tracking branches
> corresponding to a remote branch of the requested name, and if exactly one of
> these exists (and points to a valid SHA1), then that is the remote-tracking
> branch we will use.
>
> For example, in the case of "git checkout foo", we map "refs/heads/foo"
> through each remote's refspec to find the available candidate remote-tracking
> branches, and if exactly one of these candidates exist in our local repo, then
> we have found the upstream for the new local branch "foo".

Once you introduce a concrete "foo" as a name in the example, it would be far easier to understand if you spelled all the other assumptions in the example out.

I am _guessing_ that you mean a case like this:
	[remote "origin"]
		fetch = refs/heads/*:refs/remotes/origin/*
	[remote "xyzzy"]
		fetch = refs/heads/*:refs/remotes/xyzzy/nitfol/*
	[remote "frotz"]
		fetch = refs/heads/*:refs/remotes/frotz/nitfol/*

and refs/remotes/origin/foo or refs/remotes/frotz/nitfol/foo do not exist but refs/remotes/xyzzy/nitfol/foo does. And the user says "git checkout foo". Instead of finding a remote ref that matches "refs/remotes/*/foo" pattern (and assuming the part that matched * is the name of the remote), you can iterate the RHS of the refspecs to see if there is a unique match.

Then the new branch can unambiguously find that its upstream is xyzzy's foo.

I think it makes sense to update the semantics like that.

Wouldn't the traditional case (i.e. without "nitfol/" in the xyzzy/frotz remotes above) be a mere special case for this new logic? You mentioned there is a regression caught by existing tests if you go this route, but I do not see how that happens.

Previous: Johan HerlandNext: Johan Herland
Message 5 of 9 in “Improving the search for remote-tracking branches”
  1. 0/5 Improving the search for remote-tracking branchesJohan Herland, Apr 19, 2013
  2. 1/5 t2024: Add tests verifying current DWIM behavior of 'git checkout <branch>'Johan Herland, Apr 19, 2013
  3. 2/5 t2024: Show failure to use refspec when DWIMming remote branch namesJohan Herland, Apr 19, 2013
  4. 3/5 checkout: Use remote refspecs when DWIMming tracking branchesJohan Herland, Apr 19, 2013
  5. Junio C HamanoApr 19, 2013
  6. Johan HerlandApr 20, 2013
  7. 4/5 branch.c: Look up refspecs to validate tracking branchesJohan Herland, Apr 19, 2013
  8. 5/5 RFD: Disallow out-of-refspec refs within refs/remotes/* to be used as upstreamJohan Herland, Apr 19, 2013
  9. Junio C HamanoApr 19, 2013

Read the whole thread, see it on lore, or plain text.

$ cat FOOTERMessages come from the public archive at lore.kernel.org/git, fetched every hour. The front page is chosen and written each morning by an AI editor and can be wrong; the threads themselves are the record. About and API. For agents: an MCP server at https://gitlist.dev/mcp, and any thread, story or person page as Markdown by adding .md to its URL (or sending Accept: text/markdown). Details in /llms.txt.