D4813: narrow: the first version of narrow_widen wireprotocol command

pulkit (Pulkit Goyal) phabricator at mercurial-scm.org
Tue Oct 2 17:18:52 UTC 2018


pulkit updated this revision to Diff 11572.
pulkit edited the summary of this revision.
pulkit retitled this revision from "[RFC] narrow: the first version of narrow_widen wireprotocol command" to "narrow: the first version of narrow_widen wireprotocol command".

REPOSITORY
  rHG Mercurial

CHANGES SINCE LAST UPDATE
  https://phab.mercurial-scm.org/D4813?vs=11561&id=11572

REVISION DETAIL
  https://phab.mercurial-scm.org/D4813

AFFECTED FILES
  hgext/narrow/narrowbundle2.py
  hgext/narrow/narrowcommands.py
  hgext/narrow/narrowwirepeer.py
  tests/test-narrow-widen-no-ellipsis.t

CHANGE DETAILS

diff --git a/tests/test-narrow-widen-no-ellipsis.t b/tests/test-narrow-widen-no-ellipsis.t
--- a/tests/test-narrow-widen-no-ellipsis.t
+++ b/tests/test-narrow-widen-no-ellipsis.t
@@ -104,8 +104,7 @@
   sending batch command
   searching for changes
   all local heads known remotely
-  no changes found
-  sending getbundle command
+  sending narrow_widen command
   bundle2-input-bundle: with-transaction
   bundle2-input-part: "changegroup" (params: * mandatory) supported (glob)
   adding changesets
@@ -115,12 +114,7 @@
   adding widest/f revisions (tree !)
   added 0 changesets with 1 changes to 1 files
   bundle2-input-part: total payload size * (glob)
-  bundle2-input-part: "listkeys" (params: 1 mandatory) supported
-  bundle2-input-part: "phase-heads" supported
-  bundle2-input-part: total payload size 24
-  bundle2-input-bundle: 2 parts total
-  checking for updated bookmarks
-  3 local changesets published
+  bundle2-input-bundle: 0 parts total
    widest/f: add from widened narrow clone -> g
   getting widest/f
   $ hg tracked
@@ -143,6 +137,7 @@
   adding file changes
   added 5 changesets with 4 changes to 2 files
   new changesets *:* (glob)
+  3 local changesets published
   (run 'hg update' to get a working copy)
   $ hg update -r 'desc("add wider")'
   1 files updated, 0 files merged, 0 files removed, 0 files unresolved
@@ -179,12 +174,10 @@
   $ hg tracked --addinclude wider
   comparing with ssh://user@dummy/master
   searching for changes
-  no changes found
   adding changesets
   adding manifests
   adding file changes
   added 0 changesets with 1 changes to 1 files
-  5 local changesets published
   $ hg tracked
   I path:inside
   I path:wider
@@ -284,12 +277,10 @@
   $ hg tracked --addinclude d1
   comparing with ssh://user@dummy/upstream
   searching for changes
-  no changes found
   adding changesets
   adding manifests
   adding file changes
   added 0 changesets with 1 changes to 1 files
-  11 local changesets published
   $ hg tracked
   I path:d0
   I path:d1
@@ -376,12 +367,10 @@
   $ hg --config hooks.pretxnchangegroup.bad=false tracked --addinclude d1
   comparing with ssh://user@dummy/upstream
   searching for changes
-  no changes found
   adding changesets
   adding manifests
   adding file changes
   added 0 changesets with 1 changes to 1 files
-  11 local changesets published
   $ hg log -T "{if(ellipsis, '...')}{rev}: {desc}\n"
   11: local
   10: add d10/f
diff --git a/hgext/narrow/narrowwirepeer.py b/hgext/narrow/narrowwirepeer.py
--- a/hgext/narrow/narrowwirepeer.py
+++ b/hgext/narrow/narrowwirepeer.py
@@ -8,14 +8,22 @@
 from __future__ import absolute_import
 
 from mercurial import (
+    bundle2,
     extensions,
     hg,
+    match as matchmod,
+    narrowspec,
     wireprotoserver,
+    wireprototypes,
+    wireprotov1peer,
     wireprotov1server,
 )
 
+from . import narrowbundle2
+
 def uisetup():
     extensions.wrapfunction(wireprotov1server, '_capabilities', addnarrowcap)
