narrowwirepeer.py
160 lines
| 4.8 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 | ||
|
r43346 | |||
|
r36096 | def uisetup(): | ||
|
r40106 | wireprotov1peer.wirepeer.narrow_widen = peernarrowwiden | ||
|
r39559 | |||
|
r43346 | |||
|
r36096 | def reposetup(repo): | ||
def wirereposetup(ui, peer): | ||||
def wrapped(orig, cmd, *args, **kwargs): | ||||
|
r43347 | if cmd == b'unbundle': | ||
|
r36119 | # TODO: don't blindly add include/exclude wireproto | ||
# arguments to unbundle. | ||||
|
r36096 | include, exclude = repo.narrowpats | ||
|
r43347 | kwargs[r"includepats"] = b','.join(include) | ||
kwargs[r"excludepats"] = b','.join(exclude) | ||||
|
r36096 | return orig(cmd, *args, **kwargs) | ||
|
r43346 | |||
|
r43347 | extensions.wrapfunction(peer, b'_calltwowaystream', wrapped) | ||
|
r43346 | |||
|
r36096 | hg.wirepeersetupfuncs.append(wirereposetup) | ||
|
r40106 | |||
|
r43346 | |||
@wireprotov1server.wireprotocommand( | ||||
|
r43347 | b'narrow_widen', | ||
b'oldincludes oldexcludes' | ||||
b' newincludes newexcludes' | ||||
b' commonheads cgversion' | ||||
b' known ellipses', | ||||
permission=b'pull', | ||||
|
r43346 | ) | ||
def narrow_widen( | ||||
repo, | ||||
proto, | ||||
oldincludes, | ||||
oldexcludes, | ||||
newincludes, | ||||
newexcludes, | ||||
commonheads, | ||||
cgversion, | ||||
known, | ||||
ellipses, | ||||
): | ||||
|
r40106 | """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: | ||
|
r43346 | |||
|
r43214 | def splitpaths(data): | ||
# work around ''.split(',') => [''] | ||||
return data.split(b',') if data else [] | ||||
|
r43346 | |||
|
r43214 | 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) | ||
|
r43347 | if ellipses == b'0': | ||
|
r40106 | ellipses = False | ||
else: | ||||
ellipses = bool(ellipses) | ||||
cgversion = cgversion | ||||
|
r42607 | bundler = bundle2.bundle20(repo.ui) | ||
|
r42605 | if not ellipses: | ||
|
r43346 | newmatch = narrowspec.match( | ||
repo.root, include=newincludes, exclude=newexcludes | ||||
) | ||||
oldmatch = narrowspec.match( | ||||
repo.root, include=oldincludes, exclude=oldexcludes | ||||
) | ||||
bundle2.widen_bundle( | ||||
bundler, | ||||
repo, | ||||
oldmatch, | ||||
newmatch, | ||||
common, | ||||
known, | ||||
cgversion, | ||||
ellipses, | ||||
) | ||||
|
r42605 | else: | ||
|
r43517 | narrowbundle2.generate_ellipses_bundle2_for_widening( | ||
|
r43346 | bundler, | ||
repo, | ||||
oldincludes, | ||||
oldexcludes, | ||||
newincludes, | ||||
newexcludes, | ||||
cgversion, | ||||
common, | ||||
list(common), | ||||
known, | ||||
None, | ||||
) | ||||
|
r40106 | except error.Abort as exc: | ||
|
r40107 | bundler = bundle2.bundle20(repo.ui) | ||
|
r43347 | manargs = [(b'message', pycompat.bytestr(exc))] | ||
|
r40106 | advargs = [] | ||
if exc.hint is not None: | ||||
|
r43347 | advargs.append((b'hint', exc.hint)) | ||
bundler.addpart(bundle2.bundlepart(b'error:abort', manargs, advargs)) | ||||
|
r40183 | preferuncompressed = True | ||
|
r40106 | |||
chunks = bundler.getchunks() | ||||
|
r43346 | 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]) | ||||
|
r43347 | kwargs[r'ellipses'] = b'%i' % bool(kwargs[r'ellipses']) | ||
f = remote._callcompressable(b'narrow_widen', **kwargs) | ||||
|
r40106 | return bundle2.getunbundler(remote.ui, f) | ||