[PATCH 1 of 5] hidden: Initial mechanism

pierre-yves.david at logilab.fr pierre-yves.david at logilab.fr
Wed Jun 15 10:26:41 CDT 2011


# HG changeset patch
# User Pierre-Yves David <pierre-yves.david at logilab.fr>
# Date 1308148662 -7200
# Node ID 57e274bf5a792646ca7f8a09aabd4c4faaa686e7
# Parent  adbf5e7df96df6841314393dd861d804ceccbfc7
hidden: Initial mechanism

Add a mechanism to mark revision as hidden.

* An hidden revision wont appear in log if it's hidden.
* Non-hidden children of hidden changeset nullify the request.

diff --git a/mercurial/changelog.py b/mercurial/changelog.py
--- a/mercurial/changelog.py
+++ b/mercurial/changelog.py
@@ -105,10 +105,49 @@ class changelog(revlog.revlog):
             self.version &= ~revlog.REVLOGGENERALDELTA
             self._generaldelta = False
         self._realopener = opener
         self._delayed = False
         self._divert = False
+        self._hidden = set()
+        self._hidable = set()
+
+    def hidden(self, rev):
+        """Is rev hidden?"""
+        return rev in self._hidden
+
+    def hide(self, rev):
+        """Request to hide a revision,
+
+        The request won't take effect until all children are hidden too.
+        """
+        self._hidable.add(rev)
+        self._refreshhidden()
+
+    def _refreshhidden(self):
+        """Recompute the set of hidden revision
+
+        A revision is hidden if both:
+            * He is in the hidable,
+            * all it's descendant are also hidable."""
+
+        self._hidden.clear()
+        # all nodes known to be shown
+        shown = set()
+        candidates = set(self._hidable)
+        # iterate in reverse topological order to make sure children of X
+        # are resolved before we evalute X
+        for cand in sorted(self._hidable, reverse=True):
+            # self.children take node ...
+            node = self.node(cand)
+            for childnode in self.children(node):
+                # self.children return node ...
+                child = self.rev(childnode)
+                if child in shown or child not in candidates:
+                    shown.update((cand, child))
+                    break
+            else: # if no break
+                self._hidden.add(cand)
 
     def delayupdate(self):
         "delay visibility of index updates to other readers"
         self._delayed = True
         self._divert = (len(self) == 0)
diff --git a/mercurial/commands.py b/mercurial/commands.py
--- a/mercurial/commands.py
+++ b/mercurial/commands.py
@@ -3337,10 +3337,11 @@ def locate(ui, repo, *pats, **opts):
      _('BRANCH')),
     ('b', 'branch', [],
      _('show changesets within the given named branch'), _('BRANCH')),
     ('P', 'prune', [],
      _('do not display revision or any of its ancestors'), _('REV')),
