Mercurial > public > mercurial-scm > hg-stable
comparison mercurial/revset.py @ 32719:f75d0aa5dc83
revset: lookup descendents for negative arguments to ancestor operator
Negative offsets to the `~` operator now search for descendents. The search is
aborted when a node has more than one child as we do not have a definition for
'nth child'. Optionally we can introduce such a notion and take the nth child
ordered by rev number.
The current revset language does provides a short operator for ancestor lookup
but not for descendents. This gives user a simple revset to move to the previous
changeset, e.g. `hg up '.~1'` but not to the 'next' changeset. With this change
userse can now use `.~-1` as a shortcut to move to the next changeset.
This fits better into allowing users to specify revisions via revsets and
avoiding the need for special `hg next` and `hg prev` operations.
The alternative to negative offsets is adding a new operator. We do not have
many operators in ascii left that do not require bash escaping (',', '_', and
'/' come to mind). If we decide that we should add a more convenient short
operator such as ('/', e.g. './1') we can later add it and allow ascendents
lookup via negative numbers.
author | David Soria Parra <davidsp@fb.com> |
---|---|
date | Sat, 27 May 2017 10:25:09 -0700 |
parents | af854b1b36f8 |
children | 573b792872c1 |
comparison
equal
deleted
inserted
replaced
32718:1b5c61d38a52 | 32719:f75d0aa5dc83 |
---|---|
377 def _firstancestors(repo, subset, x): | 377 def _firstancestors(repo, subset, x): |
378 # ``_firstancestors(set)`` | 378 # ``_firstancestors(set)`` |
379 # Like ``ancestors(set)`` but follows only the first parents. | 379 # Like ``ancestors(set)`` but follows only the first parents. |
380 return _ancestors(repo, subset, x, followfirst=True) | 380 return _ancestors(repo, subset, x, followfirst=True) |
381 | 381 |
382 def _childrenspec(repo, subset, x, n, order): | |
383 """Changesets that are the Nth child of a changeset | |
384 in set. | |
385 """ | |
386 cs = set() | |
387 for r in getset(repo, fullreposet(repo), x): | |
388 for i in range(n): | |
389 c = repo[r].children() | |
390 if len(c) == 0: | |
391 break | |
392 if len(c) > 1: | |
393 raise error.RepoLookupError( | |
394 _("revision in set has more than one child")) | |
395 r = c[0] | |
396 else: | |
397 cs.add(r) | |
398 return subset & cs | |
399 | |
382 def ancestorspec(repo, subset, x, n, order): | 400 def ancestorspec(repo, subset, x, n, order): |
383 """``set~n`` | 401 """``set~n`` |
384 Changesets that are the Nth ancestor (first parents only) of a changeset | 402 Changesets that are the Nth ancestor (first parents only) of a changeset |
385 in set. | 403 in set. |
386 """ | 404 """ |
387 n = getinteger(n, _("~ expects a number")) | 405 n = getinteger(n, _("~ expects a number")) |
406 if n < 0: | |
407 # children lookup | |
408 return _childrenspec(repo, subset, x, -n, order) | |
388 ps = set() | 409 ps = set() |
389 cl = repo.changelog | 410 cl = repo.changelog |
390 for r in getset(repo, fullreposet(repo), x): | 411 for r in getset(repo, fullreposet(repo), x): |
391 for i in range(n): | 412 for i in range(n): |
392 try: | 413 try: |