diff options
author | cinap_lenrek <cinap_lenrek@localhost> | 2011-05-03 11:25:13 +0000 |
---|---|---|
committer | cinap_lenrek <cinap_lenrek@localhost> | 2011-05-03 11:25:13 +0000 |
commit | 458120dd40db6b4df55a4e96b650e16798ef06a0 (patch) | |
tree | 8f82685be24fef97e715c6f5ca4c68d34d5074ee /sys/lib/python/mercurial/streamclone.py | |
parent | 3a742c699f6806c1145aea5149bf15de15a0afd7 (diff) |
add hg and python
Diffstat (limited to 'sys/lib/python/mercurial/streamclone.py')
-rw-r--r-- | sys/lib/python/mercurial/streamclone.py | 67 |
1 files changed, 67 insertions, 0 deletions
diff --git a/sys/lib/python/mercurial/streamclone.py b/sys/lib/python/mercurial/streamclone.py new file mode 100644 index 000000000..82cd2f730 --- /dev/null +++ b/sys/lib/python/mercurial/streamclone.py @@ -0,0 +1,67 @@ +# streamclone.py - streaming clone server support for mercurial +# +# Copyright 2006 Vadim Gelfer <vadim.gelfer@gmail.com> +# +# This software may be used and distributed according to the terms of the +# GNU General Public License version 2, incorporated herein by reference. + +import util, error +from i18n import _ + +from mercurial import store + +class StreamException(Exception): + def __init__(self, code): + Exception.__init__(self) + self.code = code + def __str__(self): + return '%i\n' % self.code + +# if server supports streaming clone, it advertises "stream" +# capability with value that is version+flags of repo it is serving. +# client only streams if it can read that repo format. + +# stream file format is simple. +# +# server writes out line that says how many files, how many total +# bytes. separator is ascii space, byte counts are strings. +# +# then for each file: +# +# server writes out line that says filename, how many bytes in +# file. separator is ascii nul, byte count is string. +# +# server writes out raw file data. + +def stream_out(repo, untrusted=False): + '''stream out all metadata files in repository. + writes to file-like object, must support write() and optional flush().''' + + if not repo.ui.configbool('server', 'uncompressed', untrusted=untrusted): + raise StreamException(1) + + entries = [] + total_bytes = 0 + try: + # get consistent snapshot of repo, lock during scan + lock = repo.lock() + try: + repo.ui.debug(_('scanning\n')) + for name, ename, size in repo.store.walk(): + # for backwards compat, name was partially encoded + entries.append((store.encodedir(name), size)) + total_bytes += size + finally: + lock.release() + except error.LockError: + raise StreamException(2) + + yield '0\n' + repo.ui.debug(_('%d files, %d bytes to transfer\n') % + (len(entries), total_bytes)) + yield '%d %d\n' % (len(entries), total_bytes) + for name, size in entries: + repo.ui.debug(_('sending %s (%d bytes)\n') % (name, size)) + yield '%s\0%d\n' % (name, size) + for chunk in util.filechunkiter(repo.sopener(name), limit=size): + yield chunk |