Rev 2731: selection of changes paths working for dirstate, seems to be a non-dirstate bug causing new root revision ids spuriously. in http://people.ubuntu.com/~robertc/baz2.0/commit-candidates

Robert Collins robertc at robertcollins.net
Thu Aug 23 09:04:58 BST 2007


At http://people.ubuntu.com/~robertc/baz2.0/commit-candidates

------------------------------------------------------------
revno: 2731
revision-id: robertc at robertcollins.net-20070823080456-p9hx5bavzmiylje3
parent: robertc at robertcollins.net-20070823072957-nyxgpdwdlmjlsmbe
committer: Robert Collins <robertc at robertcollins.net>
branch nick: commit-candidates
timestamp: Thu 2007-08-23 18:04:56 +1000
message:
  selection of changes paths working for dirstate, seems to be a non-dirstate bug causing new root revision ids spuriously.
modified:
  bzrlib/mutabletree.py          mutabletree.py-20060906023413-4wlkalbdpsxi2r4y-2
  bzrlib/tests/workingtree_implementations/test_iter_commit_candidates.py test_iter_commit_can-20070822055451-ygz697i0te0mcg8p-1
=== modified file 'bzrlib/mutabletree.py'
--- a/bzrlib/mutabletree.py	2007-08-23 07:29:57 +0000
+++ b/bzrlib/mutabletree.py	2007-08-23 08:04:56 +0000
@@ -333,7 +333,7 @@
                 parent_vector = []
                 # special case first parent as its always present with the curent
                 # structure; and is the common case
-                if basis_parent is not None:
+                if basis_versioned:
                     entry = trees[0].inventory[file_id]
                     parent_vector.append(
                         (basis_parent, basis_name, basis_kind, basis_exec,
@@ -341,11 +341,36 @@
                 else:
                     parent_vector.append((None, None, None, None, None, None))
                 if include_unchanged:
-                    # check last_modified flags across parents here.
-                    skip = False
-                    #
-                    if skip:
-                        continue
+                    # we have all records being returned, we want to filter
+                    # out so only those that have a different last-modified, 
+                    # or a difference in metadata or content to the basis are
+                    # returned
+                    for tree in trees[1:]:
+                        try:
+                            entry = tree.inventory[file_id]
+                        except NoSuchId:
+                            parent_vector.append((None, None, None, None, None, None))
+                        else:
+                            parent_vector.append((
+                                entry.parent_id, entry.name, entry.kind, entry.executable,
+                                entry.text_sha1, entry.revision))
+                    if not content_change:
+                        all_parents = set([vector[0] for vector in
+                            parent_vector if vector[5] is not None])
+                        all_names = set([vector[1] for vector in
+                            parent_vector if vector[5] is not None])
+                        all_kinds = set([vector[2] for vector in
+                            parent_vector if vector[5] is not None])
+                        all_exec = set([vector[3] for vector in
+                            parent_vector if vector[5] is not None])
+                        # no need to check sha - content_change encapsulates that
+                        all_last_mod = set([vector[5] for vector in 
+                            parent_vector if vector[5] is not None])
+                        if (len(all_parents)==1 and len(all_names)==1 and
+                            len(all_kinds)==1 and len(all_exec)==1 and
+                            len(all_last_mod)==1):
+                            # really unchanged
+                            continue
                 # TODO: get the file hash IFF it is available. This requires
                 #       layering changes to allow querying for this - typically
                 #       we need a stat fingerprint, and thats not available here.

=== modified file 'bzrlib/tests/workingtree_implementations/test_iter_commit_candidates.py'
--- a/bzrlib/tests/workingtree_implementations/test_iter_commit_candidates.py	2007-08-23 07:29:57 +0000
+++ b/bzrlib/tests/workingtree_implementations/test_iter_commit_candidates.py	2007-08-23 08:04:56 +0000
@@ -283,3 +283,48 @@
                      tree.last_revision():tree.basis_tree()})))
         finally:
             tree.unlock()
+
+    def test_merge_unchanged_reported(self):
+        tree = self.make_branch_and_tree('tree')
+        # get a tree with one symlink/file/dir committed, so we can 
+        # delta them
+        paths = ['dir', 'file']
+        ids = ['dirid', 'fileid']
+        self.build_tree(['tree/dir/'])
+        # we want specific content for file later in the test
+        self.build_tree_contents([('tree/file', 'content')])
+        tree.add(paths, ids)
+        rev_id1 = tree.commit('commit')
+        # now make a branch
+        tree2 = tree.bzrdir.sprout('tree2').open_workingtree()
+        # change tree2, which alters the file last_modified but not the dir
+        # last modified, so we can check only file is reported on merge.
+        self.build_tree_contents([('tree2/file', 'new content')])
+        tree2.commit('change file')
+        # and revert file, so that there is no content change to be reported
+        self.build_tree_contents([('tree2/file', 'content')])
+        rev_id2 = tree2.commit('restore file')
+        # check the test will be valid:
+        tree.lock_read()
+        tree2.lock_read()
+        self.assertEqual([], list(tree._iter_changes(tree2)))
+        tree.unlock()
+        tree2.unlock()
+        # now execute
+        tree.merge_from_branch(tree2.branch)
+        tree.lock_write()
+        tree_root = tree.path2id('')
+        expected_result = [
+            ((u'file', 'fileid', tree_root, 'file', 'file', False, None),
+             ((tree_root, 'file', 'file', False,
+              '040f06fd774092478d450774f5ba30c5da78acc8', rev_id1),
+              (tree_root, 'file', 'file', False,
+              '040f06fd774092478d450774f5ba30c5da78acc8', rev_id2),),
+             False)]
+        try:
+            self.assertEqual(expected_result,
+                list(tree.iter_commit_candidates({tree.last_revision():tree.basis_tree(),
+                    tree2.last_revision():tree2.basis_tree()})))
+        finally:
+            tree.unlock()
+



More information about the bazaar-commits mailing list