+    wireprotov1peer.wirepeer.narrow_widen = peernarrowwiden
 
 def addnarrowcap(orig, repo, proto):
     """add the narrow capability to the server"""
@@ -37,3 +45,65 @@
             return orig(cmd, *args, **kwargs)
         extensions.wrapfunction(peer, '_calltwowaystream', wrapped)
     hg.wirepeersetupfuncs.append(wirereposetup)
+
+ at wireprotov1server.wireprotocommand('narrow_widen', '*', permission='pull')
+def narrow_widen(repo, proto, args):
+    """wireprotocol command to send data when a narrow clone is widen. We will
+    be sending a changegroup here.
+
+    The current set of arguments which are required:
+    oldincludes: the old includes of the narrow copy
+    oldexcludes: the old excludes of the narrow copy
+    newincludes: the new includes of the narrow copy
+    newexcludes: the new excludes of the narrow copy
+    common: list of nodes which are common between the server and client
+    cgversion(maybe): the changegroup version to produce
+    known: list of nodes which are known on the client (used in ellipses cases)
+    ellipses: whether to send ellipses data or not
+    """
+
+    oldincludes = wireprototypes.decodelist(args.get('oldincludes'))
+    newincludes = wireprototypes.decodelist(args.get('newincludes'))
+    oldexcludes = wireprototypes.decodelist(args.get('oldexcludes'))
+    newexcludes = wireprototypes.decodelist(args.get('newexcludes'))
+    # validate the patterns
+    narrowspec.validatepatterns(set(oldincludes))
+    narrowspec.validatepatterns(set(newincludes))
+    narrowspec.validatepatterns(set(oldexcludes))
+    narrowspec.validatepatterns(set(newexcludes))
+
+    common = wireprototypes.decodelist(args.get('common'))
+    known = None
+    if args.get('known'):
+        known = wireprototypes.decodelist(args.get('known'))
+    if args.get('ellipses') == '0':
+        ellipses = False
+    else:
+        ellipses = bool(args.get('ellipses'))
+    cgversion = args.get('cgversion')
+    newmatch = narrowspec.match(repo.root, include=newincludes,
+                                exclude=newexcludes)
+    oldmatch = narrowspec.match(repo.root, include=oldincludes,
+                                exclude=oldexcludes)
+    diffmatch = matchmod.differencematcher(newmatch, oldmatch)
+
+    bundler = bundle2.bundle20(repo.ui)
+    # get changegroup data
+    cg = narrowbundle2.widen_bundle(repo, diffmatch, common, known, cgversion,
+                                    ellipses)
+    if cg is not None:
+        part = bundler.newpart('changegroup', data=cg)
+        part.addparam('version', cgversion)
+        if 'treemanifest' in repo.requirements:
+            part.addparam('treemanifest', '1')
+    chunks = bundler.getchunks()
+    return wireprototypes.streamres(gen=chunks)
+
+def peernarrowwiden(remote, **kwargs):
+    for ch in ('oldincludes', 'newincludes', 'oldexcludes', 'newexcludes',
+               'common', 'known'):
+        kwargs[ch] = wireprototypes.encodelist(kwargs[ch])
+
+    kwargs['ellipses'] = '%i' % bool(kwargs['ellipses'])
+    f = remote._callcompressable('narrow_widen', **kwargs)
+    return bundle2.getunbundler(remote.ui, f)
diff --git a/hgext/narrow/narrowcommands.py b/hgext/narrow/narrowcommands.py
--- a/hgext/narrow/narrowcommands.py
+++ b/hgext/narrow/narrowcommands.py
@@ -11,6 +11,7 @@
 
 from mercurial.i18n import _
 from mercurial import (
+    bundle2,
     cmdutil,
     commands,
     discovery,
@@ -265,7 +266,6 @@
         # The old{in,ex}cludepats have already been set by orig()
         kwargs['includepats'] = newincludes
         kwargs['excludepats'] = newexcludes
-        kwargs['widen'] = True
     wrappedextraprepare = extensions.wrappedfunction(exchange,
         '_pullbundle2extraprepare', pullbundle2extraprepare_widen)
 
@@ -290,9 +290,24 @@
             with ds.parentchange():
                 ds.setparents(p1, p2)
         else:
-            with wrappedextraprepare,\
-                 repo.ui.configoverride(overrides, 'widen'):
-                exchange.pull(repo, remote, heads=common)
+            with repo.transaction('widening') as tr,\
+                 remote.commandexecutor() as e:
+                known = []
+                bundle = e.callcommand('narrow_widen', {
+                    'oldincludes': oldincludes,
+                    'oldexcludes': oldexcludes,
+                    'newincludes': newincludes,
+                    'newexcludes': newexcludes,
+                    'cgversion': '03',
+                    'common': common,
+                    'known': known,
+                    'ellipses': False,
+                }).result()
+
+                with repo.ui.configoverride(overrides, 'widen'):
+                    tgetter = lambda: tr
+                    bundle2.processbundle(repo, bundle,
+                            transactiongetter=tgetter)
 
         repo.setnewnarrowpats()
         actions = {k: [] for k in 'a am f g cd dc r dm dg m e k p pr'.split()}
diff --git a/hgext/narrow/narrowbundle2.py b/hgext/narrow/narrowbundle2.py
--- a/hgext/narrow/narrowbundle2.py
+++ b/hgext/narrow/narrowbundle2.py
@@ -85,41 +85,6 @@
 
     return None
 
-def getbundlechangegrouppart_widen(bundler, repo, source, bundlecaps=None,
-                                   b2caps=None, heads=None, common=None,
-                                   **kwargs):
-    """Handling changegroup changegroup generation on the server when user
-    is widening their narrowspec"""
-
-    cgversions = b2caps.get('changegroup')
-    if cgversions:  # 3.1 and 3.2 ship with an empty value
-        cgversions = [v for v in cgversions
-                      if v in changegroup.supportedoutgoingversions(repo)]
-        if not cgversions:
-            raise ValueError(_('no common changegroup version'))
-        version = max(cgversions)
-    else:
-        raise ValueError(_("server does not advertise changegroup version,"
-                           " can't negotiate support for ellipsis nodes"))
-
-    include = sorted(filter(bool, kwargs.get(r'includepats', [])))
-    exclude = sorted(filter(bool, kwargs.get(r'excludepats', [])))
-    newmatch = narrowspec.match(repo.root, include=include, exclude=exclude)
-    oldinclude = sorted(filter(bool, kwargs.get(r'oldincludepats', [])))
-    oldexclude = sorted(filter(bool, kwargs.get(r'oldexcludepats', [])))
-    oldmatch = narrowspec.match(repo.root, include=oldinclude,
-                                exclude=oldexclude)
-    diffmatch = matchmod.differencematcher(newmatch, oldmatch)
-    common = set(common or [nullid])
-
-    if (oldinclude != include or oldexclude != exclude):
-        cgdata = widen_bundle(repo, diffmatch, common, [], version, False)
-        if cgdata is not None:
-            part = bundler.newpart('changegroup', data=cgdata)
-            part.addparam('version', version)
-            if 'treemanifest' in repo.requirements:
-                part.addparam('treemanifest', '1')
-
 # Serve a changegroup for a client with a narrow clone.
 def getbundlechangegrouppart_narrow(bundler, repo, source,
                                     bundlecaps=None, b2caps=None, heads=None,
@@ -327,7 +292,6 @@
     getbundleargs = wireprototypes.GETBUNDLE_ARGUMENTS
 
     getbundleargs['narrow'] = 'boolean'
-    getbundleargs['widen'] = 'boolean'
     getbundleargs['depth'] = 'plain'
     getbundleargs['oldincludepats'] = 'csv'
     getbundleargs['oldexcludepats'] = 'csv'
@@ -345,8 +309,6 @@
         if (kwargs.get(r'narrow', False) and
             repo.ui.configbool('experimental', 'narrowservebrokenellipses')):
             getbundlechangegrouppart_narrow(*args, **kwargs)
-        elif kwargs.get(r'widen', False) and kwargs.get(r'narrow', False):
-            getbundlechangegrouppart_widen(*args, **kwargs)
         else:
             origcgfn(*args, **kwargs)
     exchange.getbundle2partsmapping['changegroup'] = wrappedcgfn



To: pulkit, durin42, #hg-reviewers, martinvonz
Cc: indygreg, mercurial-devel


More information about the Mercurial-devel mailing list