Re: [RFC] New kind of upstream branch: base branch

2013-05-19 Thread Junio C Hamano
Kevin Bracey ke...@bracey.fi writes:

 I found myself thinking the same thing. It's really convenient being
 able to set your topic branch's upstream to another local branch, so

 What is that another local branch? ...  And if that is your workflow, 
 setting
 push.default to current (and setting remote.pushdefault to your
 publishing repository) should be a sufficient interim solution, and
 you do not need to set branch.$name.push to each and every branch
 you intend to push out, I think.

 I agree that using push.default current covers some cases - I hadn't
 really considered it - tended to just stick with upstream. current
 nearly does the job, but I will sometimes be wanting different names.


 What I'll often be doing is creating a topic branch based on master or
 origin/master. (I would hardly ever be updating master or pushing to
 origin/master myself, so I probably should be just doing
 origin/master, but I tend to create a local master just to save typing
 on all those git rebase origin/master).

Do you mean, by save typing, instead of origin/master, I can type
master?

If you are using the checkout -t -b topic origin/master, git rebase
without any other argument should know that you meant to rebase
against 'origin/master', so you do not even have to type 'master'.
 During work, to give others visibility, and the possibility to tinker
 with the topic branch during development (as we don't have full
 inter-site sharing of work areas), I would push the topic branch up to
 the central origin server, often with a kbracey/ prefix, partially
 for namespacing, and partially to indicate it's currently private
 work and subject to rebasing.  I guess I could create the topic branch
 as kbracey/topic locally, but I'd rather not have to.

Yup, that is sensible, and I think with Felipe's proposed change,
you can spell it like this:

[branch topic]
remote = origin
merge = refs/heads/master
push = refs/heads/kbracey/topic

Note that the above assumes you did checkout -t -b topic origin/master
as a typesaver for git rebase.

 So I'd like git rebase (-i) to move my topic branch up
 (origin/)master. And I'd like git push (-f) to send it to
 origin/kbracey/topic. 

Understood.  And I think the [branch topic] configuration above
would cover that use case.

 And by extension, I suppose git pull --rebase to update origin/master
 and rebase. (Although I'm not much of a puller -  I tend to fetch
 then rebase manually).

git pull --rebase would be git fetch followed by git rebase,
and again the [branch topic] configuration above would cover that
use case, I think.

 And it would be ideal if the initial base and push tracking
 information could be set up automatically on the first git checkout
 -b/git branch and git push.

