narrowwirepeer.py
118 lines
| 4.6 KiB
| text/x-python
|
PythonLexer
|
r36096 | # narrowwirepeer.py - passes narrow spec with unbundle command | ||
# | ||||
# Copyright 2017 Google, Inc. | ||||
# | ||||
# This software may be used and distributed according to the terms of the | ||||
# GNU General Public License version 2 or any later version. | ||||
from __future__ import absolute_import | ||||
from mercurial import ( | ||||
|
r40106 | bundle2, | ||
error, | ||||
|
r36096 | extensions, | ||
hg, | ||||
|
r40106 | narrowspec, | ||
pycompat, | ||||
wireprototypes, | ||||
wireprotov1peer, | ||||
|
r39559 | wireprotov1server, | ||
|
r36096 | ) | ||
|
r42605 | from . import narrowbundle2 | ||
|
r36096 | def uisetup(): | ||
|
r40106 | wireprotov1peer.wirepeer.narrow_widen = peernarrowwiden | ||
|
r39559 | |||
|
r36096 | def reposetup(repo): | ||
def wirereposetup(ui, peer): | ||||
def wrapped(orig, cmd, *args, **kwargs): | ||||
if cmd == 'unbundle': | ||||
|
r36119 | # TODO: don't blindly add include/exclude wireproto | ||
# arguments to unbundle. | ||||
|
r36096 | include, exclude = repo.narrowpats | ||
|
r36369 | kwargs[r"includepats"] = ','.join(include) | ||
kwargs[r"excludepats"] = ','.join(exclude) | ||||
|
r36096 | return orig(cmd, *args, **kwargs) | ||
extensions.wrapfunction(peer, '_calltwowaystream', wrapped) | ||||
hg.wirepeersetupfuncs.append(wirereposetup) | ||||
|
r40106 | |||
@wireprotov1server.wireprotocommand('narrow_widen', 'oldincludes oldexcludes' | ||||
' newincludes newexcludes' | ||||
' commonheads cgversion' | ||||
' known ellipses', | ||||
permission='pull') | ||||
def narrow_widen(repo, proto, oldincludes, oldexcludes, newincludes, | ||||
newexcludes, commonheads, cgversion, known, ellipses): | ||||
"""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 | ||||
commonheads: list of heads 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 | ||||
""" | ||||
|
r40183 | preferuncompressed = False | ||
|
r40106 | try: | ||
|
r43214 | def splitpaths(data): | ||
# work around ''.split(',') => [''] | ||||
return data.split(b',') if data else [] | ||||
oldincludes = splitpaths(oldincludes) | ||||
newincludes = splitpaths(newincludes) | ||||
oldexcludes = splitpaths(oldexcludes) | ||||
newexcludes = splitpaths(newexcludes) | ||||
|
r40106 | # validate the patterns | ||
narrowspec.validatepatterns(set(oldincludes)) | ||||
narrowspec.validatepatterns(set(newincludes)) | ||||
narrowspec.validatepatterns(set(oldexcludes)) | ||||
narrowspec.validatepatterns(set(newexcludes)) | ||||
common = wireprototypes.decodelist(commonheads) | ||||
|
r42605 | known = wireprototypes.decodelist(known) | ||
|
r40106 | if ellipses == '0': | ||
ellipses = False | ||||
else: | ||||
ellipses = bool(ellipses) | ||||
cgversion = cgversion | ||||
|
r42607 | bundler = bundle2.bundle20(repo.ui) | ||
|
r42605 | if not ellipses: | ||
newmatch = narrowspec.match(repo.root, include=newincludes, | ||||
exclude=newexcludes) | ||||
oldmatch = narrowspec.match(repo.root, include=oldincludes, | ||||
exclude=oldexcludes) | ||||
|
r42607 | bundle2.widen_bundle(bundler, repo, oldmatch, newmatch, common, | ||
known, cgversion, ellipses) | ||||
|
r42605 | else: | ||
narrowbundle2.generateellipsesbundle2(bundler, repo, oldincludes, | ||||
oldexcludes, newincludes, newexcludes, cgversion, common, | ||||
list(common), known, None) | ||||
|
r40106 | except error.Abort as exc: | ||
|
r40107 | bundler = bundle2.bundle20(repo.ui) | ||
|
r40106 | manargs = [('message', pycompat.bytestr(exc))] | ||
advargs = [] | ||||
if exc.hint is not None: | ||||
advargs.append(('hint', exc.hint)) | ||||
bundler.addpart(bundle2.bundlepart('error:abort', manargs, advargs)) | ||||
|
r40183 | preferuncompressed = True | ||
|
r40106 | |||
chunks = bundler.getchunks() | ||||
|
r40183 | return wireprototypes.streamres(gen=chunks, | ||
prefer_uncompressed=preferuncompressed) | ||||
|
r40106 | |||
def peernarrowwiden(remote, **kwargs): | ||||
|
r43214 | for ch in (r'commonheads', r'known'): | ||
|
r40106 | kwargs[ch] = wireprototypes.encodelist(kwargs[ch]) | ||
|
r43214 | for ch in (r'oldincludes', r'newincludes', r'oldexcludes', r'newexcludes'): | ||
kwargs[ch] = b','.join(kwargs[ch]) | ||||
|
r40248 | kwargs[r'ellipses'] = '%i' % bool(kwargs[r'ellipses']) | ||
|
r40106 | f = remote._callcompressable('narrow_widen', **kwargs) | ||
return bundle2.getunbundler(remote.ui, f) | ||||