Mercurial > public > mercurial-scm > hg-stable
diff mercurial/bundle2.py @ 28666:ae53ecc47414
bundle: move writebundle() from changegroup.py to bundle2.py (API)
writebundle() writes a bundle2 bundle or a plain changegroup1. Imagine
away the "2" in "bundle2.py" for a moment and this change should makes
sense. The bundle wraps the changegroup, so it makes sense that it
knows about it. Another sign that this is correct is that the delayed
import of bundle2 in changegroup goes away.
I'll leave it for another time to remove the "2" in "bundle2.py"
(alternatively, extract a new bundle.py from it).
author | Martin von Zweigbergk <martinvonz@google.com> |
---|---|
date | Mon, 28 Mar 2016 14:41:29 -0700 |
parents | 88609cfa3745 |
children | ca4896110011 |
line wrap: on
line diff
--- a/mercurial/bundle2.py Mon Mar 28 17:16:00 2016 -0500 +++ b/mercurial/bundle2.py Mon Mar 28 14:41:29 2016 -0700 @@ -474,6 +474,19 @@ chunks.append(ca) return '\n'.join(chunks) +bundletypes = { + "": ("", None), # only when using unbundle on ssh and old http servers + # since the unification ssh accepts a header but there + # is no capability signaling it. + "HG20": (), # special-cased below + "HG10UN": ("HG10UN", None), + "HG10BZ": ("HG10", 'BZ'), + "HG10GZ": ("HG10GZ", 'GZ'), +} + +# hgweb uses this list to communicate its preferred type +bundlepriority = ['HG10GZ', 'HG10BZ', 'HG10UN'] + class bundle20(object): """represent an outgoing bundle2 container @@ -1265,6 +1278,48 @@ obscaps = caps.get('obsmarkers', ()) return [int(c[1:]) for c in obscaps if c.startswith('V')] +def writebundle(ui, cg, filename, bundletype, vfs=None, compression=None): + """Write a bundle file and return its filename. + + Existing files will not be overwritten. + If no filename is specified, a temporary file is created. + bz2 compression can be turned off. + The bundle file will be deleted in case of errors. + """ + + if bundletype == "HG20": + bundle = bundle20(ui) + bundle.setcompression(compression) + part = bundle.newpart('changegroup', data=cg.getchunks()) + part.addparam('version', cg.version) + chunkiter = bundle.getchunks() + else: + # compression argument is only for the bundle2 case + assert compression is None + if cg.version != '01': + raise error.Abort(_('old bundle types only supports v1 ' + 'changegroups')) + header, comp = bundletypes[bundletype] + if comp not in util.compressors: + raise error.Abort(_('unknown stream compression type: %s') + % comp) + z = util.compressors[comp]() + subchunkiter = cg.getchunks() + def chunkiter(): + yield header + for chunk in subchunkiter: + yield z.compress(chunk) + yield z.flush() + chunkiter = chunkiter() + + # parse the changegroup data, otherwise we will block + # in case of sshrepo because we don't know the end of the stream + + # an empty chunkgroup is the end of the changegroup + # a changegroup has at least 2 chunkgroups (changelog and manifest). + # after that, an empty chunkgroup is the end of the changegroup + return changegroup.writechunks(ui, chunkiter, filename, vfs=vfs) + @parthandler('changegroup', ('version', 'nbchanges', 'treemanifest')) def handlechangegroup(op, inpart): """apply a changegroup part on the repo