/brz/remove-bazaar

To get this branch, use:
bzr branch http://gegoxaren.bato24.eu/bzr/brz/remove-bazaar

« back to all changes in this revision

Viewing changes to bzrlib/transport/__init__.py

  • Committer: Robert Collins
  • Date: 2007-08-26 22:10:51 UTC
  • mto: (2592.3.117 repository)
  • mto: This revision was merged to the branch mainline in revision 2885.
  • Revision ID: robertc@robertcollins.net-20070826221051-46uq33p3oqkscdd0
* New parameter on ``bzrlib.transport.Transport.readv``
  ``adjust_for_latency`` which changes readv from returning strictly the
  requested data to inserted return larger ranges and in forward read order
  to reduce the effect of network latency. (Robert Collins)

Show diffs side-by-side

added added

removed removed

Lines of Context:
635
635
        """
636
636
        raise errors.NoSmartMedium(self)
637
637
 
638
 
    def readv(self, relpath, offsets):
 
638
    def readv(self, relpath, offsets, adjust_for_latency=False):
 
639
        """Get parts of the file at the given relative path.
 
640
 
 
641
        :param relpath: The path to read data from.
 
642
        :param offsets: A list of (offset, size) tuples.
 
643
        :param adjust_for_latency: Adjust the requested offsets to accomdate
 
644
            transport latency. This may re-order the offsets, expand them to
 
645
            grab adjacent data when there is likely a high cost to requesting
 
646
            data relative to delivering it.
 
647
        :return: A list or generator of (offset, data) tuples
 
648
        """
 
649
        if adjust_for_latency:
 
650
            offsets = sorted(offsets)
 
651
            # short circuit empty requests
 
652
            if len(offsets) == 0:
 
653
                def empty_yielder():
 
654
                    # Quick thunk to stop this function becoming a generator
 
655
                    # itself, rather we return a generator that has nothing to
 
656
                    # yield.
 
657
                    if False:
 
658
                        yield None
 
659
                return empty_yielder()
 
660
            # expand by page size at either end
 
661
            expansion = self.recommended_page_size() / 2
 
662
            new_offsets = []
 
663
            for offset, length in offsets:
 
664
                new_offset = offset - expansion
 
665
                new_length = length + expansion
 
666
                if new_offset < 0:
 
667
                    # don't ask for anything < 0
 
668
                    new_length -= new_offset
 
669
                    new_offset = 0
 
670
                new_offsets.append((new_offset, new_length))
 
671
            # combine the expanded offsets
 
672
            offsets = []
 
673
            current_offset, current_length = new_offsets[0]
 
674
            current_finish = current_length + current_offset
 
675
            for offset, length in new_offsets[1:]:
 
676
                if offset > current_finish:
 
677
                    offsets.append((current_offset, current_length))
 
678
                    current_offset = offset
 
679
                    current_length = length
 
680
                    continue
 
681
                finish = offset + length
 
682
                if finish > current_finish:
 
683
                    current_finish = finish
 
684
            offsets.append((current_offset, current_length))
 
685
        return self._readv(relpath, offsets)
 
686
 
 
687
    def _readv(self, relpath, offsets):
639
688
        """Get parts of the file at the given relative path.
640
689
 
641
690
        :offsets: A list of (offset, size) tuples.