Re: Beyond Merge and Rebase: The Upstream Import Approach in Git

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



Aleksander Korzyński <ak@xxxxxxxxxx> writes:

> So the alternative solution is to rebase your "main" branch on top of
> "upstream/main":
>
>   o---o---o---o---o  upstream/main
>                    \
>                     o'---o'---o'  main
>
> You now have the advantage of having greater visibility into the
> differences between "upstream/main" and "main". However, a rebase
> comes with a different problem: if any user of your fork had the
> "main" branch checked out in their local repository and they run "git
> pull", they are going to get an error stating that the local and
> upstream branches have diverged. They will have to take special steps
> to recover from the rebase of the "main" branch.
>
> So how to solve that problem?

In short, what you wrote is a way to use rebase but help those who
have older versions of your work to bring themselves up to date.
That is a useful thing for downstream contributors to have, and it
is a valuable goal to aim to help these downstream contributors to
coordinate sharing of their work.  Because in general, downstream
contributors tend to outnumber upstream maintainers.  It would help
you to hear perspective from upstream maintainers as well, and here
are a few things that come to my mind.

    o---o---o---o---o  upstream/main
         \           \
          \           a'---b'---c'
           \                     \
            a---b---c-------------S  main

 * It certainly would help folks who received a copy of c from you
   and then want to observe your progress after you rebased c to c',
   but how does this help those who have older versions of your
   work, *and* built their own changes on top?  They would not just
   need to update their remote-tracking branch that has your older
   version of the work to the latest, but also rebase their work on
   top.

    o---o---o---o---o  upstream/main
         \           \
          \           a'---b'---c'---d'---e'
           \                     \
            a---b---c-------------S  main
                     \
                      d---e  your coworker

 * It is a reasonable way to for keeping your work as a fork from
   the upstream up-to-date, but it is unclear what the eventual
   presentation to and adoption by the upstream would look like.  As
   an upstream maintainer, for example, I do not want to merge S
   above to the upstream tree.

 * There is no need to say that it is undesirable to merge from
   upstream to your working topic branch like 'main' repeatedly, as
   everybody knows it will clutter your history, but more
   importantly, the resulting history becomes more useless from the
   upstream's point of view as you have more such reverse merges.
   The upstream wants to see your work and only your work delineated
   on your repository.  If you repeat the "rebase and merge", then
   the next round would create a new history a", b" and c" forked on
   top of an updated upstream/main, merged on top of S, perhaps
   looking like this:

    o---o---o---o---o---------------o  upstream/main
         \           \               \
          \           a'---b'---c'    a"--b"--c"
           \                     \             \
            a---b---c-------------S-------------T  main

   However, once you keep going this way for several rounds, would
   the result really be much better than bushy history with full of
   reverse merges from upstream?  Would it help to add new history
   simplification mechanisms and options to help visualize the
   history, or do we already have necessary support (e.g. if the
   convention for these "merge to cauterize the older versions of
   history with the newly rebased history" S and T merges is to
   record the rebased history as the first-parent, then "git log
   --first-parent upstream/main..main" should be sufficient).  The
   users would benefit to have an easy way, given only T or S, to
   get range-diff among (a,b,c) and (a',b',c') and (a",b",c").

What is interesting is that, because S and T are essentially "ours"
merges of your local history into the history that would result if
you rebased on top of the upstream (i.e. merge S and T would have
the same tree as c' and c"), what is tested and used by the holder
of S and T are the changes represented by the latest rebased
versions of the commits.  So from the upstream point of view,
throwing a pull request for c" (not the original a, b and c) would
be a reasonable way to finalize your work.  That way, what you are
offering to the upstream is not an ancient original commits (i.e. a,
b, and c) that you haven't been using at all once you created S and
T.

Thanks.




[Index of Archives]     [Linux Kernel Development]     [Gcc Help]     [IETF Annouce]     [DCCP]     [Netdev]     [Networking]     [Security]     [V4L]     [Bugtraq]     [Yosemite]     [MIPS Linux]     [ARM Linux]     [Linux Security]     [Linux RAID]     [Linux SCSI]     [Fedora Users]

  Powered by Linux