[PATCH 1 of 4 V2] obsolete: track node versions
Durham Goode
durham at fb.com
Thu Mar 30 14:28:32 EDT 2017
Let's step back a moment and think about what obsmarkers are used for.
They are used to hide commits, and to automatically perform rebases. The
concerns around obscycles is that allowing cycles (without a perfect
version scheme) could affect those two uses. For hiding, it could
result in hiding commits from the user that they didn't mean to be
hidden. For rebasing, it means we could rebase onto the wrong successor.
I think the underlying issue is that we're trying to do too much magic
for the user, and we're unable to find a perfect design to make that
magic safe and understandable. I think finding the right answer here may
be impossible.
Proposal
===
I propose a series of changes to reduce the magic and remove the need
for obs versioning, while maintaining the power and increasing the
understandability of these workflows. It has two parts:
1. Never hide a commit during hg pull. Only hide commits when the user
does an action (strip/rebase/amend/histedit/evolve)
---
One of the recurring issues with obsmarkers is that commits may
magically disappear when you pull from another repo. This has two
issues: A) we have no good way of explaining it to the user, and B) we
can't even be sure the user wants those commits to disappear.
I propose we *never* hide a commit when doing hg pull. When the user
pulls, we download the obsmarkers like normal, but the commits don't
disappear. Instead, we show the "[amended|rebased] to HASH" text in a
log/smartlog output so the user can know the old commits are dead, then
they can strip them at their leisure. This has the added benefit of
making it user visible what obsmarker changes the pull brought in.
This proposal has two optional side features:
1a. *Do* hide commits during pull if the pulled version is public.
1b. Add an option to strip/prune to auto hide any visible commits that
have visible successors and don't have visible descendants. So "hg pull
&& hg strip/prune --obsolete-commits" would be roughly equivalent to hg
pull today.
This proposal requires a notable change to core:
- Hidden must be separated from obsmarkers storage and mutable outside
obsmarkers. This is possible with Jun's proposed phaseroot-esque hidden
storage.
2. Auto rebase uses "visible successors" instead of "latest successor"
---
Today auto rebase (i.e. evolve) uses the latest successor as the
destination of the rebases. I propose we change that to "visible
successor" instead, where visible successor is defined as "any successor
commit that is not hidden". This means, regardless of the current
obsmarkers setup, the destination of the auto rebase is whatever
successor is currently visible. Which is probably what the user wanted
anyway.
If there are multiple visible successors, auto rebase fails and shows a
list of the potential visible successors. Each item in the list can have
the "[amended|rebased] to HASH" string next to it so users can
understand at a glance the ordering and make a decision. They can either
use -d on rebase to specify a solution to the conflict, or they can use
the normal visibility commands (hg strip/prune) to remove any
undesirable commits.
The presence of cycles does not affect this at all, and there is no need
for marker versioning. Auto rebase still uses whatever successors are
visible, even if the successor is "older" than it, because of a cycle.
The user can use the same rebase -d or strip/prune resolutions to
resolve the conflict.
Summary of what these two changes achieve
===
From a single, non-exchanging user's perspective the above proposal
does not affect current UX around when things are hidden (like during
rebase/amend/etc), but does allows all the benefits of the obscycle
discussion (allowing unhiding) without the need for obsmarker versioning.
From an exchange user's perspective, this makes exchange much more
deterministic for the user (nothing is magically removed from the repo,
and what new obs information from the pull is explained via smartlog),
while still enabling auto rebase workflows. It also makes obsmarker
conflict (divergence/etc) easier to understand and resolve by allowing
users to resolve obsmarker conflicts using tools they're already
familiar with (rebase -d, strip/prune).
More information about the Mercurial-devel
mailing list