##// END OF EJS Templates
stream-clone: avoid opening a revlog in case we do not need it...
Arseniy Alekseyev -
r51565:3b563954 default
parent child Browse files
Show More
@@ -290,6 +290,16 b' class revlog:'
290
290
291 _flagserrorclass = error.RevlogError
291 _flagserrorclass = error.RevlogError
292
292
293 @staticmethod
294 def is_inline_index(header_bytes):
295 header = INDEX_HEADER.unpack(header_bytes)[0]
296
297 _format_flags = header & ~0xFFFF
298 _format_version = header & 0xFFFF
299
300 features = FEATURES_BY_VERSION[_format_version]
301 return features[b'inline'](_format_flags)
302
293 def __init__(
303 def __init__(
294 self,
304 self,
295 opener,
305 opener,
@@ -16,6 +16,9 b' from .i18n import _'
16 from .pycompat import getattr
16 from .pycompat import getattr
17 from .thirdparty import attr
17 from .thirdparty import attr
18 from .node import hex
18 from .node import hex
19 from .revlogutils.constants import (
20 INDEX_HEADER,
21 )
19 from . import (
22 from . import (
20 changelog,
23 changelog,
21 error,
24 error,
@@ -23,6 +26,7 b' from . import ('
23 manifest,
26 manifest,
24 policy,
27 policy,
25 pycompat,
28 pycompat,
29 revlog as revlogmod,
26 util,
30 util,
27 vfs as vfsmod,
31 vfs as vfsmod,
28 )
32 )
@@ -619,44 +623,70 b' class RevlogStoreEntry(BaseStoreEntry):'
619 copies=None,
623 copies=None,
620 max_changeset=None,
624 max_changeset=None,
621 ):
625 ):
622 if repo is None or max_changeset is None:
626 if (
623 return super().get_streams(
627 repo is None
624 repo=repo,
628 or max_changeset is None
625 vfs=vfs,
626 copies=copies,
627 max_changeset=max_changeset,
628 )
629 if any(k.endswith(b'.idx') for k in self._details.keys()):
630 # This use revlog-v2, ignore for now
629 # This use revlog-v2, ignore for now
630 or any(k.endswith(b'.idx') for k in self._details.keys())
631 # This is not inline, no race expected
632 or b'.d' in self._details
633 ):
631 return super().get_streams(
634 return super().get_streams(
632 repo=repo,
635 repo=repo,
633 vfs=vfs,
636 vfs=vfs,
634 copies=copies,
637 copies=copies,
635 max_changeset=max_changeset,
638 max_changeset=max_changeset,
636 )
639 )
637 name_to_ext = {}
640
638 for ext in self._details.keys():
639 name_to_ext[self._path_prefix + ext] = ext
640 name_to_size = {}
641 name_to_size = {}
641 for f in self.files():
642 for f in self.files():
642 name_to_size[f.unencoded_path] = f.file_size(None)
643 name_to_size[f.unencoded_path] = f.file_size(None)
644
643 stream = [
645 stream = [
644 f.get_stream(vfs, copies)
646 f.get_stream(vfs, copies)
645 for f in self.files()
647 for f in self.files()
646 if name_to_ext[f.unencoded_path] not in (b'.d', b'.i')
648 if not f.unencoded_path.endswith(b'.i')
647 ]
649 ]
648
650
649 is_inline = b'.d' not in self._details
651 index_path = self._path_prefix + b'.i'
652
653 index_file = None
654 try:
655 index_file = vfs(index_path)
656 header = index_file.read(INDEX_HEADER.size)
657 if revlogmod.revlog.is_inline_index(header):
658 size = name_to_size[index_path]
650
659
660 # no split underneath, just return the stream
661 def get_stream():
662 fp = index_file
663 try:
664 fp.seek(0)
665 yield None
666 if size <= 65536:
667 yield fp.read(size)
668 else:
669 yield from util.filechunkiter(fp, limit=size)
670 finally:
671 fp.close()
672
673 s = get_stream()
674 next(s)
675 index_file = None
676 stream.append((index_path, s, size))
677 else:
651 rl = self.get_revlog_instance(repo).get_revlog()
678 rl = self.get_revlog_instance(repo).get_revlog()
652 rl_stream = rl.get_streams(max_changeset, force_inline=is_inline)
679 rl_stream = rl.get_streams(max_changeset, force_inline=True)
653
654 for name, s, size in rl_stream:
680 for name, s, size in rl_stream:
655 if name_to_size.get(name, 0) != size:
681 if name_to_size.get(name, 0) != size:
656 msg = _(b"expected %d bytes but %d provided for %s")
682 msg = _(b"expected %d bytes but %d provided for %s")
657 msg %= name_to_size.get(name, 0), size, name
683 msg %= name_to_size.get(name, 0), size, name
658 raise error.Abort(msg)
684 raise error.Abort(msg)
659 stream.extend(rl_stream)
685 stream.extend(rl_stream)
686 finally:
687 if index_file is not None:
688 index_file.close()
689
660 files = self.files()
690 files = self.files()
661 assert len(stream) == len(files), (
691 assert len(stream) == len(files), (
662 stream,
692 stream,
General Comments 0
You need to be logged in to leave comments. Login now