← Back to team overview

dulwich-users team mailing list archive

[PATCH 26/33] pack: Add PackInflater to quickly inflate pack objects.

 

From: Dave Borowitz <dborowitz@xxxxxxxxxx>

Change-Id: I7ce6065370ca31680cb6666b6f7d79fd789489d4
---
 NEWS                       |    3 ++-
 dulwich/pack.py            |   15 +++++++++++----
 dulwich/tests/test_pack.py |    9 +++++++++
 3 files changed, 22 insertions(+), 5 deletions(-)

diff --git a/NEWS b/NEWS
index 02745fb..b445391 100644
--- a/NEWS
+++ b/NEWS
@@ -3,7 +3,8 @@
  FEATURES
 
   * New DeltaChainIterator abstract class for quickly iterating all objects in
-    a pack, with an implementation for pack indexing. (Dave Borowitz)
+    a pack, with implementations for pack indexing and inflation.
+    (Dave Borowitz)
 
  BUG FIXES
 
diff --git a/dulwich/pack.py b/dulwich/pack.py
index da83f7e..55c4ed5 100644
--- a/dulwich/pack.py
+++ b/dulwich/pack.py
@@ -1260,6 +1260,16 @@ class PackIndexer(DeltaChainIterator):
         return sha, offset, crc32
 
 
+class PackInflater(DeltaChainIterator):
+    """Delta chain iterator that yields ShaFile objects."""
+
+    def _result(self, unused_offset, type_num, chunks, unused_sha,
+                unused_crc32):
+        # TODO: If from_raw_chunks supported it, we could pass in the SHA to
+        # avoid another pass over the file.
+        return ShaFile.from_raw_chunks(type_num, chunks)
+
+
 class SHA1Reader(object):
     """Wrapper around a file-like object that remembers the SHA1 of its data."""
 
@@ -1768,10 +1778,7 @@ class Pack(object):
 
     def iterobjects(self):
         """Iterate over the objects in this pack."""
-        for offset, type, obj, crc32 in self.data.iterobjects():
-            assert isinstance(offset, int)
-            yield ShaFile.from_raw_chunks(
-              *self.data.resolve_object(offset, type, obj))
+        return iter(PackInflater.for_pack_data(self.data))
 
     def pack_tuples(self):
         """Provide an iterable for use with write_pack_objects.
diff --git a/dulwich/tests/test_pack.py b/dulwich/tests/test_pack.py
index 1be2e01..0f39c1a 100644
--- a/dulwich/tests/test_pack.py
+++ b/dulwich/tests/test_pack.py
@@ -424,6 +424,15 @@ class TestPack(PackTests):
         self.assertRaises(ChecksumMismatch, lambda:
                           bad_pack.check_length_and_checksum())
 
+    def test_iterobjects(self):
+        p = self.get_pack(pack1_sha)
+        objs = dict((o.id, o) for o in p.iterobjects())
+        self.assertEquals(3, len(objs))
+        self.assertEquals(sorted(objs), sorted(p.index))
+        self.assertTrue(isinstance(objs[a_sha], Blob))
+        self.assertTrue(isinstance(objs[tree_sha], Tree))
+        self.assertTrue(isinstance(objs[commit_sha], Commit))
+
 
 class WritePackTests(TestCase):
 
-- 
1.7.3.1



References