def capable(self, capability): if capability == b'bundle2': return quote_from_bytes(HgRepoHelper.capable(b'bundle2') or b'').encode('ascii') if capability in (b'clonebundles', b'cinnabarclone'): return HgRepoHelper.capable(capability) is not None return capability in (b'getbundle', b'unbundle', b'lookup')
def get_repo(remote): if not changegroup or experiment('wire'): if not changegroup: logging.warning('Mercurial libraries not found. Falling back to ' 'native access.') logging.warning( 'Native access to mercurial repositories is experimental!') stream = HgRepoHelper.connect(remote.url) if stream: return bundlerepo(remote.url, stream) return HelperRepo(remote.url) if remote.parsed_url.scheme == 'file': path = remote.parsed_url.path if sys.platform == 'win32': # TODO: This probably needs more thought. path = path.lstrip('/') if not os.path.isdir(path): return bundlerepo(path) ui = get_ui() if changegroup and remote.parsed_url.scheme == 'file': repo = localpeer(ui, path) else: try: repo = hg.peer(ui, {}, remote.url) except (error.RepoError, urllib2.HTTPError, IOError): return bundlerepo(remote.url, url.open(ui, remote.url)) assert repo.capable('getbundle') return repo
def get_repo(remote): if not changegroup or experiment('wire'): if not changegroup and not check_enabled('no-mercurial'): logging.warning('Mercurial libraries not found. Falling back to ' 'native access.') logging.warning( 'Native access to mercurial repositories is experimental!') stream = HgRepoHelper.connect(remote.url) if stream: return bundlerepo(remote.url, stream) return HelperRepo(remote.url) if remote.parsed_url.scheme == 'file': # Make file://c:/... paths work by taking the netloc path = remote.parsed_url.netloc + remote.parsed_url.path if sys.platform == 'win32': # TODO: This probably needs more thought. path = path.lstrip('/') if not os.path.isdir(path): return bundlerepo(path) ui = get_ui() if changegroup and remote.parsed_url.scheme == 'file': repo = localpeer(ui, path) else: try: repo = hg.peer(ui, {}, remote.url) except (error.RepoError, urllib2.HTTPError, IOError): return bundlerepo(remote.url, HTTPReader(remote.url)) assert repo.capable('getbundle') return repo
def _get_repo(remote): if not changegroup or experiment('wire'): if not changegroup and not check_enabled('no-mercurial'): logging.warning('Mercurial libraries not found. Falling back to ' 'experimental native access.') stream = HgRepoHelper.connect(remote.url) if stream: return bundlerepo(remote.url, stream) return HelperRepo(remote.url) if remote.parsed_url.scheme == b'file': # Make file://c:/... paths work by taking the netloc path = remote.parsed_url.netloc + remote.parsed_url.path if sys.platform == 'win32': # TODO: This probably needs more thought. path = path.lstrip(b'/') if not os.path.isdir(path): return bundlerepo(path) ui = get_ui() if changegroup and remote.parsed_url.scheme == b'file': repo = localpeer(ui, path) else: try: repo = hg.peer(ui, {}, remote.url) except (error.RepoError, HTTPError, IOError): if remote.parsed_url.scheme in ('http', 'https'): return bundlerepo(remote.url, HTTPReader(remote.url)) raise assert repo.capable(b'getbundle') return repo
def get_clonebundle_url(repo): bundles = repo._call(b'clonebundles') supported_bundles = (b'v1', b'v2') supported_compressions = tuple( k for k, v in ( (b'none', b'UN'), (b'gzip', b'GZ'), (b'bzip2', b'BZ'), (b'zstd', b'ZS'), ) if HgRepoHelper.supports((b'compression', v)) ) has_sni = getattr(ssl, 'HAS_SNI', False) logger = logging.getLogger('clonebundle') for line in bundles.splitlines(): attrs = line.split() if not attrs: continue url = attrs.pop(0) logger.debug(url) attrs = { unquote_to_bytes(k): unquote_to_bytes(v) for k, _, v in (a.partition(b'=') for a in attrs) } logger.debug(attrs) if b'REQUIRESNI' in attrs and not has_sni: logger.debug('Skip because of REQUIRESNI, but SNI unsupported') continue spec = attrs.get(b'BUNDLESPEC') if not spec: logger.debug('Skip because missing BUNDLESPEC') continue typ, _, params = spec.partition(b';') compression, _, version = typ.partition(b'-') if compression not in supported_compressions: logger.debug('Skip because unsupported compression (%s)', compression) continue if version not in supported_bundles: logger.debug('Skip because unsupported bundle type (%s)', version) continue params_dict = {} for p in params.split(b':'): k, _, v = p.partition(b'=') params_dict[k] = v if 'stream' in params_dict: logger.debug('Skip because stream bundles are not supported') continue return url
def init_state(self): state = HgRepoHelper.state() self._branchmap = { urllib.unquote(branch): [unhexlify(h) for h in heads.split(' ')] for line in state['branchmap'].splitlines() for branch, heads in (line.split(' ', 1), ) } self._heads = [unhexlify(h) for h in state['heads'][:-1].split(' ')] self._bookmarks = self._decode_keys(state['bookmarks'])
def init_state(self): state = HgRepoHelper.state() self._branchmap = { urllib.unquote(branch): [unhexlify(h) for h in heads.split(' ')] for line in state['branchmap'].splitlines() for branch, heads in (line.split(' ', 1),) } self._heads = [unhexlify(h) for h in state['heads'][:-1].split(' ')] self._bookmarks = self._decode_keys(state['bookmarks'])
def __init__(self, url): self._url = url connect_result = HgRepoHelper.connect(url) self._branchmap = { urllib.unquote(branch): [unhexlify(h) for h in heads.split(' ')] for line in connect_result['branchmap'].splitlines() for branch, heads in (line.split(' ', 1),) } self._heads = [unhexlify(h) for h in connect_result['heads'][:-1].split(' ')] self._bookmarks = self._decode_keys(connect_result['bookmarks'])
def getbundle(self, name, heads, common, *args, **kwargs): data = HgRepoHelper.getbundle((hexlify(h) for h in heads), (hexlify(c) for c in common), ','.join(kwargs.get('bundlecaps', ()))) header = readexactly(data, 4) if header == 'HG20': return unbundle20(self.ui, data) class Reader(object): def __init__(self, header, data): self.header = header self.data = data def read(self, length): result = self.header[:length] self.header = self.header[length:] if length > len(result): result += self.data.read(length - len(result)) return result return Reader(header, data)
def getbundle(self, name, heads, common, *args, **kwargs): data = HgRepoHelper.getbundle((hexlify(h) for h in heads), (hexlify(c) for c in common), ','.join(kwargs.get('bundlecaps', ()))) header = readexactly(data, 4) if header == 'HG20': return unbundle20(get_ui(), data) class Reader(object): def __init__(self, header, data): self.header = header self.data = data def read(self, length): result = self.header[:length] self.header = self.header[length:] if length > len(result): result += self.data.read(length - len(result)) return result return Reader(header, data)
def _call(self, command, *args): if command == 'clonebundles': return HgRepoHelper.clonebundles() raise NotImplementedError()
def known(self, nodes): result = HgRepoHelper.known(hexlify(n) for n in nodes) return [b == b'1'[0] for b in result]
def _call(self, command, *args): if command == 'clonebundles': return HgRepoHelper.clonebundles() if command == 'cinnabarclone': return HgRepoHelper.cinnabarclone() raise NotImplementedError()
def lookup(self, key): data = HgRepoHelper.lookup(key) if data: return unhexlify(data) raise Exception('Unknown revision %s' % key)
def get_clonebundle_url(repo): bundles = repo._call('clonebundles') try: if check_enabled('no-mercurial'): raise ImportError('Do not use mercurial') from mercurial.exchange import ( parseclonebundlesmanifest, filterclonebundleentries, ) except ImportError: parseclonebundlesmanifest = False if parseclonebundlesmanifest: class dummy(object): pass fakerepo = dummy() fakerepo.requirements = set() fakerepo.supportedformats = set() fakerepo.ui = repo.ui entries = parseclonebundlesmanifest(fakerepo, bundles) if not entries: return None entries = filterclonebundleentries(fakerepo, entries) if not entries: return None return entries[0].get('URL') supported_bundles = ('v1', 'v2') supported_compressions = tuple( k for k, v in ( ('none', 'UN'), ('gzip', 'GZ'), ('bzip2', 'BZ'), ('zstd', 'ZS'), ) if HgRepoHelper.supports(('compression', v)) ) has_sni = getattr(ssl, 'HAS_SNI', False) logger = logging.getLogger('clonebundle') for line in bundles.splitlines(): attrs = line.split() if not attrs: continue url = attrs.pop(0) logger.debug(url) attrs = { urllib.unquote(k): urllib.unquote(v) for k, _, v in (a.partition('=') for a in attrs) } logger.debug(attrs) if 'REQUIRESNI' in attrs and not has_sni: logger.debug('Skip because of REQUIRESNI, but SNI unsupported') continue spec = attrs.get('BUNDLESPEC') if not spec: logger.debug('Skip because missing BUNDLESPEC') continue typ, _, params = spec.partition(';') compression, _, version = typ.partition('-') if compression not in supported_compressions: logger.debug('Skip because unsupported compression (%s)', compression) continue if version not in supported_bundles: logger.debug('Skip because unsupported bundle type (%s)', version) continue return url
def known(self, nodes): result = HgRepoHelper.known(hexlify(n) for n in nodes) return [bool(int(b)) for b in result]
def capable(self, capability): if capability == 'bundle2': return urllib.quote(HgRepoHelper.capable('bundle2')) return capability in ('getbundle', 'unbundle', 'lookup')
def __init__(self, url): self._url = url HgRepoHelper.connect(url)
def unbundle(self, cg, heads, *args, **kwargs): data = HgRepoHelper.unbundle(cg, (hexlify(h) if h != 'force' else h for h in heads)) if isinstance(data, str) and data.startswith('HG20'): data = unbundle20(get_ui(), StringIO(data[4:])) return data
def pushkey(self, namespace, key, old, new): return HgRepoHelper.pushkey(namespace, key, old, new)
def capable(self, capability): if capability == 'bundle2': return urllib.quote(HgRepoHelper.capable('bundle2') or '') if capability == 'clonebundles': return HgRepoHelper.capable(capability) is not None return capability in ('getbundle', 'unbundle', 'lookup')
def listkeys(self, namespace): if namespace == 'bookmarks': if self._bookmarks is None: self.init_state() return self._bookmarks return self._decode_keys(HgRepoHelper.listkeys(namespace))
def capable(self, capability): if capability == 'bundle2': return urllib.quote(HgRepoHelper.capable('bundle2')) return capability in ('getbundle', 'unbundle')
def listkeys(self, namespace): if namespace == 'bookmarks': return self._bookmarks return self._decode_keys(HgRepoHelper.listkeys(namespace))
def unbundle(self, cg, heads, *args, **kwargs): data = HgRepoHelper.unbundle(cg, (hexlify(h) if h != 'force' else h for h in heads)) if isinstance(data, str) and data.startswith('HG20'): data = unbundle20(self.ui, StringIO(data[4:])) return data
def get_clonebundle_url(repo): bundles = repo._call(b'clonebundles') try: if check_enabled('no-mercurial'): raise ImportError('Do not use mercurial') from mercurial.exchange import ( parseclonebundlesmanifest, filterclonebundleentries, ) except ImportError: parseclonebundlesmanifest = False if parseclonebundlesmanifest: class dummy(object): pass fakerepo = dummy() fakerepo.requirements = set() fakerepo.supportedformats = set() fakerepo.ui = repo.ui entries = parseclonebundlesmanifest(fakerepo, bundles) if not entries: return None entries = filterclonebundleentries(fakerepo, entries) if not entries: return None return entries[0].get(b'URL') supported_bundles = (b'v1', b'v2') supported_compressions = tuple(k for k, v in ( (b'none', b'UN'), (b'gzip', b'GZ'), (b'bzip2', b'BZ'), (b'zstd', b'ZS'), ) if HgRepoHelper.supports((b'compression', v))) has_sni = getattr(ssl, 'HAS_SNI', False) logger = logging.getLogger('clonebundle') for line in bundles.splitlines(): attrs = line.split() if not attrs: continue url = attrs.pop(0) logger.debug(url) attrs = { unquote_to_bytes(k): unquote_to_bytes(v) for k, _, v in (a.partition(b'=') for a in attrs) } logger.debug(attrs) if b'REQUIRESNI' in attrs and not has_sni: logger.debug('Skip because of REQUIRESNI, but SNI unsupported') continue spec = attrs.get(b'BUNDLESPEC') if not spec: logger.debug('Skip because missing BUNDLESPEC') continue typ, _, params = spec.partition(b';') compression, _, version = typ.partition(b'-') if compression not in supported_compressions: logger.debug('Skip because unsupported compression (%s)', compression) continue if version not in supported_bundles: logger.debug('Skip because unsupported bundle type (%s)', version) continue params_dict = {} for p in params.split(b':'): k, _, v = p.partition(b'=') params_dict[k] = v if 'stream' in params_dict: logger.debug('Skip because stream bundles are not supported') continue return url
def listkeys(self, namespace): if namespace == 'bookmarks': if not hasattr(self, '_bookmarks'): self.init_state() return self._bookmarks return self._decode_keys(HgRepoHelper.listkeys(namespace))
def capable(self, capability): if capability == 'bundle2': return urllib.quote(HgRepoHelper.capable('bundle2') or '') if capability in ('clonebundles', 'cinnabarclone'): return HgRepoHelper.capable(capability) is not None return capability in ('getbundle', 'unbundle', 'lookup')