Mercurial > hg
comparison mercurial/changegroup.py @ 38794:1d01cf0416a5
changegroup: move file matcher from narrow extension
Sparse changegroup generation requires the use of a matcher to
filter which files are relevant.
This commit moves the file matcher from the narrow extension to core
and updates the narrow extension to use it.
I'm not sure why the narrow extension was storing the matcher as
a callable that resolved to a matcher. So I changed it to be a
simple matcher instance.
In addition, code from narrow to intersect the matcher with the local
narrow spec is now performed automatically when the changegroup
packer is created.
If a matcher is not passed into getbundler() an alwaysmatcher() is
assumed. This ensures that a matcher is always defined for all
operations.
Differential Revision: https://phab.mercurial-scm.org/D4011
author | Gregory Szorc <gregory.szorc@gmail.com> |
---|---|
date | Sat, 28 Jul 2018 11:40:31 -0700 |
parents | e7aa113b14f7 |
children | 5742d0428ed9 |
comparison
equal
deleted
inserted
replaced
38793:6c8e3c847977 | 38794:1d01cf0416a5 |
---|---|
19 ) | 19 ) |
20 | 20 |
21 from . import ( | 21 from . import ( |
22 dagutil, | 22 dagutil, |
23 error, | 23 error, |
24 match as matchmod, | |
24 mdiff, | 25 mdiff, |
25 phases, | 26 phases, |
26 pycompat, | 27 pycompat, |
27 util, | 28 util, |
28 ) | 29 ) |
494 return readexactly(self._fh, n) | 495 return readexactly(self._fh, n) |
495 | 496 |
496 class cg1packer(object): | 497 class cg1packer(object): |
497 deltaheader = _CHANGEGROUPV1_DELTA_HEADER | 498 deltaheader = _CHANGEGROUPV1_DELTA_HEADER |
498 version = '01' | 499 version = '01' |
499 def __init__(self, repo, bundlecaps=None): | 500 def __init__(self, repo, filematcher, bundlecaps=None): |
500 """Given a source repo, construct a bundler. | 501 """Given a source repo, construct a bundler. |
502 | |
503 filematcher is a matcher that matches on files to include in the | |
504 changegroup. Used to facilitate sparse changegroups. | |
501 | 505 |
502 bundlecaps is optional and can be used to specify the set of | 506 bundlecaps is optional and can be used to specify the set of |
503 capabilities which can be used to build the bundle. While bundlecaps is | 507 capabilities which can be used to build the bundle. While bundlecaps is |
504 unused in core Mercurial, extensions rely on this feature to communicate | 508 unused in core Mercurial, extensions rely on this feature to communicate |
505 capabilities to customize the changegroup packer. | 509 capabilities to customize the changegroup packer. |
506 """ | 510 """ |
511 assert filematcher | |
512 self._filematcher = filematcher | |
513 | |
507 # Set of capabilities we can use to build the bundle. | 514 # Set of capabilities we can use to build the bundle. |
508 if bundlecaps is None: | 515 if bundlecaps is None: |
509 bundlecaps = set() | 516 bundlecaps = set() |
510 self._bundlecaps = bundlecaps | 517 self._bundlecaps = bundlecaps |
511 # experimental config: bundle.reorder | 518 # experimental config: bundle.reorder |
811 | 818 |
812 class cg2packer(cg1packer): | 819 class cg2packer(cg1packer): |
813 version = '02' | 820 version = '02' |
814 deltaheader = _CHANGEGROUPV2_DELTA_HEADER | 821 deltaheader = _CHANGEGROUPV2_DELTA_HEADER |
815 | 822 |
816 def __init__(self, repo, bundlecaps=None): | 823 def __init__(self, repo, filematcher, bundlecaps=None): |
817 super(cg2packer, self).__init__(repo, bundlecaps) | 824 super(cg2packer, self).__init__(repo, filematcher, |
825 bundlecaps=bundlecaps) | |
826 | |
818 if self._reorder is None: | 827 if self._reorder is None: |
819 # Since generaldelta is directly supported by cg2, reordering | 828 # Since generaldelta is directly supported by cg2, reordering |
820 # generally doesn't help, so we disable it by default (treating | 829 # generally doesn't help, so we disable it by default (treating |
821 # bundle.reorder=auto just like bundle.reorder=False). | 830 # bundle.reorder=auto just like bundle.reorder=False). |
822 self._reorder = False | 831 self._reorder = False |
925 if 'generaldelta' in repo.requirements: | 934 if 'generaldelta' in repo.requirements: |
926 versions.discard('01') | 935 versions.discard('01') |
927 assert versions | 936 assert versions |
928 return min(versions) | 937 return min(versions) |
929 | 938 |
930 def getbundler(version, repo, bundlecaps=None): | 939 def getbundler(version, repo, bundlecaps=None, filematcher=None): |
931 assert version in supportedoutgoingversions(repo) | 940 assert version in supportedoutgoingversions(repo) |
932 return _packermap[version][0](repo, bundlecaps) | 941 |
942 if filematcher is None: | |
943 filematcher = matchmod.alwaysmatcher(repo.root, '') | |
944 | |
945 if version == '01' and not filematcher.always(): | |
946 raise error.ProgrammingError('version 01 changegroups do not support ' | |
947 'sparse file matchers') | |
948 | |
949 # Requested files could include files not in the local store. So | |
950 # filter those out. | |
951 filematcher = matchmod.intersectmatchers(repo.narrowmatch(), | |
952 filematcher) | |
953 | |
954 return _packermap[version][0](repo, filematcher=filematcher, | |
955 bundlecaps=bundlecaps) | |
933 | 956 |
934 def getunbundler(version, fh, alg, extras=None): | 957 def getunbundler(version, fh, alg, extras=None): |
935 return _packermap[version][1](fh, alg, extras=extras) | 958 return _packermap[version][1](fh, alg, extras=extras) |
936 | 959 |
937 def _changegroupinfo(repo, nodes, source): | 960 def _changegroupinfo(repo, nodes, source): |
948 fastpath=fastpath, bundlecaps=bundlecaps) | 971 fastpath=fastpath, bundlecaps=bundlecaps) |
949 return getunbundler(version, util.chunkbuffer(cgstream), None, | 972 return getunbundler(version, util.chunkbuffer(cgstream), None, |
950 {'clcount': len(outgoing.missing) }) | 973 {'clcount': len(outgoing.missing) }) |
951 | 974 |
952 def makestream(repo, outgoing, version, source, fastpath=False, | 975 def makestream(repo, outgoing, version, source, fastpath=False, |
953 bundlecaps=None): | 976 bundlecaps=None, filematcher=None): |
954 bundler = getbundler(version, repo, bundlecaps=bundlecaps) | 977 bundler = getbundler(version, repo, bundlecaps=bundlecaps, |
978 filematcher=filematcher) | |
955 | 979 |
956 repo = repo.unfiltered() | 980 repo = repo.unfiltered() |
957 commonrevs = outgoing.common | 981 commonrevs = outgoing.common |
958 csets = outgoing.missing | 982 csets = outgoing.missing |
959 heads = outgoing.missingheads | 983 heads = outgoing.missingheads |