I think checkout and branch is already covered with -t.  There may
even be a configuration option to implicitly add -t to them (I
didn't check).

 (For one, I've always found it odd
 that there's an asymmetry - if you check out a topic branch from the
 server to work on or use it, you get a local copy with upstream set by
 default. But if you create a topic branch yourself then push it, the
 upstream isn't set by default - you need the -u flag. This seems odd
 to me, and I've seen others confused by this).

Yeah, I would imagine that it would be trivial to add an option to
cause git push to do that, and it would be useful if you push to
and pull from the same place (I haven't thought about ramifications
such an option would have on the triangular workflows, though).

Thanks.
--
To unsubscribe from this list: send the line unsubscribe git in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [RFC] New kind of upstream branch: base branch

2013-05-19 Thread Felipe Contreras
Junio C Hamano wrote:
 Kevin Bracey ke...@bracey.fi writes:

  And it would be ideal if the initial base and push tracking
  information could be set up automatically on the first git checkout
  -b/git branch and git push.
 
 I think checkout and branch is already covered with -t.  There may
 even be a configuration option to implicitly add -t to them (I
 didn't check).

branch.autosetupmerge=always

  (For one, I've always found it odd
  that there's an asymmetry - if you check out a topic branch from the
  server to work on or use it, you get a local copy with upstream set by
  default. But if you create a topic branch yourself then push it, the
  upstream isn't set by default - you need the -u flag. This seems odd
  to me, and I've seen others confused by this).
 
 Yeah, I would imagine that it would be trivial to add an option to
 cause git push to do that, and it would be useful if you push to
 and pull from the same place (I haven't thought about ramifications
 such an option would have on the triangular workflows, though).

It would work wonderfully. Now:

== remote ==

% git checkout -b master origin/master
# work
% git push

== local ==

% git checkout -b topic master
# work
% git push # ERR
% git push -u origin/master
# work
% git push # ERR

That doesn't work. We could set branch.autosetupmerge=always as the default,
but it still wouldn't work, because push.default=simple (or at least it will
be), and the names don't match.

But with my patches, and branch.autosetupmerge=always (hopefully for 2.0):

== local ==

% git checkout -b topic master
# work
% git push # ERR
% git push --set-downstream origin/master
# work
% git push

Cheers.

-- 
Felipe Contreras
--
To unsubscribe from this list: send the line unsubscribe git in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [RFC] New kind of upstream branch: base branch

2013-05-18 Thread Kevin Bracey

On 17/05/2013 22:51, Junio C Hamano wrote:

Kevin Bracey ke...@bracey.fi writes:


On 15/05/2013 23:34, Felipe Contreras wrote:

   I think I'm using 'upstream' for something it was not intended to,
and
I think the current 'upstream' behavior should be split into
'upstream' and 'base'.


I found myself thinking the same thing. It's really convenient being
able to set your topic branch's upstream to another local branch, so

What is that another local branch? ...  And if that is your workflow, setting
push.default to current (and setting remote.pushdefault to your
publishing repository) should be a sufficient interim solution, and
you do not need to set branch.$name.push to each and every branch
you intend to push out, I think.


I agree that using push.default current covers some cases - I hadn't 
really considered it - tended to just stick with upstream. current 
nearly does the job, but I will sometimes be wanting different names.


What I'll often be doing is creating a topic branch based on master or 
origin/master. (I would hardly ever be updating master or pushing to 
origin/master myself, so I probably should be just doing origin/master, 
but I tend to create a local master just to save typing on all those 
git rebase origin/master).


During work, to give others visibility, and the possibility to tinker 
with the topic branch during development (as we don't have full 
inter-site sharing of work areas), I would push the topic branch up to 
the central origin server, often with a kbracey/ prefix, partially 
for namespacing, and partially to indicate it's currently private work 
and subject to rebasing.  I guess I could create the topic branch as 
kbracey/topic locally, but I'd rather not have to.


So I'd like git rebase (-i) to move my topic branch up 
(origin/)master. And I'd like git push (-f) to send it to 
origin/kbracey/topic. And by extension, I suppose git pull --rebase 
to update origin/master and rebase. (Although I'm not much of a puller - 
I tend to fetch then rebase manually).


The final releasing procedure for the topic branch would be to hand that 
branch over to an integrator, who would then merge/rebase it into master.


And it would be ideal if the initial base and push tracking information 
could be set up automatically on the first git checkout -b/git 
branch and git push. (For one, I've always found it odd that there's 
an asymmetry - if you check out a topic branch from the server to work 
on or use it, you get a local copy with upstream set by default. But if 
you create a topic branch yourself then push it, the upstream isn't set 
by default - you need the -u flag. This seems odd to me, and I've seen 
others confused by this).


Kevin


--
To unsubscribe from this list: send the line unsubscribe git in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [RFC] New kind of upstream branch: base branch

2013-05-18 Thread Ramkumar Ramachandra
Kevin Bracey wrote:
 What I'll often be doing is creating a topic branch based on master or
 origin/master. (I would hardly ever be updating master or pushing to
 origin/master myself, so I probably should be just doing origin/master, but
 I tend to create a local master just to save typing on all those git rebase
 origin/master).

branch.name.merge was designed primarily for pull and merge.  I use
operations like git diff origin.., git log origin.., git rebase [-i]
origin.  Ofcourse, rebase is a bit of a special case because it
defaults to operating on branch.name.merge by default: this is
useful to me when I want to rebase against what I just fetched
(central workflows: we're slowly getting triangular workflows).
Abusing branch.name.merge because you want a different default for
rebase means we're doing something wrong.  Perhaps we should get a
rebase.defaultUpstream = @{u}|origin|... -- @{u} being the current
default.  In my opinion, branch.name.base is a huge overkill.

 During work, to give others visibility, and the possibility to tinker with
 the topic branch during development (as we don't have full inter-site
 sharing of work areas), I would push the topic branch up to the central
 origin server, often with a kbracey/ prefix, partially for namespacing,
 and partially to indicate it's currently private work and subject to
 rebasing.  I guess I could create the topic branch as kbracey/topic
 locally, but I'd rather not have to.

All we have to do for this is to allow the user to set a custom
refspec using remote.name.push.  The refspecs you get now are
limited to the ones set by the different modes of push.default (see
builtin/push.c to see what refspec each of them set).  We discussed
branch.name.push too on another thread, but I'm not convinced that
we need it.

 (Although I'm not much of a puller - I tend to fetch then rebase manually).

pull needs to be fixed.  I've partially fixed the rebasing pull thing
with rebase.autostash (still in pu), but there's a lot of work to be
done there.

 And it would be ideal if the initial base and push tracking information
 could be set up automatically on the first git checkout -b/git branch
 and git push. (For one, I've always found it odd that there's an asymmetry
 - if you check out a topic branch from the server to work on or use it, you
 get a local copy with upstream set by default. But if you create a topic
 branch yourself then push it, the upstream isn't set by default - you need
 the -u flag. This seems odd to me, and I've seen others confused by this).

It happens because @{u} doesn't exist before the first push.  We
should definitely fix git checkout -b to inherit branch.name.remote
and infer branch.name.merge.

To sum it up, lots of work to be done.
--
To unsubscribe from this list: send the line unsubscribe git in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [RFC] New kind of upstream branch: base branch

2013-05-18 Thread Felipe Contreras
On Sat, May 18, 2013 at 9:29 AM, Kevin Bracey ke...@bracey.fi wrote:
 On 17/05/2013 22:51, Junio C Hamano wrote:

 Kevin Bracey ke...@bracey.fi writes:

 On 15/05/2013 23:34, Felipe Contreras wrote:

I think I'm using 'upstream' for something it was not intended to,
 and
 I think the current 'upstream' behavior should be split into
 'upstream' and 'base'.

 I found myself thinking the same thing. It's really convenient being
 able to set your topic branch's upstream to another local branch, so

 What is that another local branch? ...  And if that is your workflow,
 setting

 push.default to current (and setting remote.pushdefault to your
 publishing repository) should be a sufficient interim solution, and
 you do not need to set branch.$name.push to each and every branch
 you intend to push out, I think.


 I agree that using push.default current covers some cases - I hadn't
 really considered it - tended to just stick with upstream. current
 nearly does the job, but I will sometimes be wanting different names.

 What I'll often be doing is creating a topic branch based on master or
 origin/master. (I would hardly ever be updating master or pushing to
 origin/master myself, so I probably should be just doing origin/master, but
 I tend to create a local master just to save typing on all those git rebase
 origin/master).

 During work, to give others visibility, and the possibility to tinker with
 the topic branch during development (as we don't have full inter-site
 sharing of work areas), I would push the topic branch up to the central
 origin server, often with a kbracey/ prefix, partially for namespacing,
 and partially to indicate it's currently private work and subject to
 rebasing.  I guess I could create the topic branch as kbracey/topic
 locally, but I'd rather not have to.

 So I'd like git rebase (-i) to move my topic branch up (origin/)master.
 And I'd like git push (-f) to send it to origin/kbracey/topic. And by
 extension, I suppose git pull --rebase to update origin/master and rebase.
 (Although I'm not much of a puller - I tend to fetch then rebase manually).

 The final releasing procedure for the topic branch would be to hand that
 branch over to an integrator, who would then merge/rebase it into master.

 And it would be ideal if the initial base and push tracking information
 could be set up automatically on the first git checkout -b/git branch
 and git push. (For one, I've always found it odd that there's an asymmetry
 - if you check out a topic branch from the server to work on or use it, you
 get a local copy with upstream set by default. But if you create a topic
 branch yourself then push it, the upstream isn't set by default - you need
 the -u flag. This seems odd to me, and I've seen others confused by this).

Indeed, and I agree.

I've started to set branch.autosetupmerge=always, so I always get an
upstream no matter what. The only problem is that 'git fetch' now is
useless without any argument, but that can be fixed with another
configuration 'fetch.default=simple', so that it always fetches from
origin, no matter what. Then, everything is consistent, it doesn't
matter what 'branch.autosetupmerge' you have configured, and in which
branch you are sitting at, 'git fetch' will always do something
useful.

The missing problem is that you have to manually do 'git push origin
kbracey/topic', and that can be solved with the concept of a
downstream (branch.x.remotepush+branch.x.push).

If we have these two changes, everything would work perfectly, wouldn't it?

-- 
Felipe Contreras
--
To unsubscribe from this list: send the line unsubscribe git in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [RFC] New kind of upstream branch: base branch

2013-05-17 Thread Kevin Bracey

On 15/05/2013 23:34, Felipe Contreras wrote:
  
I think I'm using 'upstream' for something it was not intended to, and

I think the current 'upstream' behavior should be split into
'upstream' and 'base'.

I found myself thinking the same thing. It's really convenient being 
able to set your topic branch's upstream to another local branch, so git 
rebase works without parameters. But then I can't use upstream to point 
to a remote version of that topic branch. I want my topic branch to know 
both that it's based on master (or origin/master), and that it's 
upstream is origin/topic.


So, yes, here's a vote in favour of the general concept.

Kevin

--
To unsubscribe from this list: send the line unsubscribe git in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [RFC] New kind of upstream branch: base branch

2013-05-17 Thread Junio C Hamano
Kevin Bracey ke...@bracey.fi writes:

 On 15/05/2013 23:34, Felipe Contreras wrote:
   I think I'm using 'upstream' for something it was not intended to,
 and
 I think the current 'upstream' behavior should be split into
 'upstream' and 'base'.

 I found myself thinking the same thing. It's really convenient being
 able to set your topic branch's upstream to another local branch, so

What is that another local branch?

Is the use case master forks from origin/master and has its own
changes on top, and then topic builds on my master but the range of
commits origin/master..topic includes both changes, that is
inconvenient to when rebuilding topic on top of my master?

I'd assume that it is the case, and the answer to the previous
question is 'master' in the example.

 git rebase works without parameters. But then I can't use upstream to
 point to a remote version of that topic branch. I want my topic branch
 to know both that it's based on master (or origin/master), and that
 it's upstream is origin/topic.

If we do s/and that it's upstream is/and that it is pushed to/, then
I think I am in general agreement (I wrote about it earlier in a
separate message).

 So, yes, here's a vote in favour of the general concept.

Yes, you should be able to treat what you build on top (upstream)
and where you publish the result (we are still looking for a better
name in the other thread) as two distinct things in a triangular
workflow.  I agree that it is an issue we need to address.

We have solved a half (push goes to a different repository) but
not the other half (updates a branch whose name is different from
the upstream) in the upcoming 1.8.3 release.

The latest round of design from Felipe calls it branch.$name.push,
if I am not mistaken.

I think it is somewhat an overkill, though.

It is normal for upstream's name not to match the topic's name
(i.e. your 'topic' may branch off of a generic 'master', but would
be named after a more specific purpose of the branch and is unlikely
to be named 'master'.  In other words, branch.$name.merge that
points at an upstream that has a name that is totally different from
$name is not an exception.  So branch.$name.merge that you have to
set for each branch is a necessity.

However, if you were to push out 'topic' directly (as opposed to
pushing out a result of integrating it and other topic branches to
your 'master') to your own publishing point, it is likely you would
push it out to the same name (i.e. 'topic' will be pushed out as
'topic', not as 'master').  And if that is your workflow, setting
push.default to current (and setting remote.pushdefault to your
publishing repository) should be a sufficient interim solution, and
you do not need to set branch.$name.push to each and every branch
you intend to push out, I think.

--
To unsubscribe from this list: send the line unsubscribe git in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [RFC] New kind of upstream branch: base branch

2013-05-17 Thread Felipe Contreras
On Fri, May 17, 2013 at 2:20 PM, Kevin Bracey ke...@bracey.fi wrote:
 On 15/05/2013 23:34, Felipe Contreras wrote:

   I think I'm using 'upstream' for something it was not intended to, and
 I think the current 'upstream' behavior should be split into
 'upstream' and 'base'.

 I found myself thinking the same thing. It's really convenient being able to
 set your topic branch's upstream to another local branch, so git rebase
 works without parameters. But then I can't use upstream to point to a remote
 version of that topic branch. I want my topic branch to know both that it's
 based on master (or origin/master), and that it's upstream is origin/topic.

If you are in your topic branch, what do you expect 'git pull' to do?
And what do you expect 'git push' to do?

-- 
Felipe Contreras
--
To unsubscribe from this list: send the line unsubscribe git in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [RFC] New kind of upstream branch: base branch

2013-05-16 Thread Felipe Contreras
On Thu, May 16, 2013 at 2:35 PM, Philip Oakley philipoak...@iee.org wrote:
 From: Felipe Contreras felipe.contre...@gmail.com
 Sent: Thursday, May 16, 2013 4:46 AM

 On Wed, May 15, 2013 at 5:22 PM, Philip Oakley philipoak...@iee.org
 wrote:

 Sound a reasonable idea. On some patches I was working on I had to [chose
 to] add a tag for the base which made it easier to rebase later.


 And was the 'upstream' branch somehow not appropriate for some reason?


 If I remember correctly, I had a short branch based on 'pu', which was
 rewound, so I wanted to rebase that short branch onto the new 'pu'. This
 creates a confusion between old-pu and new-pu. Having a marker for the
 'base' at the branch point allowed an easy specification of the branch

So you were not doing 'git rebase @{base}', you were doing 'git rebase
--onto X @{base}'?

 I think I misunderstood your proposal. I thought that it would effectively
 save a marker (e.g. the sha1) for the base point of the branch, it may have
 been something similar to a [lightweight] tag, it could have been just local
 or could have been transferable, I hadn't thought it further.

Yeah, I thought about that, and I think it might make sense, but
that's another topic.

-- 
Felipe Contreras
--
To unsubscribe from this list: send the line unsubscribe git in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


[RFC] New kind of upstream branch: base branch

2013-05-15 Thread Felipe Contreras
Hi,

I've been using Git from the start, but only lately have I forced myself to
configure upstream branches for all my branches, and I've found a few things
more convenient, but others completely contrary to what I expected.

Inconvenient:

Before, I used to do 'git fetch' to simply fetch from 'origin', but now, it
depends on where 'upstream' is set to.

Convinient:

Now, I can just do 'git rebase --interactive' and I don't have to specify the
starting point, which is particularily useful when there's a lot of branches
one depending on another.

I think I'm using 'upstream' for something it was not intended to, and I think
the current 'upstream' behavior should be split into 'upstream' and 'base'.

== base ==

The 'base' branch will be set each time you create a branch from another;
'git checkout -b foobar master' sets 'master' as the 'base' of 'foobar'.

Then you can do 'git rebase foobar@{base}' or simply 'git rebase', and Git will
pick the right branch to rebase unto, even if you have no 'upstream'
configured.

This way 'git fetch' will keep picking 'origin', and other commands that make
use of 'upstrem' would be undisturbed.

If both 'base' and 'upstream' are defined, I think 'git rebase' should use
'base', but since that would break old behavior, perhaps there should be a
configuration variable to enable a different behavior.

I already started writting the patches, and although tedious, I think they
they'll be rather straightforward, but I thought it would be best to hear some
opinions first.

What do you think?

Cheers.

-- 
Felipe Contreras
--
To unsubscribe from this list: send the line unsubscribe git in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


[RFC] New kind of upstream branch: base branch

2013-05-15 Thread Felipe Contreras
Hi,

I've been using Git from the start, but only lately have I forced
myself to configure upstream branches for all my branches, and I've
found a few things more convenient, but others completely contrary to
what I expected.

Inconvenient:

Before, I used to do 'git fetch' to simply fetch from 'origin', but
now, it depends on where 'upstream' is set to.

Convinient:

Now, I can just do 'git rebase --interactive' and I don't have to
specify the starting point, which is particularily useful when there's
a lot of branches one depending on another.

I think I'm using 'upstream' for something it was not intended to, and
I think the current 'upstream' behavior should be split into
'upstream' and 'base'.

== base ==

The 'base' branch will be set each time you create a branch from another;
'git checkout -b foobar master' sets 'master' as the 'base' of 'foobar'.

Then you can do 'git rebase foobar@{base}' or simply 'git rebase', and
Git will pick the right branch to rebase unto, even if you have no
'upstream'
configured.

This way 'git fetch' will keep picking 'origin', and other commands
that make use of 'upstream' would be undisturbed.

If both 'base' and 'upstream' are defined, I think 'git rebase' should
use 'base', but since that would break old behavior, perhaps there
should be a configuration variable to enable a different behavior.

I already started writting the patches, and although tedious, I think
they they'll be rather straightforward, but I thought it would be best
to hear some opinions first.

What do you think?

-- 
Felipe Contreras
--
To unsubscribe from this list: send the line unsubscribe git in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [RFC] New kind of upstream branch: base branch

2013-05-15 Thread Junio C Hamano
Felipe Contreras felipe.contre...@gmail.com writes:

 The 'base' branch will be set each time you create a branch from another;
 'git checkout -b foobar master' sets 'master' as the 'base' of 'foobar'.

git checkout -t -b foobar mastee would instead set 'upstream' of
'foobar' to the branch 'master' of remote '.' (the current one).
This 'base' is a new mechanism to explicitly say The upstream of
this branch lives locally by not setting branch.foobar.remote.

 Then you can do 'git rebase foobar@{base}' or simply 'git rebase', and Git 
 will
 pick the right branch to rebase unto, even if you have no 'upstream'
 configured.

Surely you can teach rebase to pay attention to 'base' and achieve
that.  But you can already do so with upstream, so this is not an
advertisement of a 'plus', but rather a lack of 'minus' (which is
not a bad thing at all).

 This way 'git fetch' will keep picking 'origin', and other commands that make
 use of 'upstrem' would be undisturbed.

And this is the true plus, because 'git fetch' with the current
setting a local base using the same upstream mechanism to point at
a branch of _this_ repository, indirectly setting the upstream
_repository_ for this branch to the current repository will end up
making you fetch from yourself, which is not very interesting.

So I think I understand your itch and I agree that it is a valid
one.

I however am not yet convinced if that direction is what you really
want go in, though.  What should your 'git pull' on that branch do,
for example?

When you are on foobar and want to integrate with the branch you
based your work on (i.e. local 'master'), you can do one of these:

$ git pull
$ git pull --rebase

to fetch the upstream branch and integrate with it, without having
to even care if that upstream branch is from the remote, or happens
to be truly local.  By making 'git fetch' to go to the remote origin
site, what will you be merging (or rebasing on) when you do the
above two?

Incidentally, I suspect you can do exactly the same thing without
introducing a new concept base and instead special casing a remote
whose URL is .; you essentially declare that The upstream of this
branch whose branch.$name.remote is set to '.' lives locally, which
is not all that different from saying The upstream of this branch
whose branch.$name.base exists lives locally, which is what you
seem to be proposing.  One of the things this alternative approach
would special case such remote is probably to cause git fetch to
ignore such a branch.$name.remote setting and instead go fetch from
'origin', just like your if there is branch.$name.base, but no
branch.$name.remote, fetch will go to 'origin' does.

But it has exactly the same what happens when you do 'git pull'
problem, so even though it is conceptually a lot simpler, it has the
same brokenness.
--
To unsubscribe from this list: send the line unsubscribe git in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [RFC] New kind of upstream branch: base branch

2013-05-15 Thread Philip Oakley

From: Felipe Contreras felipe.contre...@gmail.com
Sent: Wednesday, May 15, 2013 9:34 PM

Hi,

I've been using Git from the start, but only lately have I forced
myself to configure upstream branches for all my branches, and I've
found a few things more convenient, but others completely contrary to
what I expected.

Inconvenient:

Before, I used to do 'git fetch' to simply fetch from 'origin', but
now, it depends on where 'upstream' is set to.

Convinient:

Now, I can just do 'git rebase --interactive' and I don't have to
specify the starting point, which is particularily useful when there's
a lot of branches one depending on another.

I think I'm using 'upstream' for something it was not intended to, and
I think the current 'upstream' behavior should be split into
'upstream' and 'base'.

== base ==

The 'base' branch will be set each time you create a branch from 
another;
'git checkout -b foobar master' sets 'master' as the 'base' of 
'foobar'.


Then you can do 'git rebase foobar@{base}' or simply 'git rebase', and
Git will pick the right branch to rebase unto, even if you have no
'upstream'
configured.

This way 'git fetch' will keep picking 'origin', and other commands
that make use of 'upstream' would be undisturbed.

If both 'base' and 'upstream' are defined, I think 'git rebase' should
use 'base', but since that would break old behavior, perhaps there
should be a configuration variable to enable a different behavior.

I already started writting the patches, and although tedious, I think
they they'll be rather straightforward, but I thought it would be best
to hear some opinions first.

What do you think?

--
Felipe Contreras

---
Sound a reasonable idea. On some patches I was working on I had to 
[chose to] add a tag for the base which made it easier to rebase later.


The other point is that I had already noted that the glossary doesn't 
include the many base terms in use that aren't always well understood.


Philip Oakley 


--
To unsubscribe from this list: send the line unsubscribe git in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [RFC] New kind of upstream branch: base branch

2013-05-15 Thread Junio C Hamano
Junio C Hamano gits...@pobox.com writes:

 I however am not yet convinced if that direction is what you really
 want go in, though.  What should your 'git pull' on that branch do,
 for example?

 When you are on foobar and want to integrate with the branch you
 based your work on (i.e. local 'master'), you can do one of these:

 $ git pull
 $ git pull --rebase

 to fetch the upstream branch and integrate with it, without having
 to even care if that upstream branch is from the remote, or happens
 to be truly local.  By making 'git fetch' to go to the remote origin
 site, what will you be merging (or rebasing on) when you do the
 above two?

 Incidentally, I suspect you can do exactly the same thing without
 introducing a new concept base and instead special casing a remote
 whose URL is .; you essentially declare that The upstream of this
 branch whose branch.$name.remote is set to '.' lives locally, which
 is not all that different from saying The upstream of this branch
 whose branch.$name.base exists lives locally, which is what you
 seem to be proposing.  One of the things this alternative approach
 would special case such remote is probably to cause git fetch to
 ignore such a branch.$name.remote setting and instead go fetch from
 'origin', just like your if there is branch.$name.base, but no
 branch.$name.remote, fetch will go to 'origin' does.

 But it has exactly the same what happens when you do 'git pull'
 problem, so even though it is conceptually a lot simpler, it has the
 same brokenness.

I do not think of a good way to fix the 'git pull' confusion; the
desire to 'fetch from the overall upstream repository regardless of
which branch I am on' is a valid and understandable one, but that
does not mesh well with 'git pull' is 'git fetch' followed by
either merge or rebase to integrate the result and git merge or
git rebase pays attention to the other branch that is specified to
integrate with.  The best we could do might be to simply forbid
git pull if your current branch is marked with branch.$name.base
but still allow git fetch.

The changes that are involved are:

 * Do not change anything to @{upstream}'s definition, that is,
   checkout -t -b A localbranch will set branch.A.remote to '.',
   and git log A@{u}..A will stand for git log localbranch..A.

 * Current 'git fetch' pays attention to branch.A.remote when you
   are on branch A, and tries to fetch from there.  Stop doing that
   when branch.A.remote is set to '.' (the current repository) and
   let other rules in the current implementation decide what remote
   to fetch from. Also teach it to error out when branch.A.remote is
   set to '.' when a new --forbid-local option is passed.

 * Teach 'git pull' to pass --forbid-local option to 'git fetch',
   and let an error return fail the whole thing.

Ah, alternatively, instead of adding --forbid-local, we could modify
the changes for 'git fetch' and 'git pull' to read like this:

 * Current 'git fetch' pays attention to branch.A.remote when you
   are on branch A, and tries to fetch from there.  Stop doing that
   when branch.A.remote is set to '.' (the current repository) and
   let other rules in the current implementation decide what remote
   to fetch from, unless a new --allow-fetch-from-local option is
   passed.

 * Teach 'git pull' to pass --allow-fetch-from-local to 'git fetch'.

If we did this, we can keep the git pull [--rebase] as a way to
integrate with what you specified as your upstream, which is a
common expectation, without forcing you to say git fetch origin.
--
To unsubscribe from this list: send the line unsubscribe git in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [RFC] New kind of upstream branch: base branch

2013-05-15 Thread Felipe Contreras
On Wed, May 15, 2013 at 5:20 PM, Junio C Hamano gits...@pobox.com wrote:
 Felipe Contreras felipe.contre...@gmail.com writes:

 The 'base' branch will be set each time you create a branch from another;
 'git checkout -b foobar master' sets 'master' as the 'base' of 'foobar'.

 git checkout -t -b foobar mastee would instead set 'upstream' of
 'foobar' to the branch 'master' of remote '.' (the current one).

Yeah, but I don't to set an upstream, because 'master' is not the
upstream of 'foobar'.

 This 'base' is a new mechanism to explicitly say The upstream of
 this branch lives locally by not setting branch.foobar.remote.

No, 'base' can point to a remote tracking branch.

 Then you can do 'git rebase foobar@{base}' or simply 'git rebase', and Git 
 will
 pick the right branch to rebase unto, even if you have no 'upstream'
 configured.

 Surely you can teach rebase to pay attention to 'base' and achieve
 that.  But you can already do so with upstream, so this is not an
 advertisement of a 'plus', but rather a lack of 'minus' (which is
 not a bad thing at all).

Only if there's an upstream configured, which many times is not the
case, and many times causes side-effects the user doesn't want to.

The purpose of 'upstream' is completely different.

 This way 'git fetch' will keep picking 'origin', and other commands that make
 use of 'upstrem' would be undisturbed.

 And this is the true plus, because 'git fetch' with the current
 setting a local base using the same upstream mechanism to point at
 a branch of _this_ repository, indirectly setting the upstream
 _repository_ for this branch to the current repository will end up
 making you fetch from yourself, which is not very interesting.

 So I think I understand your itch and I agree that it is a valid
 one.

 I however am not yet convinced if that direction is what you really
 want go in, though.  What should your 'git pull' on that branch do,
 for example?

Exactly the same as 'git pull' does right now.

'base' has absolutely nothing to do with pulling or pushing.

 When you are on foobar and want to integrate with the branch you
 based your work on (i.e. local 'master'), you can do one of these:

 $ git pull
 $ git pull --rebase

 to fetch the upstream branch and integrate with it, without having
 to even care if that upstream branch is from the remote, or happens
 to be truly local.  By making 'git fetch' to go to the remote origin
 site, what will you be merging (or rebasing on) when you do the
 above two?

The same as we do now.

 Incidentally, I suspect you can do exactly the same thing without
 introducing a new concept base and instead special casing a remote
 whose URL is .; you essentially declare that The upstream of this
 branch whose branch.$name.remote is set to '.' lives locally, which
 is not all that different from saying The upstream of this branch
 whose branch.$name.base exists lives locally, which is what you
 seem to be proposing.

That would be good, but it doesn't have the same benefits:

If I have set an 'upstream' branch, say 'github/master', and I have
'base' branch, say 'origin/master'. I would expect 'git rebase' to
rebase onto 'origin/master'. When I do 'git push', I expect to push to
'github/master'. Moreover, I would expect 'git fetch' to fetch from
'origin', but that can be discussed later.

Right now I'm forced to choose a single branch and set it to
'upstream'. If I choose 'origin/master' (which is not really the
upstream), the rebase would do what I want, but not the push, unless I
have configured a remote.pushdefault, but that would only work if I
the real upstream is the common one. If I choose 'github/master', then
rebase would not do what I want (and neither would fetch).

 One of the things this alternative approach
 would special case such remote is probably to cause git fetch to
 ignore such a branch.$name.remote setting and instead go fetch from
 'origin', just like your if there is branch.$name.base, but no
 branch.$name.remote, fetch will go to 'origin' does.

 But it has exactly the same what happens when you do 'git pull'
 problem, so even though it is conceptually a lot simpler, it has the
 same brokenness.

There is no brokenness; 'git pull' does different things depending on
the configuration. With my proposal nothing would change.

-- 
Felipe Contreras
--
To unsubscribe from this list: send the line unsubscribe git in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [RFC] New kind of upstream branch: base branch

2013-05-15 Thread Junio C Hamano
Felipe Contreras felipe.contre...@gmail.com writes:

 Exactly the same as 'git pull' does right now.

You set

[branch 'foobar']
base = refs/heads/master

then 'git pull [--rebase]' will go to 'origin' due to the default,
but then what branch from the 'origin' are you integrating with?

Do you mean you are also setting both remote and upstream, perhaps
like this, for all of your branches?

[remote origin]
url = github.com:maintainer/hisproject
fetch = +refs/heads/*:refs/remotes/origin/*

[remote github]
url = github.com:felipec/myproject
fetch = +refs/heads/*:refs/remotes/github/*

[branch 'foobar']
base = refs/heads/master
remote = github ;# or is it origin???
upstream = refs/heads/foobar

Then your 'git pull' will fetch from remote 'origin' and integrate
with its 'foobar' and 'push' may go to update 'foobar' at 'github'.

Perhaps that is what you meant.

 'base' has absolutely nothing to do with pulling or pushing.

I agree it shouldn't have anything to do with pushing, but given
that 'git pull [--rebase]' is a way to do a 'merge' or 'rebase' with
what you 'git fetch', introducing something that 'merge' or 'rebase'
pays attention to that does not have anything to do with 'pull'
sounds like it breaks existing end user expectation.

But that does not mean it is a bad idea. The behaviour changes only
when you have branch.$name.base, so I suspect that we do not need to
worry about what if the user has both? case you mentioned in your
first message.

I think I misunderstood what you meant.  If it is the norm to have
both base and upstream/remote in branch.$name (as opposed to have
only branch.$name.base and not branch.$name.remote to force fetch to
go to the default 'origin'), then 'git pull' will not break and I
can see how many things would work naturally (admittedly I can only
say 'many things', not 'everything', at this point, as I haven't
thought things through).
--
To unsubscribe from this list: send the line unsubscribe git in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [RFC] New kind of upstream branch: base branch

2013-05-15 Thread Felipe Contreras
On Wed, May 15, 2013 at 5:50 PM, Junio C Hamano gits...@pobox.com wrote:
 Junio C Hamano gits...@pobox.com writes:

 I however am not yet convinced if that direction is what you really
 want go in, though.  What should your 'git pull' on that branch do,
 for example?

 When you are on foobar and want to integrate with the branch you
 based your work on (i.e. local 'master'), you can do one of these:

 $ git pull
 $ git pull --rebase

 to fetch the upstream branch and integrate with it, without having
 to even care if that upstream branch is from the remote, or happens
 to be truly local.  By making 'git fetch' to go to the remote origin
 site, what will you be merging (or rebasing on) when you do the
 above two?

 Incidentally, I suspect you can do exactly the same thing without
 introducing a new concept base and instead special casing a remote
 whose URL is .; you essentially declare that The upstream of this
 branch whose branch.$name.remote is set to '.' lives locally, which
 is not all that different from saying The upstream of this branch
 whose branch.$name.base exists lives locally, which is what you
 seem to be proposing.  One of the things this alternative approach
 would special case such remote is probably to cause git fetch to
 ignore such a branch.$name.remote setting and instead go fetch from
 'origin', just like your if there is branch.$name.base, but no
 branch.$name.remote, fetch will go to 'origin' does.

 But it has exactly the same what happens when you do 'git pull'
 problem, so even though it is conceptually a lot simpler, it has the
 same brokenness.

 I do not think of a good way to fix the 'git pull' confusion; the
 desire to 'fetch from the overall upstream repository regardless of
 which branch I am on' is a valid and understandable one, but that
 does not mesh well with 'git pull' is 'git fetch' followed by
 either merge or rebase to integrate the result

But that is not true. It's only true when merge.defaulttoupstream=true.

 and git merge or
 git rebase pays attention to the other branch that is specified to
 integrate with.  The best we could do might be to simply forbid
 git pull if your current branch is marked with branch.$name.base
 but still allow git fetch.

Why forbid it? Why not leave it as it is?

 The changes that are involved are:

  * Do not change anything to @{upstream}'s definition, that is,
checkout -t -b A localbranch will set branch.A.remote to '.',
and git log A@{u}..A will stand for git log localbranch..A.

Yes, but in addition it would set 'branch.A.base'.

  * Current 'git fetch' pays attention to branch.A.remote when you
are on branch A, and tries to fetch from there.  Stop doing that
when branch.A.remote is set to '.' (the current repository) and
let other rules in the current implementation decide what remote
to fetch from. Also teach it to error out when branch.A.remote is
set to '.' when a new --forbid-local option is passed.

I don't see the point of --forbid-local, but otherwise yeah.

 Ah, alternatively, instead of adding --forbid-local, we could modify
 the changes for 'git fetch' and 'git pull' to read like this:

  * Current 'git fetch' pays attention to branch.A.remote when you
are on branch A, and tries to fetch from there.  Stop doing that
when branch.A.remote is set to '.' (the current repository) and
let other rules in the current implementation decide what remote
to fetch from, unless a new --allow-fetch-from-local option is
passed.

  * Teach 'git pull' to pass --allow-fetch-from-local to 'git fetch'.

Perhaps.

 If we did this, we can keep the git pull [--rebase] as a way to
 integrate with what you specified as your upstream, which is a
 common expectation, without forcing you to say git fetch origin.

I'm starting to change my mind. Perhaps instead of aiming to change
the behavior 'git rebase', it would make more sense to change the
behavior of 'git push'. So that 'git rebase', 'git fetch' and 'git
pull' all use 'upstream' as is currently the case, but 'git push'
would use something different. That would solve my 'origin/master' vs.
'github/master' distinction. But I would like 'git checkout -b foo
master' to automatically setup 'upstream', and 'git checkout -t -b foo
master' to in addition set this other kind that only affects 'git
push'. This would be a much more intrusive change though.

So, 'branch.A.merge' would become 'branch.A.upstream' and have the
full tracking branch (e.g. 'refs/remotes/github/master'), and
'branch.A.remote' would only affect 'git push'.

-- 
Felipe Contreras
--
To unsubscribe from this list: send the line unsubscribe git in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [RFC] New kind of upstream branch: base branch

2013-05-15 Thread Felipe Contreras
On Wed, May 15, 2013 at 6:14 PM, Junio C Hamano gits...@pobox.com wrote:
 Felipe Contreras felipe.contre...@gmail.com writes:

 Exactly the same as 'git pull' does right now.

 You set

 [branch 'foobar']
 base = refs/heads/master

 then 'git pull [--rebase]' will go to 'origin' due to the default,
 but then what branch from the 'origin' are you integrating with?

The same as if you didn't have 'branch.foobar.base': none. You get an
error because there's no upstream.

 Do you mean you are also setting both remote and upstream, perhaps
 like this, for all of your branches?

 [remote origin]
 url = github.com:maintainer/hisproject
 fetch = +refs/heads/*:refs/remotes/origin/*

 [remote github]
 url = github.com:felipec/myproject
 fetch = +refs/heads/*:refs/remotes/github/*

 [branch 'foobar']
 base = refs/heads/master
 remote = github ;# or is it origin???
 upstream = refs/heads/foobar

 Then your 'git pull' will fetch from remote 'origin' and integrate
 with its 'foobar' and 'push' may go to update 'foobar' at 'github'.

 Perhaps that is what you meant.

That's what I described in my example.

 'base' has absolutely nothing to do with pulling or pushing.

 I agree it shouldn't have anything to do with pushing, but given
 that 'git pull [--rebase]' is a way to do a 'merge' or 'rebase' with
 what you 'git fetch', introducing something that 'merge' or 'rebase'
 pays attention to that does not have anything to do with 'pull'
 sounds like it breaks existing end user expectation.

But it's already broken.

'git pull' is not the same as 'git fetch'+'git merge'. That *only*
works  when merge.defaulttoupstream is set.

 But that does not mean it is a bad idea. The behaviour changes only
 when you have branch.$name.base, so I suspect that we do not need to
 worry about what if the user has both? case you mentioned in your
 first message.

Indeed. It wouldn't be an intrusive change; it would only affect 'git
rebase', and nothing more.

But I'm wondering if the behavior of 'git fecth' should change as
well. And in fact it should be the other way around.

 I think I misunderstood what you meant.  If it is the norm to have
 both base and upstream/remote in branch.$name (as opposed to have
 only branch.$name.base and not branch.$name.remote to force fetch to
 go to the default 'origin'), then 'git pull' will not break and I
 can see how many things would work naturally (admittedly I can only
 say 'many things', not 'everything', at this point, as I haven't
 thought things through).

But I think the norm would be to have only 'base', because a lot of
people don't manually set an upstream branch.

In the end it all boils down to; which is the upstream
'origin/master', or 'github/master'? Well, it is 'origin/master', so
'upstream' should point there, but I don't want to push to the
'upstream', I want to push somewhere else by default.

-- 
Felipe Contreras
--
To unsubscribe from this list: send the line unsubscribe git in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [RFC] New kind of upstream branch: base branch

2013-05-15 Thread Felipe Contreras
On Wed, May 15, 2013 at 5:22 PM, Philip Oakley philipoak...@iee.org wrote:

 Sound a reasonable idea. On some patches I was working on I had to [chose
 to] add a tag for the base which made it easier to rebase later.

And was the 'upstream' branch somehow not appropriate for some reason?

-- 
Felipe Contreras
--
To unsubscribe from this list: send the line unsubscribe git in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html