def unbundle(repo, proto, heads): their_heads = decodelist(heads) try: proto.redirect() exchange.check_heads(repo, their_heads, 'preparing changes') # write bundle data to temporary file because it can be big fd, tempname = tempfile.mkstemp(prefix='hg-unbundle-') fp = os.fdopen(fd, 'wb+') r = 0 try: proto.getfile(fp) fp.seek(0) gen = exchange.readbundle(repo.ui, fp, None) r = exchange.unbundle(repo, gen, their_heads, 'serve', proto._client()) if util.safehasattr(r, 'addpart'): # The return looks streameable, we are in the bundle2 case and # should return a stream. return streamres(r.getchunks()) return pushres(r) finally: fp.close() os.unlink(tempname) except bundle2.UnknownPartError, exc: bundler = bundle2.bundle20(repo.ui) part = bundle2.bundlepart('B2X:ERROR:UNKNOWNPART', [('parttype', str(exc))]) bundler.addpart(part) return streamres(bundler.getchunks())
def unbundle(repo, proto, heads): their_heads = decodelist(heads) try: proto.redirect() exchange.check_heads(repo, their_heads, 'preparing changes') # write bundle data to temporary file because it can be big fd, tempname = tempfile.mkstemp(prefix='hg-unbundle-') fp = os.fdopen(fd, 'wb+') r = 0 try: proto.getfile(fp) fp.seek(0) gen = exchange.readbundle(repo.ui, fp, None) r = exchange.unbundle(repo, gen, their_heads, 'serve', proto._client()) if util.safehasattr(r, 'addpart'): # The return looks streamable, we are in the bundle2 case and # should return a stream. return streamres(r.getchunks()) return pushres(r) finally: fp.close() os.unlink(tempname) except error.BundleValueError, exc: bundler = bundle2.bundle20(repo.ui) errpart = bundler.newpart('b2x:error:unsupportedcontent') if exc.parttype is not None: errpart.addparam('parttype', exc.parttype) if exc.params: errpart.addparam('params', '\0'.join(exc.params)) return streamres(bundler.getchunks())
def unbundle(repo, proto, heads): their_heads = decodelist(heads) try: proto.redirect() exchange.check_heads(repo, their_heads, "preparing changes") # write bundle data to temporary file because it can be big fd, tempname = tempfile.mkstemp(prefix="hg-unbundle-") fp = os.fdopen(fd, "wb+") r = 0 try: proto.getfile(fp) fp.seek(0) gen = exchange.readbundle(repo.ui, fp, None) r = exchange.unbundle(repo, gen, their_heads, "serve", proto._client()) if util.safehasattr(r, "addpart"): # The return looks streameable, we are in the bundle2 case and # should return a stream. return streamres(r.getchunks()) return pushres(r) finally: fp.close() os.unlink(tempname) except error.BundleValueError, exc: bundler = bundle2.bundle20(repo.ui) errpart = bundler.newpart("B2X:ERROR:UNSUPPORTEDCONTENT") if exc.parttype is not None: errpart.addparam("parttype", exc.parttype) if exc.params: errpart.addparam("params", "\0".join(exc.params)) return streamres(bundler.getchunks())
def __init__(self, ui, path, bundlename): self._tempparent = None try: localrepo.localrepository.__init__(self, ui, path) except error.RepoError: self._tempparent = tempfile.mkdtemp() localrepo.instance(ui, self._tempparent, 1) localrepo.localrepository.__init__(self, ui, self._tempparent) self.ui.setconfig('phases', 'publish', False, 'bundlerepo') if path: self._url = 'bundle:' + util.expandpath(path) + '+' + bundlename else: self._url = 'bundle:' + bundlename self.tempfile = None f = util.posixfile(bundlename, "rb") self.bundle = exchange.readbundle(ui, f, bundlename) if self.bundle.compressed(): fdtemp, temp = self.vfs.mkstemp(prefix="hg-bundle-", suffix=".hg10un") self.tempfile = temp fptemp = os.fdopen(fdtemp, 'wb') try: fptemp.write("HG10UN") while True: chunk = self.bundle.read(2**18) if not chunk: break fptemp.write(chunk) finally: fptemp.close() f = self.vfs.open(self.tempfile, mode="rb") self.bundle = exchange.readbundle(ui, f, bundlename, self.vfs) # dict with the mapping 'filename' -> position in the bundle self.bundlefilespos = {} self.firstnewrev = self.changelog.repotiprev + 1 phases.retractboundary(self, None, phases.draft, [ctx.node() for ctx in self[self.firstnewrev:]])
def unbundle(repo, proto, heads): their_heads = decodelist(heads) try: proto.redirect() exchange.check_heads(repo, their_heads, 'preparing changes') # write bundle data to temporary file because it can be big fd, tempname = tempfile.mkstemp(prefix='hg-unbundle-') fp = os.fdopen(fd, 'wb+') r = 0 try: proto.getfile(fp) fp.seek(0) gen = exchange.readbundle(repo.ui, fp, None) r = exchange.unbundle(repo, gen, their_heads, 'serve', proto._client()) if util.safehasattr(r, 'addpart'): # The return looks streamable, we are in the bundle2 case and # should return a stream. return streamres(r.getchunks()) return pushres(r) finally: fp.close() os.unlink(tempname) except (error.BundleValueError, util.Abort, error.PushRaced), exc: # handle non-bundle2 case first if not getattr(exc, 'duringunbundle2', False): try: raise except util.Abort: # The old code we moved used sys.stderr directly. # We did not change it to minimise code change. # This need to be moved to something proper. # Feel free to do it. sys.stderr.write("abort: %s\n" % exc) return pushres(0) except error.PushRaced: return pusherr(str(exc)) bundler = bundle2.bundle20(repo.ui) for out in getattr(exc, '_bundle2salvagedoutput', ()): bundler.addpart(out) try: raise except error.BundleValueError, exc: errpart = bundler.newpart('error:unsupportedcontent') if exc.parttype is not None: errpart.addparam('parttype', exc.parttype) if exc.params: errpart.addparam('params', '\0'.join(exc.params))
def __init__(self, ui, path, bundlename): self._tempparent = None try: localrepo.localrepository.__init__(self, ui, path) except error.RepoError: self._tempparent = tempfile.mkdtemp() localrepo.instance(ui, self._tempparent, 1) localrepo.localrepository.__init__(self, ui, self._tempparent) self.ui.setconfig("phases", "publish", False, "bundlerepo") if path: self._url = "bundle:" + util.expandpath(path) + "+" + bundlename else: self._url = "bundle:" + bundlename self.tempfile = None f = util.posixfile(bundlename, "rb") self.bundle = exchange.readbundle(ui, f, bundlename) if self.bundle.compressed(): fdtemp, temp = self.vfs.mkstemp(prefix="hg-bundle-", suffix=".hg10un") self.tempfile = temp fptemp = os.fdopen(fdtemp, "wb") try: fptemp.write("HG10UN") while True: chunk = self.bundle.read(2 ** 18) if not chunk: break fptemp.write(chunk) finally: fptemp.close() f = self.vfs.open(self.tempfile, mode="rb") self.bundle = exchange.readbundle(ui, f, bundlename, self.vfs) # dict with the mapping 'filename' -> position in the bundle self.bundlefilespos = {}
def __init__(self, ui, path, bundlename): self._tempparent = None try: localrepo.localrepository.__init__(self, ui, path) except error.RepoError: self._tempparent = tempfile.mkdtemp() localrepo.instance(ui, self._tempparent, 1) localrepo.localrepository.__init__(self, ui, self._tempparent) self.ui.setconfig('phases', 'publish', False, 'bundlerepo') if path: self._url = 'bundle:' + util.expandpath(path) + '+' + bundlename else: self._url = 'bundle:' + bundlename self.tempfile = None f = util.posixfile(bundlename, "rb") self.bundlefile = self.bundle = exchange.readbundle(ui, f, bundlename) if self.bundle.compressed(): fdtemp, temp = self.vfs.mkstemp(prefix="hg-bundle-", suffix=".hg10un") self.tempfile = temp fptemp = os.fdopen(fdtemp, 'wb') try: fptemp.write("HG10UN") while True: chunk = self.bundle.read(2**18) if not chunk: break fptemp.write(chunk) finally: fptemp.close() f = self.vfs.open(self.tempfile, mode="rb") self.bundlefile = self.bundle = exchange.readbundle( ui, f, bundlename, self.vfs) if isinstance(self.bundle, bundle2.unbundle20): cgparts = [ part for part in self.bundle.iterparts() if (part.type == 'b2x:changegroup') and ( part.params.get('version', '01') in changegroup.packermap) ] if not cgparts: raise util.Abort('No changegroups found') version = cgparts[0].params.get('version', '01') cgparts = [ p for p in cgparts if p.params.get('version', '01') == version ] if len(cgparts) > 1: raise NotImplementedError( "Can't process multiple changegroups") part = cgparts[0] part.seek(0) self.bundle = changegroup.packermap[version][1](part, 'UN') # dict with the mapping 'filename' -> position in the bundle self.bundlefilespos = {} self.firstnewrev = self.changelog.repotiprev + 1 phases.retractboundary(self, None, phases.draft, [ctx.node() for ctx in self[self.firstnewrev:]])
def handleremotechangegroup(op, inpart): """apply a bundle10 on the repo, given an url and validation information All the information about the remote bundle to import are given as parameters. The parameters include: - url: the url to the bundle10. - size: the bundle10 file size. It is used to validate what was retrieved by the client matches the server knowledge about the bundle. - digests: a space separated list of the digest types provided as parameters. - digest:<digest-type>: the hexadecimal representation of the digest with that name. Like the size, it is used to validate what was retrieved by the client matches what the server knows about the bundle. When multiple digest types are given, all of them are checked. """ try: raw_url = inpart.params['url'] except KeyError: raise util.Abort(_('remote-changegroup: missing "%s" param') % 'url') parsed_url = util.url(raw_url) if parsed_url.scheme not in capabilities['b2x:remote-changegroup']: raise util.Abort( _('remote-changegroup does not support %s urls') % parsed_url.scheme) try: size = int(inpart.params['size']) except ValueError: raise util.Abort( _('remote-changegroup: invalid value for param "%s"') % 'size') except KeyError: raise util.Abort(_('remote-changegroup: missing "%s" param') % 'size') digests = {} for typ in inpart.params.get('digests', '').split(): param = 'digest:%s' % typ try: value = inpart.params[param] except KeyError: raise util.Abort( _('remote-changegroup: missing "%s" param') % param) digests[typ] = value real_part = util.digestchecker(url.open(op.ui, raw_url), size, digests) # Make sure we trigger a transaction creation # # The addchangegroup function will get a transaction object by itself, but # we need to make sure we trigger the creation of a transaction object used # for the whole processing scope. op.gettransaction() import exchange cg = exchange.readbundle(op.repo.ui, real_part, raw_url) if not isinstance(cg, changegroup.cg1unpacker): raise util.Abort( _('%s: not a bundle version 1.0') % util.hidepassword(raw_url)) ret = changegroup.addchangegroup(op.repo, cg, 'bundle2', 'bundle2') op.records.add('changegroup', {'return': ret}) if op.reply is not None: # This is definitly not the final form of this # return. But one need to start somewhere. part = op.reply.newpart('b2x:reply:changegroup') part.addparam('in-reply-to', str(inpart.id), mandatory=False) part.addparam('return', '%i' % ret, mandatory=False) try: real_part.validate() except util.Abort, e: raise util.Abort( _('bundle at %s is corrupted:\n%s') % (util.hidepassword(raw_url), str(e)))
def handleremotechangegroup(op, inpart): """apply a bundle10 on the repo, given an url and validation information All the information about the remote bundle to import are given as parameters. The parameters include: - url: the url to the bundle10. - size: the bundle10 file size. It is used to validate what was retrieved by the client matches the server knowledge about the bundle. - digests: a space separated list of the digest types provided as parameters. - digest:<digest-type>: the hexadecimal representation of the digest with that name. Like the size, it is used to validate what was retrieved by the client matches what the server knows about the bundle. When multiple digest types are given, all of them are checked. """ try: raw_url = inpart.params['url'] except KeyError: raise util.Abort(_('remote-changegroup: missing "%s" param') % 'url') parsed_url = util.url(raw_url) if parsed_url.scheme not in capabilities['b2x:remote-changegroup']: raise util.Abort(_('remote-changegroup does not support %s urls') % parsed_url.scheme) try: size = int(inpart.params['size']) except ValueError: raise util.Abort(_('remote-changegroup: invalid value for param "%s"') % 'size') except KeyError: raise util.Abort(_('remote-changegroup: missing "%s" param') % 'size') digests = {} for typ in inpart.params.get('digests', '').split(): param = 'digest:%s' % typ try: value = inpart.params[param] except KeyError: raise util.Abort(_('remote-changegroup: missing "%s" param') % param) digests[typ] = value real_part = util.digestchecker(url.open(op.ui, raw_url), size, digests) # Make sure we trigger a transaction creation # # The addchangegroup function will get a transaction object by itself, but # we need to make sure we trigger the creation of a transaction object used # for the whole processing scope. op.gettransaction() import exchange cg = exchange.readbundle(op.repo.ui, real_part, raw_url) if not isinstance(cg, changegroup.cg1unpacker): raise util.Abort(_('%s: not a bundle version 1.0') % util.hidepassword(raw_url)) ret = changegroup.addchangegroup(op.repo, cg, 'bundle2', 'bundle2') op.records.add('changegroup', {'return': ret}) if op.reply is not None: # This is definitly not the final form of this # return. But one need to start somewhere. part = op.reply.newpart('b2x:reply:changegroup') part.addparam('in-reply-to', str(inpart.id), mandatory=False) part.addparam('return', '%i' % ret, mandatory=False) try: real_part.validate() except util.Abort, e: raise util.Abort(_('bundle at %s is corrupted:\n%s') % (util.hidepassword(raw_url), str(e)))
def __init__(self, ui, path, bundlename): self._tempparent = None try: localrepo.localrepository.__init__(self, ui, path) except error.RepoError: self._tempparent = tempfile.mkdtemp() localrepo.instance(ui, self._tempparent, 1) localrepo.localrepository.__init__(self, ui, self._tempparent) self.ui.setconfig('phases', 'publish', False, 'bundlerepo') if path: self._url = 'bundle:' + util.expandpath(path) + '+' + bundlename else: self._url = 'bundle:' + bundlename self.tempfile = None f = util.posixfile(bundlename, "rb") self.bundlefile = self.bundle = exchange.readbundle(ui, f, bundlename) if self.bundle.compressed(): fdtemp, temp = self.vfs.mkstemp(prefix="hg-bundle-", suffix=".hg10un") self.tempfile = temp fptemp = os.fdopen(fdtemp, 'wb') try: fptemp.write("HG10UN") while True: chunk = self.bundle.read(2**18) if not chunk: break fptemp.write(chunk) finally: fptemp.close() f = self.vfs.open(self.tempfile, mode="rb") self.bundlefile = self.bundle = exchange.readbundle(ui, f, bundlename, self.vfs) if isinstance(self.bundle, bundle2.unbundle20): cgparts = [part for part in self.bundle.iterparts() if (part.type == 'changegroup') and (part.params.get('version', '01') in changegroup.packermap)] if not cgparts: raise util.Abort('No changegroups found') version = cgparts[0].params.get('version', '01') cgparts = [p for p in cgparts if p.params.get('version', '01') == version] if len(cgparts) > 1: raise NotImplementedError("Can't process multiple changegroups") part = cgparts[0] part.seek(0) self.bundle = changegroup.packermap[version][1](part, 'UN') # dict with the mapping 'filename' -> position in the bundle self.bundlefilespos = {} self.firstnewrev = self.changelog.repotiprev + 1 phases.retractboundary(self, None, phases.draft, [ctx.node() for ctx in self[self.firstnewrev:]])
def unbundle(repo, proto, heads): their_heads = decodelist(heads) try: proto.redirect() exchange.check_heads(repo, their_heads, 'preparing changes') # write bundle data to temporary file because it can be big fd, tempname = tempfile.mkstemp(prefix='hg-unbundle-') fp = os.fdopen(fd, 'wb+') r = 0 try: proto.getfile(fp) fp.seek(0) gen = exchange.readbundle(repo.ui, fp, None) r = exchange.unbundle(repo, gen, their_heads, 'serve', proto._client()) if util.safehasattr(r, 'addpart'): # The return looks streamable, we are in the bundle2 case and # should return a stream. return streamres(r.getchunks()) return pushres(r) finally: fp.close() os.unlink(tempname) except (error.BundleValueError, util.Abort, error.PushRaced) as exc: # handle non-bundle2 case first if not getattr(exc, 'duringunbundle2', False): try: raise except util.Abort: # The old code we moved used sys.stderr directly. # We did not change it to minimise code change. # This need to be moved to something proper. # Feel free to do it. sys.stderr.write("abort: %s\n" % exc) return pushres(0) except error.PushRaced: return pusherr(str(exc)) bundler = bundle2.bundle20(repo.ui) for out in getattr(exc, '_bundle2salvagedoutput', ()): bundler.addpart(out) try: try: raise except error.PushkeyFailed as exc: # check client caps remotecaps = getattr(exc, '_replycaps', None) if (remotecaps is not None and 'pushkey' not in remotecaps.get('error', ())): # no support remote side, fallback to Abort handler. raise part = bundler.newpart('error:pushkey') part.addparam('in-reply-to', exc.partid) if exc.namespace is not None: part.addparam('namespace', exc.namespace, mandatory=False) if exc.key is not None: part.addparam('key', exc.key, mandatory=False) if exc.new is not None: part.addparam('new', exc.new, mandatory=False) if exc.old is not None: part.addparam('old', exc.old, mandatory=False) if exc.ret is not None: part.addparam('ret', exc.ret, mandatory=False) except error.BundleValueError as exc: errpart = bundler.newpart('error:unsupportedcontent') if exc.parttype is not None: errpart.addparam('parttype', exc.parttype) if exc.params: errpart.addparam('params', '\0'.join(exc.params)) except util.Abort as exc: manargs = [('message', str(exc))] advargs = [] if exc.hint is not None: advargs.append(('hint', exc.hint)) bundler.addpart(bundle2.bundlepart('error:abort', manargs, advargs)) except error.PushRaced as exc: bundler.newpart('error:pushraced', [('message', str(exc))]) return streamres(bundler.getchunks())
def unbundle(repo, proto, heads): their_heads = decodelist(heads) try: proto.redirect() exchange.check_heads(repo, their_heads, "preparing changes") # write bundle data to temporary file because it can be big fd, tempname = tempfile.mkstemp(prefix="hg-unbundle-") fp = os.fdopen(fd, "wb+") r = 0 try: proto.getfile(fp) fp.seek(0) gen = exchange.readbundle(repo.ui, fp, None) r = exchange.unbundle(repo, gen, their_heads, "serve", proto._client()) if util.safehasattr(r, "addpart"): # The return looks streamable, we are in the bundle2 case and # should return a stream. return streamres(r.getchunks()) return pushres(r) finally: fp.close() os.unlink(tempname) except (error.BundleValueError, util.Abort, error.PushRaced) as exc: # handle non-bundle2 case first if not getattr(exc, "duringunbundle2", False): try: raise except util.Abort: # The old code we moved used sys.stderr directly. # We did not change it to minimise code change. # This need to be moved to something proper. # Feel free to do it. sys.stderr.write("abort: %s\n" % exc) return pushres(0) except error.PushRaced: return pusherr(str(exc)) bundler = bundle2.bundle20(repo.ui) for out in getattr(exc, "_bundle2salvagedoutput", ()): bundler.addpart(out) try: try: raise except error.PushkeyFailed as exc: # check client caps remotecaps = getattr(exc, "_replycaps", None) if remotecaps is not None and "pushkey" not in remotecaps.get("error", ()): # no support remote side, fallback to Abort handler. raise part = bundler.newpart("error:pushkey") part.addparam("in-reply-to", exc.partid) if exc.namespace is not None: part.addparam("namespace", exc.namespace, mandatory=False) if exc.key is not None: part.addparam("key", exc.key, mandatory=False) if exc.new is not None: part.addparam("new", exc.new, mandatory=False) if exc.old is not None: part.addparam("old", exc.old, mandatory=False) if exc.ret is not None: part.addparam("ret", exc.ret, mandatory=False) except error.BundleValueError as exc: errpart = bundler.newpart("error:unsupportedcontent") if exc.parttype is not None: errpart.addparam("parttype", exc.parttype) if exc.params: errpart.addparam("params", "\0".join(exc.params)) except util.Abort as exc: manargs = [("message", str(exc))] advargs = [] if exc.hint is not None: advargs.append(("hint", exc.hint)) bundler.addpart(bundle2.bundlepart("error:abort", manargs, advargs)) except error.PushRaced as exc: bundler.newpart("error:pushraced", [("message", str(exc))]) return streamres(bundler.getchunks())