Rev 3584: Add the ability to define a series of commits, which allows us to hold open the locks. in http://bzr.arbash-meinel.com/branches/bzr/1.7-dev/use_branch_builder

John Arbash Meinel john at arbash-meinel.com
Tue Jul 22 21:41:39 BST 2008


At http://bzr.arbash-meinel.com/branches/bzr/1.7-dev/use_branch_builder

------------------------------------------------------------
revno: 3584
revision-id: john at arbash-meinel.com-20080722204034-x54day968ipfmr1y
parent: john at arbash-meinel.com-20080722194840-dqp3t6mc12f2s36n
committer: John Arbash Meinel <john at arbash-meinel.com>
branch nick: use_branch_builder
timestamp: Tue 2008-07-22 15:40:34 -0500
message:
  Add the ability to define a series of commits, which allows us to hold open the locks.
-------------- next part --------------
=== modified file 'bzrlib/branchbuilder.py'
--- a/bzrlib/branchbuilder.py	2008-07-22 19:45:01 +0000
+++ b/bzrlib/branchbuilder.py	2008-07-22 20:40:34 +0000
@@ -51,6 +51,7 @@
             format = bzrdir.format_registry.make_bzrdir(format)
         self._branch = bzrdir.BzrDir.create_branch_convenience(transport.base,
             format=format, force_new_tree=False)
+        self._tree = None
 
     def build_commit(self):
         """Build a commit on the branch."""
@@ -75,6 +76,32 @@
             self._branch.set_last_revision_info(new_revno, new_revision_id)
         finally:
             self._branch.unlock()
+        if self._tree is not None:
+            # We are currently processing a series, but when switching branch
+            # pointers, it is easiest to just create a new memory tree.
+            # That way we are sure to have the right files-on-disk
+            # We are cheating a little bit here, and locking the new tree
+            # before the old tree is unlocked. But that way the branch stays
+            # locked throughout.
+            new_tree = memorytree.MemoryTree.create_on_branch(self._branch)
+            new_tree.lock_write()
+            self._tree.unlock()
+            self._tree = new_tree
+
+    def start_series(self):
+        """We will be creating a series of commits.
+
+        This allows us to hold open the locks while we are processing.
+
+        Make sure to call 'finish_series' when you are done.
+        """
+        self._tree = memorytree.MemoryTree.create_on_branch(self._branch)
+        self._tree.lock_write()
+
+    def finish_series(self):
+        """Call this after start_series to unlock the various objects."""
+        self._tree.unlock()
+        self._tree = None
 
     def build_snapshot(self, revision_id, parent_ids, actions,
                        message=None):
@@ -97,7 +124,10 @@
             if base_id != self._branch.last_revision():
                 self._move_branch_pointer(base_id)
 
-        tree = memorytree.MemoryTree.create_on_branch(self._branch)
+        if self._tree is not None:
+            tree = self._tree
+        else:
+            tree = memorytree.MemoryTree.create_on_branch(self._branch)
         tree.lock_write()
         try:
             if parent_ids is not None:

=== modified file 'bzrlib/tests/test_branchbuilder.py'
--- a/bzrlib/tests/test_branchbuilder.py	2008-07-22 19:45:01 +0000
+++ b/bzrlib/tests/test_branchbuilder.py	2008-07-22 20:40:34 +0000
@@ -201,6 +201,8 @@
 
     def test_set_parent(self):
         builder = self.build_a_rev()
+        builder.start_series()
+        self.addCleanup(builder.finish_series)
         builder.build_snapshot('B-id', ['A-id'],
             [('modify', ('a-id', 'new\ncontent\n'))])
         builder.build_snapshot('C-id', ['A-id'], 
@@ -211,8 +213,6 @@
         #   C B
         # And not A => B => C
         repo = builder.get_branch().repository
-        repo.lock_read()
-        self.addCleanup(repo.unlock)
         self.assertEqual({'B-id': ('A-id',), 'C-id': ('A-id',)},
                          repo.get_parent_map(['B-id', 'C-id']))
         b_tree = repo.revision_tree('B-id')
@@ -232,14 +232,14 @@
 
     def test_set_merge_parent(self):
         builder = self.build_a_rev()
+        builder.start_series()
+        self.addCleanup(builder.finish_series)
         builder.build_snapshot('B-id', ['A-id'],
             [('add', ('b', 'b-id', 'file', 'b\ncontent\n'))])
         builder.build_snapshot('C-id', ['A-id'],
             [('add', ('c', 'c-id', 'file', 'alt\ncontent\n'))])
         builder.build_snapshot('D-id', ['B-id', 'C-id'], [])
         repo = builder.get_branch().repository
-        repo.lock_read()
-        self.addCleanup(repo.unlock)
         self.assertEqual({'B-id': ('A-id',), 'C-id': ('A-id',),
                           'D-id': ('B-id', 'C-id')},
                          repo.get_parent_map(['B-id', 'C-id', 'D-id']))
@@ -253,6 +253,8 @@
 
     def test_set_merge_parent_and_contents(self):
         builder = self.build_a_rev()
+        builder.start_series()
+        self.addCleanup(builder.finish_series)
         builder.build_snapshot('B-id', ['A-id'],
             [('add', ('b', 'b-id', 'file', 'b\ncontent\n'))])
         builder.build_snapshot('C-id', ['A-id'],
@@ -260,8 +262,6 @@
         builder.build_snapshot('D-id', ['B-id', 'C-id'],
             [('add', ('c', 'c-id', 'file', 'alt\ncontent\n'))])
         repo = builder.get_branch().repository
-        repo.lock_read()
-        self.addCleanup(repo.unlock)
         self.assertEqual({'B-id': ('A-id',), 'C-id': ('A-id',),
                           'D-id': ('B-id', 'C-id')},
                          repo.get_parent_map(['B-id', 'C-id', 'D-id']))
@@ -274,3 +274,15 @@
         # Because we copied the exact text into *this* tree, the 'c' file
         # should look like it was not modified in the merge
         self.assertEqual('C-id', d_tree.inventory['c-id'].revision)
+
+    def test_start_finish_series(self):
+        builder = BranchBuilder(self.get_transport().clone('foo'))
+        builder.start_series()
+        try:
+            self.assertIsNot(None, builder._tree)
+            self.assertEqual('w', builder._tree._lock_mode)
+            self.assertTrue(builder._branch.is_locked())
+        finally:
+            builder.finish_series()
+        self.assertIs(None, builder._tree)
+        self.assertFalse(builder._branch.is_locked())



More information about the bazaar-commits mailing list