mercurial/wireprotov2server.py
changeset 39630 9c2c77c73f23
parent 39559 07b58266bce3
child 39632 c1aacb0d76ff
equal deleted inserted replaced
39629:a86d21e70b2b 39630:9c2c77c73f23
     7 from __future__ import absolute_import
     7 from __future__ import absolute_import
     8 
     8 
     9 import contextlib
     9 import contextlib
    10 
    10 
    11 from .i18n import _
    11 from .i18n import _
       
    12 from .node import (
       
    13     nullid,
       
    14 )
    12 from . import (
    15 from . import (
       
    16     discovery,
    13     encoding,
    17     encoding,
    14     error,
    18     error,
    15     pycompat,
    19     pycompat,
    16     streamclone,
    20     streamclone,
    17     util,
    21     util,
   458 
   462 
   459 @wireprotocommand('capabilities', permission='pull')
   463 @wireprotocommand('capabilities', permission='pull')
   460 def capabilitiesv2(repo, proto):
   464 def capabilitiesv2(repo, proto):
   461     yield _capabilitiesv2(repo, proto)
   465     yield _capabilitiesv2(repo, proto)
   462 
   466 
       
   467 @wireprotocommand('changesetdata',
       
   468                   args={
       
   469                       'noderange': [[b'0123456...'], [b'abcdef...']],
       
   470                       'nodes': [b'0123456...'],
       
   471                       'fields': {b'parents', b'revision'},
       
   472                   },
       
   473                   permission='pull')
       
   474 def changesetdata(repo, proto, noderange=None, nodes=None, fields=None):
       
   475     fields = fields or set()
       
   476 
       
   477     if noderange is None and nodes is None:
       
   478         raise error.WireprotoCommandError(
       
   479             'noderange or nodes must be defined')
       
   480 
       
   481     if noderange is not None:
       
   482         if len(noderange) != 2:
       
   483             raise error.WireprotoCommandError(
       
   484                 'noderange must consist of 2 elements')
       
   485 
       
   486         if not noderange[1]:
       
   487             raise error.WireprotoCommandError(
       
   488                 'heads in noderange request cannot be empty')
       
   489 
       
   490     cl = repo.changelog
       
   491     hasnode = cl.hasnode
       
   492 
       
   493     seen = set()
       
   494     outgoing = []
       
   495 
       
   496     if nodes is not None:
       
   497         outgoing.extend(n for n in nodes if hasnode(n))
       
   498         seen |= set(outgoing)
       
   499 
       
   500     if noderange is not None:
       
   501         if noderange[0]:
       
   502             common = [n for n in noderange[0] if hasnode(n)]
       
   503         else:
       
   504             common = [nullid]
       
   505 
       
   506         for n in discovery.outgoing(repo, common, noderange[1]).missing:
       
   507             if n not in seen:
       
   508                 outgoing.append(n)
       
   509             # Don't need to add to seen here because this is the final
       
   510             # source of nodes and there should be no duplicates in this
       
   511             # list.
       
   512 
       
   513     seen.clear()
       
   514 
       
   515     if outgoing:
       
   516         repo.hook('preoutgoing', throw=True, source='serve')
       
   517 
       
   518     yield {
       
   519         b'totalitems': len(outgoing),
       
   520     }
       
   521 
       
   522     # It is already topologically sorted by revision number.
       
   523     for node in outgoing:
       
   524         d = {
       
   525             b'node': node,
       
   526         }
       
   527 
       
   528         if b'parents' in fields:
       
   529             d[b'parents'] = cl.parents(node)
       
   530 
       
   531         revisiondata = None
       
   532 
       
   533         if b'revision' in fields:
       
   534             revisiondata = cl.revision(node, raw=True)
       
   535             d[b'revisionsize'] = len(revisiondata)
       
   536 
       
   537         yield d
       
   538 
       
   539         if revisiondata is not None:
       
   540             yield revisiondata
       
   541 
   463 @wireprotocommand('heads',
   542 @wireprotocommand('heads',
   464                   args={
   543                   args={
   465                       'publiconly': False,
   544                       'publiconly': False,
   466                   },
   545                   },
   467                   permission='pull')
   546                   permission='pull')