Patchwork [2,of,4] stack: take getstack() and turn it into stack class (API)

login
register
mail settings
Submitter Anton Shestakov
Date Sept. 23, 2019, 3:39 a.m.
Message ID <6430e0ae6d8634398057.1569209990@df1>
Download mbox | patch
Permalink /patch/41732/
State Accepted
Headers show

Comments

Anton Shestakov - Sept. 23, 2019, 3:39 a.m.
# HG changeset patch
# User Anton Shestakov <av6@dwimlabs.net>
# Date 1569138369 -25200
#      Sun Sep 22 14:46:09 2019 +0700
# Node ID 6430e0ae6d86343980578e36fa26c5e4893170fd
# Parent  d81e537a421f78d9f1bf6b3bdf736977ad126f68
# EXP-Topic stack-object
stack: take getstack() and turn it into stack class (API)

Stack used to be just a set of revisions, but it's going to grow more features
and it makes sense to encapsulate them into an object.

One reason we don't make stack class inherit from something like smartset class
(and be an iterable containing stack revisions) is that there's going to be
another property related to revisions and we don't want any ambiguity.

Patch

diff --git a/mercurial/destutil.py b/mercurial/destutil.py
--- a/mercurial/destutil.py
+++ b/mercurial/destutil.py
@@ -13,7 +13,7 @@  from . import (
     error,
     obsutil,
     scmutil,
-    stack
+    stack as stackmod,
 )
 
 def orphanpossibledestination(repo, rev):
@@ -378,7 +378,7 @@  def desthistedit(ui, repo):
     default = ui.config('histedit', 'defaultrev')
 
     if default is None:
-        revs = stack.getstack(repo)
+        revs = stackmod.stack(repo).revs
     elif default:
         revs = scmutil.revrange(repo, [default])
     else:
@@ -391,7 +391,7 @@  def desthistedit(ui, repo):
     return None
 
 def stackbase(ui, repo):
-    revs = stack.getstack(repo)
+    revs = stackmod.stack(repo).revs
     return revs.first() if revs else None
 
 def _statusotherbook(ui, repo):
diff --git a/mercurial/revset.py b/mercurial/revset.py
--- a/mercurial/revset.py
+++ b/mercurial/revset.py
@@ -1695,12 +1695,11 @@  def stack(repo, subset, x):
     parent. (EXPERIMENTAL)
     """
     if x is None:
-        stacks = stackmod.getstack(repo)
+        stacks = stackmod.stack(repo).revs
     else:
         stacks = smartset.baseset([])
         for revision in getset(repo, fullreposet(repo), x):
-            currentstack = stackmod.getstack(repo, revision)
-            stacks = stacks + currentstack
+            stacks += stackmod.stack(repo, revision).revs
 
     return subset & stacks
 
diff --git a/mercurial/stack.py b/mercurial/stack.py
--- a/mercurial/stack.py
+++ b/mercurial/stack.py
@@ -10,17 +10,27 @@  from __future__ import absolute_import
 from . import (
 )
 
-def getstack(repo, rev=None):
-    """return a sorted smartrev of the stack containing either rev if it is
-    not None or the current working directory parent.
+class stack(object):
+    """Collection of revisions grouped into a stack.
 
-    The stack will always contain all drafts changesets which are ancestors to
-    the revision and are not merges.
+    The stack usually contains all drafts changesets which are ancestors to
+    the given revision and are not merges, but extensions are allowed to modify
+    stack definition (and add new methods to this class).
     """
-    if rev is None:
-        rev = '.'
+    def __init__(self, repo, rev=None):
+        """Stack object contatining either rev (if it is not None) or the
+        current working directory parent.
+        """
+        self._repo = repo
+
+        if rev is None:
+            rev = '.'
 
-    revspec = 'only(%s) and not public() and not ::merge()'
-    revisions = repo.revs(revspec, rev)
-    revisions.sort()
-    return revisions
+        revspec = 'only(%s) and not public() and not ::merge()'
+        self.revs = self._repo.revs(revspec, rev)
+        self.revs.sort()
+
+    def __nonzero__(self):
+        return bool(self.revs)
+
+    __bool__ = __nonzero__