+    ('h', 'hidden', False, _('show hidden changesets')),
     ] + logopts + walkopts,
     _('[OPTION]... [FILE]'))
 def log(ui, repo, *pats, **opts):
     """show revision history of entire repository or files
 
@@ -3398,10 +3399,12 @@ def log(ui, repo, *pats, **opts):
             return
         if opts.get('only_merges') and len(parents) != 2:
             return
         if opts.get('branch') and ctx.branch() not in opts['branch']:
             return
+        if not opts.get('hidden') and ctx.hidden():
+            return
         if df and not df(ctx.date()[0]):
             return
         if opts['user'] and not [k for k in opts['user']
                                  if k.lower() in ctx.user().lower()]:
             return
diff --git a/mercurial/context.py b/mercurial/context.py
--- a/mercurial/context.py
+++ b/mercurial/context.py
@@ -108,10 +108,12 @@ class changectx(object):
         return self._changeset[3]
     def description(self):
         return self._changeset[4]
     def branch(self):
         return encoding.tolocal(self._changeset[5].get("branch"))
+    def hidden(self):
+        return self._repo.changelog.hidden(self._rev)
     def extra(self):
         return self._changeset[5]
     def tags(self):
         return self._repo.nodetags(self._node)
     def bookmarks(self):
diff --git a/tests/test-debugcomplete.t b/tests/test-debugcomplete.t
--- a/tests/test-debugcomplete.t
+++ b/tests/test-debugcomplete.t
@@ -192,11 +192,11 @@ Show all commands + options
   commit: addremove, close-branch, include, exclude, message, logfile, date, user
   diff: rev, change, text, git, nodates, show-function, reverse, ignore-all-space, ignore-space-change, ignore-blank-lines, unified, stat, include, exclude, subrepos
   export: output, switch-parent, rev, text, git, nodates
   forget: include, exclude
   init: ssh, remotecmd, insecure
-  log: follow, follow-first, date, copies, keyword, rev, removed, only-merges, user, only-branch, branch, prune, patch, git, limit, no-merges, stat, style, template, include, exclude
+  log: follow, follow-first, date, copies, keyword, rev, removed, only-merges, user, only-branch, branch, prune, hidden, patch, git, limit, no-merges, stat, style, template, include, exclude
   merge: force, tool, rev, preview
   pull: update, force, rev, bookmark, branch, ssh, remotecmd, insecure
   push: force, rev, bookmark, branch, new-branch, ssh, remotecmd, insecure
   remove: after, force, include, exclude
   serve: accesslog, daemon, daemon-pipefds, errorlog, port, address, prefix, name, web-conf, webdir-conf, pid-file, stdio, templates, style, ipv6, certificate
diff --git a/tests/test-log.t b/tests/test-log.t
--- a/tests/test-log.t
+++ b/tests/test-log.t
@@ -1136,5 +1136,232 @@ Diff here should be the same:
   changeset:   0:9f758d63dcde
   user:        test
   date:        Thu Jan 01 00:00:00 1970 +0000
   summary:     a
   
+
+Test hidden mechanism
+init repo
+
+  $ cd $HGTMP
+  $ cat > hidden.py << EOF
+  > def reposetup(ui, repo):
+  >     for line in repo.opener('hidden'):
+  >         hex, comment = line.split(' ', 1)
+  >         ctx = repo[hex]
+  >         repo.changelog.hide(ctx.rev())
+  > EOF
+  $ echo '[extensions]' >> $HGRCPATH
+  $ echo "hidden=$HGTMP/hidden.py" >> $HGRCPATH
+  $ hg init hiddentest
+  $ cd hiddentest
+  $ touch .hg/hidden
+  $ echo '_' > a; echo '_' > b
+  $ hg add a b; hg ci -m 0
+  $ echo '1' >> a; hg ci -m 1
+  $ echo '2' >> a; hg ci -m 2
+  $ echo '3' >> a; hg ci -m 3
+  $ echo '4' >> a; hg ci -m 4
+  $ hg up 3 -q
+  $ echo '5' >> b; hg ci -m 5 -q
+  $ echo '6' >> b; hg ci -m 6
+  $ hg merge 4 -q; hg ci -m 7
+  $ echo '8' >> a; hg ci -m 8
+  $ hg up 3 -q
+  $ echo '9' >> a; hg ci -m 9 -q
+  $ echo '10' >> a; hg ci -m 10
+  $ echo '11' >> a; hg ci -m 11
+  $ echo '12' >> a; hg ci -m 12
+  $ hg up 10 -q
+  $ echo '13' >> a; hg ci -m 13 -q
+  $ echo '14' >> a; hg ci -m 14
+  $ echo '15' >> a; hg ci -m 15
+  $ hg --config "extensions.graphlog=" glog
+  @  changeset:   15:c8e4494f8126
+  |  tag:         tip
+  |  user:        test
+  |  date:        Thu Jan 01 00:00:00 1970 +0000
+  |  summary:     15
+  |
+  o  changeset:   14:aa3059824d26
+  |  user:        test
+  |  date:        Thu Jan 01 00:00:00 1970 +0000
+  |  summary:     14
+  |
+  o  changeset:   13:5c1055d45d20
+  |  parent:      10:dff9b57eca11
+  |  user:        test
+  |  date:        Thu Jan 01 00:00:00 1970 +0000
+  |  summary:     13
+  |
+  | o  changeset:   12:88baa6741396
+  | |  user:        test
+  | |  date:        Thu Jan 01 00:00:00 1970 +0000
+  | |  summary:     12
+  | |
+  | o  changeset:   11:b258c7a46440
+  |/   user:        test
+  |    date:        Thu Jan 01 00:00:00 1970 +0000
+  |    summary:     11
+  |
+  o  changeset:   10:dff9b57eca11
+  |  user:        test
+  |  date:        Thu Jan 01 00:00:00 1970 +0000
+  |  summary:     10
+  |
+  o  changeset:   9:a756506fd35a
+  |  parent:      3:60e67a92a94f
+  |  user:        test
+  |  date:        Thu Jan 01 00:00:00 1970 +0000
+  |  summary:     9
+  |
+  | o  changeset:   8:2d3fca4ddc00
+  | |  user:        test
+  | |  date:        Thu Jan 01 00:00:00 1970 +0000
+  | |  summary:     8
+  | |
+  | o    changeset:   7:2a88ca465041
+  | |\   parent:      6:ad1c999002ef
+  | | |  parent:      4:a59ff34372ac
+  | | |  user:        test
+  | | |  date:        Thu Jan 01 00:00:00 1970 +0000
+  | | |  summary:     7
+  | | |
+  | | o  changeset:   6:ad1c999002ef
+  | | |  user:        test
+  | | |  date:        Thu Jan 01 00:00:00 1970 +0000
+  | | |  summary:     6
+  | | |
+  +---o  changeset:   5:2b505b595288
+  | |    parent:      3:60e67a92a94f
+  | |    user:        test
+  | |    date:        Thu Jan 01 00:00:00 1970 +0000
+  | |    summary:     5
+  | |
+  | o  changeset:   4:a59ff34372ac
+  |/   user:        test
+  |    date:        Thu Jan 01 00:00:00 1970 +0000
+  |    summary:     4
+  |
+  o  changeset:   3:60e67a92a94f
+  |  user:        test
+  |  date:        Thu Jan 01 00:00:00 1970 +0000
+  |  summary:     3
+  |
+  o  changeset:   2:473f5001ac99
+  |  user:        test
+  |  date:        Thu Jan 01 00:00:00 1970 +0000
+  |  summary:     2
+  |
+  o  changeset:   1:10a761c17446
+  |  user:        test
+  |  date:        Thu Jan 01 00:00:00 1970 +0000
+  |  summary:     1
+  |
+  o  changeset:   0:cda5afe6f3d2
+     user:        test
+     date:        Thu Jan 01 00:00:00 1970 +0000
+     summary:     0
+  
+  $ hg log --template='{rev}:{node}\n'
+  15:c8e4494f8126a1b6c5b0143d44518ba77a1457a9
+  14:aa3059824d26659d090e95773db87504e454d708
+  13:5c1055d45d20f4ed08ce50f91bc4896ec91ffe91
+  12:88baa6741396ecbffa195b125b52c553dd3d0462
+  11:b258c7a4644063b85a3a36c1cf3f3cd51ab3529a
+  10:dff9b57eca11c4645fb2122c1f5d7d7b78fdac3f
+  9:a756506fd35a49b3cf99915d8974308df4bef7ec
+  8:2d3fca4ddc00bb9c098e4a99baa6a0e80dae923f
+  7:2a88ca4650410d49e4c69ebcfde85c90fce3e363
+  6:ad1c999002efac0128ef8235618f8982372ca1d6
+  5:2b505b5952886a816e27527a9dc3c1d82b415ea9
+  4:a59ff34372acc3e4b8eb208f662f33f1ef5a8950
+  3:60e67a92a94fc211dc726afc04db428f12fe0f86
+  2:473f5001ac99bfef17310952fce2d98a7249fd6d
+  1:10a761c174467562fcd0b38ce817a547b90b6f59
+  0:cda5afe6f3d23455dbf4e60220dae437aa716994
+
+init repo simple hidden
+
+  $ cat > .hg/hidden  << EOF
+  > c8e4494f8126a1b6c5b0143d44518ba77a1457a9 some reason for 15
+  > aa3059824d26659d090e95773db87504e454d708 babar for 14
+  > EOF
+  $ hg log --template='{rev}\n'
+  13
+  12
+  11
+  10
+  9
+  8
+  7
+  6
+  5
+  4
+  3
+  2
+  1
+  0
+  $ hg log --hidden --template='{rev}\n'
+  15
+  14
+  13
+  12
+  11
+  10
+  9
+  8
+  7
+  6
+  5
+  4
+  3
+  2
+  1
+  0
+
+init repo complex
+
+  $ cat > .hg/hidden  << EOF
+  > 60e67a92a94fc211dc726afc04db428f12fe0f86 won't work for 3
+  > a59ff34372acc3e4b8eb208f662f33f1ef5a8950 should work for 4
+  > 2d3fca4ddc00bb9c098e4a99baa6a0e80dae923f ok for 8 (the head)
+  > 2a88ca4650410d49e4c69ebcfde85c90fce3e363 ok for 7
+  > EOF
+  $ hg log --template='{rev}\n'
+  15
+  14
+  13
+  12
+  11
+  10
+  9
+  6
+  5
+  3
+  2
+  1
+  0
+  $ cat > .hg/hidden  << EOF
+  > 5c1055d45d20f4ed08ce50f91bc4896ec91ffe91 won't work for 13
+  > b258c7a4644063b85a3a36c1cf3f3cd51ab3529a zou for 11
+  > 88baa6741396ecbffa195b125b52c553dd3d0462 ok for 12
+  > dff9b57eca11c4645fb2122c1f5d7d7b78fdac3f 10 won't work (branch)
+  > 2d3fca4ddc00bb9c098e4a99baa6a0e80dae923f 8 is a head
+  > ad1c999002efac0128ef8235618f8982372ca1d6 6 has no hope
+  > dff9b57eca11c4645fb2122c1f5d7d7b78fdac3f have duplicated request for 10
+  > 2b505b5952886a816e27527a9dc3c1d82b415ea9 5 idem
+  > EOF
+  $ hg log --template='{rev}\n'
+  15
+  14
+  13
+  10
+  9
+  7
+  6
+  5
+  4
+  3
+  2
+  1
+  0


More information about the Mercurial-devel mailing list