/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 breezy/tests/per_intertree/test_compare.py

  • Committer: Jelmer Vernooij
  • Date: 2018-11-11 04:08:32 UTC
  • mto: (7143.16.20 even-more-cleanups)
  • mto: This revision was merged to the branch mainline in revision 7175.
  • Revision ID: jelmer@jelmer.uk-20181111040832-nsljjynzzwmznf3h
Run autopep8.

Show diffs side-by-side

added added

removed removed

Lines of Context:
51
51
def _change_key(change):
52
52
    """Return a valid key for sorting Tree.iter_changes entries."""
53
53
    (file_id, paths, content_changed, versioned, parent, name, kind,
54
 
            executable) = change
 
54
     executable) = change
55
55
    return (file_id or b'', (paths[0] or '', paths[1] or ''), versioned,
56
56
            parent, name, kind, executable)
57
57
 
96
96
        self.assertEqual([('a', b'a-id', 'file'),
97
97
                          ('b', b'b-id', 'directory'),
98
98
                          ('b/c', b'c-id', 'file'),
99
 
                         ], d.added)
 
99
                          ], d.added)
100
100
        self.assertEqual([], d.modified)
101
101
        self.assertEqual([], d.removed)
102
102
        self.assertEqual([], d.renamed)
142
142
        self.assertEqual([('a', tree1.path2id('a'), 'file'),
143
143
                          ('b', tree1.path2id('b'), 'directory'),
144
144
                          ('b/c', tree1.path2id('b/c'), 'file'),
145
 
                         ], d.removed)
 
145
                          ], d.removed)
146
146
        self.assertEqual([], d.renamed)
147
147
        self.assertEqual([], d.unchanged)
148
148
 
155
155
        tree1, tree2 = self.mutable_trees_to_test_trees(self, tree1, tree2)
156
156
        d = self.intertree_class(tree1, tree2).compare()
157
157
        self.assertEqual([], d.added)
158
 
        self.assertEqual([('a', tree1.path2id('a'), 'file', True, False)], d.modified)
 
158
        self.assertEqual(
 
159
            [('a', tree1.path2id('a'), 'file', True, False)], d.modified)
159
160
        self.assertEqual([], d.removed)
160
161
        self.assertEqual([], d.renamed)
161
162
        self.assertEqual([], d.unchanged)
169
170
        tree1, tree2 = self.mutable_trees_to_test_trees(self, tree1, tree2)
170
171
        d = self.intertree_class(tree1, tree2).compare()
171
172
        self.assertEqual([], d.added)
172
 
        self.assertEqual([('b/c', tree1.path2id('b/c'), 'file', False, True)], d.modified)
 
173
        self.assertEqual(
 
174
            [('b/c', tree1.path2id('b/c'), 'file', False, True)], d.modified)
173
175
        self.assertEqual([], d.removed)
174
176
        self.assertEqual([], d.renamed)
175
177
        self.assertEqual([], d.unchanged)
185
187
        self.assertEqual([], d.added)
186
188
        self.assertEqual([], d.modified)
187
189
        self.assertEqual([], d.removed)
188
 
        self.assertEqual([('a', 'd', tree1.path2id('a'), 'file', False, False)], d.renamed)
 
190
        self.assertEqual(
 
191
            [('a', 'd', tree1.path2id('a'), 'file', False, False)], d.renamed)
189
192
        self.assertEqual([], d.unchanged)
190
193
 
191
194
    def test_file_rename_and_modification(self):
199
202
        self.assertEqual([], d.added)
200
203
        self.assertEqual([], d.modified)
201
204
        self.assertEqual([], d.removed)
202
 
        self.assertEqual([('a', 'd', tree1.path2id('a'), 'file', True, False)], d.renamed)
 
205
        self.assertEqual(
 
206
            [('a', 'd', tree1.path2id('a'), 'file', True, False)], d.renamed)
203
207
        self.assertEqual([], d.unchanged)
204
208
 
205
209
    def test_file_rename_and_meta_modification(self):
213
217
        self.assertEqual([], d.added)
214
218
        self.assertEqual([], d.modified)
215
219
        self.assertEqual([], d.removed)
216
 
        self.assertEqual([('b/c', 'e', tree1.path2id('b/c'), 'file', False, True)], d.renamed)
 
220
        self.assertEqual(
 
221
            [('b/c', 'e', tree1.path2id('b/c'), 'file', False, True)], d.renamed)
217
222
        self.assertEqual([], d.unchanged)
218
223
 
219
224
    def test_empty_to_abc_content_a_only(self):
338
343
        tree2 = self.get_tree_no_parents_abc_content(tree2)
339
344
        tree1, tree2 = self.mutable_trees_to_test_trees(self, tree1, tree2)
340
345
        self.assertRaises(errors.PathsNotVersionedError,
341
 
            self.intertree_class(tree1, tree2).compare,
342
 
            specific_files=['d'],
343
 
            require_versioned=True)
 
346
                          self.intertree_class(tree1, tree2).compare,
 
347
                          specific_files=['d'],
 
348
                          require_versioned=True)
344
349
 
345
350
    def test_default_ignores_unversioned_files(self):
346
351
        tree1 = self.make_branch_and_tree('tree1')
355
360
        d = self.intertree_class(tree1, tree2).compare()
356
361
        self.assertEqual([], d.added)
357
362
        self.assertEqual([(u'a', b'a-id', 'file', True, False),
358
 
            (u'c', b'c-id', 'file', True, False)], d.modified)
 
363
                          (u'c', b'c-id', 'file', True, False)], d.modified)
359
364
        self.assertEqual([], d.removed)
360
365
        self.assertEqual([], d.renamed)
361
366
        self.assertEqual([], d.unchanged)
431
436
        # when all the ids are unique on both sides.
432
437
        left_dict = dict((item[0], item) for item in left_changes)
433
438
        right_dict = dict((item[0], item) for item in right_changes)
434
 
        if (len(left_dict) != len(left_changes) or
435
 
            len(right_dict) != len(right_changes)):
 
439
        if (len(left_dict) != len(left_changes)
 
440
                or len(right_dict) != len(right_changes)):
436
441
            # Can't do a direct comparison. We could do a sequence diff, but
437
442
            # for now just do a regular assertEqual for now.
438
443
            self.assertEqual(left_changes, right_changes)
446
451
                same.append(str(left_item))
447
452
            else:
448
453
                different.append(" %s\n %s" % (left_item, right_item))
449
 
        self.fail("iter_changes output different. Unchanged items:\n" +
450
 
            "\n".join(same) + "\nChanged items:\n" + "\n".join(different))
 
454
        self.fail("iter_changes output different. Unchanged items:\n"
 
455
                  + "\n".join(same) + "\nChanged items:\n" + "\n".join(different))
451
456
 
452
457
    def do_iter_changes(self, tree1, tree2, **extra_args):
453
458
        """Helper to run iter_changes from tree1 to tree2.
460
465
        with tree1.lock_read(), tree2.lock_read():
461
466
            # sort order of output is not strictly defined
462
467
            return self.sorted(self.intertree_class(tree1, tree2)
463
 
                .iter_changes(**extra_args))
 
468
                               .iter_changes(**extra_args))
464
469
 
465
470
    def check_has_changes(self, expected, tree1, tree2):
466
471
        # has_changes is defined for mutable trees only
529
534
                'a/a/a/a',
530
535
                'a/a/a/a-a',
531
536
                'a/a/a/a/a',
532
 
               ]
 
537
                ]
533
538
        with_slashes = []
534
539
        paths = []
535
540
        path_ids = []
537
542
            with_slashes.append(base_path + '/' + d + '/')
538
543
            with_slashes.append(base_path + '/' + d + '/f')
539
544
            paths.append(d)
540
 
            paths.append(d+'/f')
 
545
            paths.append(d + '/f')
541
546
            path_ids.append((d.replace('/', '_') + '-id').encode('ascii'))
542
547
            path_ids.append((d.replace('/', '_') + '_f-id').encode('ascii'))
543
548
        self.build_tree(with_slashes)
590
595
        _, to_basename = os.path.split(to_path)
591
596
        # missing files have both paths, but no kind.
592
597
        return (file_id, (from_path, to_path), True, (True, True),
593
 
            (parent_id, parent_id),
594
 
            (from_basename, to_basename), (kind, None), (False, False))
 
598
                (parent_id, parent_id),
 
599
                (from_basename, to_basename), (kind, None), (False, False))
595
600
 
596
601
    def deleted(self, tree, file_id):
597
602
        entry = tree.root_inventory.get_entry(file_id)
604
609
        from_path, from_entry = self.get_path_entry(from_tree, file_id)
605
610
        to_path, to_entry = self.get_path_entry(to_tree, file_id)
606
611
        return (file_id, (from_path, to_path), content_changed, (True, True),
607
 
            (from_entry.parent_id, to_entry.parent_id),
608
 
            (from_entry.name, to_entry.name),
609
 
            (from_entry.kind, to_entry.kind),
610
 
            (from_entry.executable, to_entry.executable))
 
612
                (from_entry.parent_id, to_entry.parent_id),
 
613
                (from_entry.name, to_entry.name),
 
614
                (from_entry.kind, to_entry.kind),
 
615
                (from_entry.executable, to_entry.executable))
611
616
 
612
617
    def unchanged(self, tree, file_id):
613
618
        path, entry = self.get_path_entry(tree, file_id)
616
621
        kind = entry.kind
617
622
        executable = entry.executable
618
623
        return (file_id, (path, path), False, (True, True),
619
 
               (parent, parent), (name, name), (kind, kind),
620
 
               (executable, executable))
 
624
                (parent, parent), (name, name), (kind, kind),
 
625
                (executable, executable))
621
626
 
622
627
    def unversioned(self, tree, path):
623
628
        """Create an unversioned result."""
652
657
        tree2 = self.get_tree_no_parents_abc_content(tree2)
653
658
        tree1, tree2 = self.mutable_trees_to_locked_test_trees(tree1, tree2)
654
659
        self.assertEqual([],
655
 
            self.do_iter_changes(tree1, tree2, specific_files=[]))
 
660
                         self.do_iter_changes(tree1, tree2, specific_files=[]))
656
661
 
657
662
    def test_no_specific_files(self):
658
663
        tree1 = self.make_branch_and_tree('1')
677
682
        tree1, tree2 = self.mutable_trees_to_locked_test_trees(tree1, tree2)
678
683
        self.assertEqual(
679
684
            self.sorted([self.added(tree2, b'root-id'),
680
 
             self.added(tree2, b'a-id'),
681
 
             self.deleted(tree1, b'empty-root-id')]),
 
685
                         self.added(tree2, b'a-id'),
 
686
                         self.deleted(tree1, b'empty-root-id')]),
682
687
            self.do_iter_changes(tree1, tree2, specific_files=['a']))
683
688
 
684
689
    def test_abc_content_to_empty_a_only(self):
710
715
        tree2 = self.get_tree_no_parents_abc_content(tree2)
711
716
        tree1, tree2 = self.mutable_trees_to_locked_test_trees(tree1, tree2)
712
717
        expected_result = self.sorted([self.added(tree2, b'root-id'),
713
 
            self.added(tree2, b'a-id'), self.added(tree2, b'b-id'),
714
 
            self.added(tree2, b'c-id'), self.deleted(tree1, b'empty-root-id')])
 
718
                                       self.added(
 
719
                                           tree2, b'a-id'), self.added(tree2, b'b-id'),
 
720
                                       self.added(tree2, b'c-id'), self.deleted(tree1, b'empty-root-id')])
715
721
        self.assertEqual(expected_result,
716
 
            self.do_iter_changes(tree1, tree2, specific_files=['a', 'b/c']))
 
722
                         self.do_iter_changes(tree1, tree2, specific_files=['a', 'b/c']))
717
723
 
718
724
    def test_abc_content_to_empty(self):
719
725
        tree1 = self.make_branch_and_tree('1')
751
757
        tree1, tree2 = self.mutable_trees_to_test_trees(self, tree1, tree2)
752
758
        self.assertEqual([(b'c-id', ('b/c', 'b/c'), False, (True, True),
753
759
                           (b'b-id', b'b-id'), ('c', 'c'), ('file', 'file'),
754
 
                          (False, True))],
 
760
                           (False, True))],
755
761
                         self.do_iter_changes(tree1, tree2))
756
762
 
757
763
    def test_empty_dir(self):
800
806
        tree1.mkdir('changing/unchanging', b'mid-id')
801
807
        tree1.add(['changing/unchanging/file'], [b'file-id'], ['file'])
802
808
        tree1.put_file_bytes_non_atomic(
803
 
                'changing/unchanging/file', b'a file', file_id=b'file-id')
 
809
            'changing/unchanging/file', b'a file', file_id=b'file-id')
804
810
        tree2 = self.make_to_branch_and_tree('2')
805
811
        tree2.set_root_id(tree1.get_root_id())
806
812
        tree2.mkdir('changed', b'parent-id')
807
813
        tree2.mkdir('changed/unchanging', b'mid-id')
808
814
        tree2.add(['changed/unchanging/file'], [b'file-id'], ['file'])
809
815
        tree2.put_file_bytes_non_atomic(
810
 
                'changed/unchanging/file', b'changed content', file_id=b'file-id')
 
816
            'changed/unchanging/file', b'changed content', file_id=b'file-id')
811
817
        tree1, tree2 = self.mutable_trees_to_test_trees(self, tree1, tree2)
812
818
        # parent-id has changed, as has file-id
813
819
        root_id = tree1.path2id('')
814
820
        self.assertEqualIterChanges(
815
821
            [self.renamed(tree1, tree2, b'parent-id', False),
816
822
             self.renamed(tree1, tree2, b'file-id', True)],
817
 
             self.do_iter_changes(tree1, tree2,
818
 
             specific_files=['changed/unchanging/file']))
 
823
            self.do_iter_changes(tree1, tree2,
 
824
                                 specific_files=['changed/unchanging/file']))
819
825
 
820
826
    def test_specific_content_modification_grabs_parents_root_changes(self):
821
827
        # WHen the only direct change to a specified file is a content change,
827
833
        tree1.mkdir('changed/unchanging', b'mid-id')
828
834
        tree1.add(['changed/unchanging/file'], [b'file-id'], ['file'])
829
835
        tree1.put_file_bytes_non_atomic(
830
 
                'changed/unchanging/file', b'a file',
831
 
                b'file-id')
 
836
            'changed/unchanging/file', b'a file',
 
837
            b'file-id')
832
838
        tree2 = self.make_to_branch_and_tree('2')
833
839
        tree2.set_root_id(b'new')
834
840
        tree2.mkdir('changed', b'parent-id')
835
841
        tree2.mkdir('changed/unchanging', b'mid-id')
836
842
        tree2.add(['changed/unchanging/file'], [b'file-id'], ['file'])
837
843
        tree2.put_file_bytes_non_atomic(
838
 
                'changed/unchanging/file', b'changed content', file_id=b'file-id')
 
844
            'changed/unchanging/file', b'changed content', file_id=b'file-id')
839
845
        tree1, tree2 = self.mutable_trees_to_locked_test_trees(tree1, tree2)
840
846
        # old is gone, new is added, parent-id has changed(reparented), as has
841
847
        # file-id(content)
845
851
             self.added(tree2, b'new'),
846
852
             self.deleted(tree1, b'old'),
847
853
             self.renamed(tree1, tree2, b'file-id', True)],
848
 
             self.do_iter_changes(tree1, tree2,
849
 
             specific_files=['changed/unchanging/file']))
 
854
            self.do_iter_changes(tree1, tree2,
 
855
                                 specific_files=['changed/unchanging/file']))
850
856
 
851
857
    def test_specific_with_rename_under_new_dir_reports_new_dir(self):
852
858
        tree1 = self.make_branch_and_tree('1')
854
860
        tree1 = self.get_tree_no_parents_abc_content(tree1)
855
861
        tree2 = self.get_tree_no_parents_abc_content_7(tree2)
856
862
        tree1, tree2 = self.mutable_trees_to_test_trees(self, tree1, tree2)
857
 
        # d(d-id) is new, e is b-id renamed. 
 
863
        # d(d-id) is new, e is b-id renamed.
858
864
        root_id = tree1.path2id('')
859
865
        self.assertEqualIterChanges(
860
866
            [self.renamed(tree1, tree2, b'b-id', False),
861
867
             self.added(tree2, b'd-id')],
862
 
             self.do_iter_changes(tree1, tree2, specific_files=['d/e']))
 
868
            self.do_iter_changes(tree1, tree2, specific_files=['d/e']))
863
869
 
864
870
    def test_specific_with_rename_under_dir_under_new_dir_reports_new_dir(self):
865
871
        tree1 = self.make_branch_and_tree('1')
868
874
        tree2 = self.get_tree_no_parents_abc_content_7(tree2)
869
875
        tree2.rename_one('a', 'd/e/a')
870
876
        tree1, tree2 = self.mutable_trees_to_test_trees(self, tree1, tree2)
871
 
        # d is new, d/e is b-id renamed, d/e/a is a-id renamed 
 
877
        # d is new, d/e is b-id renamed, d/e/a is a-id renamed
872
878
        root_id = tree1.path2id('')
873
879
        self.assertEqualIterChanges(
874
880
            [self.renamed(tree1, tree2, tree1.path2id('b'), False),
875
881
             self.added(tree2, b'd-id'),
876
882
             self.renamed(tree1, tree2, b'a-id', False)],
877
 
             self.do_iter_changes(tree1, tree2, specific_files=['d/e/a']))
 
883
            self.do_iter_changes(tree1, tree2, specific_files=['d/e/a']))
878
884
 
879
885
    def test_specific_old_parent_same_path_new_parent(self):
880
886
        # when a parent is new at its path, if the path was used in the source
893
899
            [self.deleted(tree1, b'a-id'),
894
900
             self.added(tree2, b'b-id'),
895
901
             self.added(tree2, b'c-id')],
896
 
             self.do_iter_changes(tree1, tree2, specific_files=['a/c']))
 
902
            self.do_iter_changes(tree1, tree2, specific_files=['a/c']))
897
903
 
898
904
    def test_specific_old_parent_becomes_file(self):
899
905
        # When an old parent included because of a path conflict becomes a
916
922
             self.added(tree2, b'a-new-id'),
917
923
             self.renamed(tree1, tree2, b'reparented-id', False),
918
924
             self.deleted(tree1, b'deleted-id')],
919
 
             self.do_iter_changes(tree1, tree2,
920
 
                specific_files=['a/reparented']))
 
925
            self.do_iter_changes(tree1, tree2,
 
926
                                 specific_files=['a/reparented']))
921
927
 
922
928
    def test_specific_old_parent_is_deleted(self):
923
929
        # When an old parent included because of a path conflict is removed,
938
944
             self.added(tree2, b'a-new-id'),
939
945
             self.renamed(tree1, tree2, b'reparented-id', False),
940
946
             self.deleted(tree1, b'deleted-id')],
941
 
             self.do_iter_changes(tree1, tree2,
942
 
                specific_files=['a/reparented']))
 
947
            self.do_iter_changes(tree1, tree2,
 
948
                                 specific_files=['a/reparented']))
943
949
 
944
950
    def test_specific_old_parent_child_collides_with_unselected_new(self):
945
951
        # When the child of an old parent because of a path conflict becomes a
964
970
             self.renamed(tree1, tree2, b'reparented-id', False),
965
971
             self.deleted(tree1, b'collides-id'),
966
972
             self.added(tree2, b'selected-id')],
967
 
             self.do_iter_changes(tree1, tree2,
968
 
                specific_files=['a/selected']))
 
973
            self.do_iter_changes(tree1, tree2,
 
974
                                 specific_files=['a/selected']))
969
975
 
970
976
    def test_specific_old_parent_child_dir_stops_being_dir(self):
971
977
        # When the child of an old parent also stops being a directory, its
994
1000
             self.renamed(tree1, tree2, b'reparented-id-2', False),
995
1001
             self.deleted(tree1, b'deleted-id-1'),
996
1002
             self.deleted(tree1, b'deleted-id-2')],
997
 
             self.do_iter_changes(tree1, tree2,
998
 
                specific_files=['a/reparented']))
 
1003
            self.do_iter_changes(tree1, tree2,
 
1004
                                 specific_files=['a/reparented']))
999
1005
 
1000
1006
    def test_file_rename_and_meta_modification(self):
1001
1007
        tree1 = self.make_branch_and_tree('1')
1015
1021
        # trees.
1016
1022
        # In bug 438569, a file becoming a fifo causes an assert. Fifo's are
1017
1023
        # not versionable or diffable. For now, we simply stop cold when they
1018
 
        # are detected (because we don't know how far through the code the 
1019
 
        # assumption 'fifo's do not exist' goes). In future we could report 
 
1024
        # are detected (because we don't know how far through the code the
 
1025
        # assumption 'fifo's do not exist' goes). In future we could report
1020
1026
        # the kind change and have commit refuse to go futher, or something
1021
1027
        # similar. One particular reason for choosing this approach is that
1022
 
        # there is no minikind for 'fifo' in dirstate today, so we can't 
 
1028
        # there is no minikind for 'fifo' in dirstate today, so we can't
1023
1029
        # actually update records that way.
1024
1030
        # To add confusion, the totally generic code path works - but it
1025
1031
        # doesn't update persistent metadata. So this test permits InterTrees
1090
1096
        self.not_applicable_if_missing_in('file', tree1)
1091
1097
        root_id = tree1.path2id('')
1092
1098
        expected = [(b'file-id', ('file', None), False, (True, False),
1093
 
            (root_id, None), ('file', None), (None, None), (False, None))]
 
1099
                     (root_id, None), ('file', None), (None, None), (False, None))]
1094
1100
        self.assertEqual(expected, self.do_iter_changes(tree1, tree2))
1095
1101
 
1096
1102
    def test_only_in_target_and_missing(self):
1104
1110
        self.not_applicable_if_missing_in('file', tree2)
1105
1111
        root_id = tree1.path2id('')
1106
1112
        expected = [(b'file-id', (None, 'file'), False, (False, True),
1107
 
            (None, root_id), (None, 'file'), (None, None), (None, False))]
 
1113
                     (None, root_id), (None, 'file'), (None, None), (None, False))]
1108
1114
        self.assertEqual(expected, self.do_iter_changes(tree1, tree2))
1109
1115
 
1110
1116
    def test_only_in_target_missing_subtree_specific_bug_367632(self):
1120
1126
        root_id = tree1.path2id('')
1121
1127
        expected = [
1122
1128
            (b'dir-id', (None, 'a-dir'), False, (False, True),
1123
 
            (None, root_id), (None, 'a-dir'), (None, None), (None, False)),
 
1129
             (None, root_id), (None, 'a-dir'), (None, None), (None, False)),
1124
1130
            (b'file-id', (None, 'a-dir/a-file'), False, (False, True),
1125
 
            (None, b'dir-id'), (None, 'a-file'), (None, None), (None, False))
 
1131
             (None, b'dir-id'), (None, 'a-file'), (None, None), (None, False))
1126
1132
            ]
1127
1133
        # bug 367632 showed that specifying the root broke some code paths,
1128
1134
        # so we check this contract with and without it.
1129
1135
        self.assertEqual(expected, self.do_iter_changes(tree1, tree2))
1130
1136
        self.assertEqual(expected,
1131
 
            self.do_iter_changes(tree1, tree2, specific_files=['']))
 
1137
                         self.do_iter_changes(tree1, tree2, specific_files=['']))
1132
1138
 
1133
1139
    def test_unchanged_with_renames_and_modifications(self):
1134
1140
        """want_unchanged should generate a list of unchanged entries."""
1138
1144
        tree2 = self.get_tree_no_parents_abc_content_5(tree2)
1139
1145
        tree1, tree2 = self.mutable_trees_to_locked_test_trees(tree1, tree2)
1140
1146
        self.assertEqual(sorted([self.unchanged(tree1, b'root-id'),
1141
 
            self.unchanged(tree1, b'b-id'),
1142
 
            (b'a-id', ('a', 'd'), True, (True, True),
1143
 
             (b'root-id', b'root-id'), ('a', 'd'), ('file', 'file'),
1144
 
            (False, False)), self.unchanged(tree1, b'c-id')]),
1145
 
            self.do_iter_changes(tree1, tree2, include_unchanged=True))
 
1147
                                 self.unchanged(tree1, b'b-id'),
 
1148
                                 (b'a-id', ('a', 'd'), True, (True, True),
 
1149
                                  (b'root-id', b'root-id'), ('a',
 
1150
                                                             'd'), ('file', 'file'),
 
1151
                                  (False, False)), self.unchanged(tree1, b'c-id')]),
 
1152
                         self.do_iter_changes(tree1, tree2, include_unchanged=True))
1146
1153
 
1147
1154
    def test_compare_subtrees(self):
1148
1155
        tree1 = self.make_branch_and_tree('1')
1181
1188
             ('sub', 'sub'),
1182
1189
             ('tree-reference', 'tree-reference'),
1183
1190
             (False, False))],
1184
 
                         list(tree2.iter_changes(tree1,
1185
 
                             include_unchanged=True)))
 
1191
            list(tree2.iter_changes(tree1,
 
1192
                                    include_unchanged=True)))
1186
1193
 
1187
1194
    def test_disk_in_subtrees_skipped(self):
1188
1195
        """subtrees are considered not-in-the-current-tree.
1205
1212
        tree1, tree2 = self.mutable_trees_to_locked_test_trees(tree1, tree2)
1206
1213
        # this should filter correctly from above
1207
1214
        self.assertEqual([self.added(tree2, b'subtree-id')],
1208
 
            self.do_iter_changes(tree1, tree2, want_unversioned=True))
 
1215
                         self.do_iter_changes(tree1, tree2, want_unversioned=True))
1209
1216
        # and when the path is named
1210
1217
        self.assertEqual([self.added(tree2, b'subtree-id')],
1211
 
            self.do_iter_changes(tree1, tree2, specific_files=['sub'],
1212
 
                want_unversioned=True))
 
1218
                         self.do_iter_changes(tree1, tree2, specific_files=['sub'],
 
1219
                                              want_unversioned=True))
1213
1220
 
1214
1221
    def test_default_ignores_unversioned_files(self):
1215
1222
        tree1 = self.make_branch_and_tree('tree1')
1251
1258
            expected.append(self.unversioned(tree2, 'link'))
1252
1259
        expected = self.sorted(expected)
1253
1260
        self.assertEqual(expected, self.do_iter_changes(tree1, tree2,
1254
 
            want_unversioned=True))
 
1261
                                                        want_unversioned=True))
1255
1262
 
1256
1263
    def test_unversioned_paths_in_tree_specific_files(self):
1257
1264
        tree1 = self.make_branch_and_tree('tree1')
1268
1275
            self.unversioned(tree2, 'file'),
1269
1276
            self.unversioned(tree2, 'dir'),
1270
1277
            ]
1271
 
        specific_files=['file', 'dir']
 
1278
        specific_files = ['file', 'dir']
1272
1279
        if links_supported:
1273
1280
            expected.append(self.unversioned(tree2, 'link'))
1274
1281
            specific_files.append('link')
1275
1282
        expected = self.sorted(expected)
1276
1283
        self.assertEqual(expected, self.do_iter_changes(tree1, tree2,
1277
 
            specific_files=specific_files, require_versioned=False,
1278
 
            want_unversioned=True))
 
1284
                                                        specific_files=specific_files, require_versioned=False,
 
1285
                                                        want_unversioned=True))
1279
1286
 
1280
1287
    def test_unversioned_paths_in_target_matching_source_old_names(self):
1281
1288
        # its likely that naive implementations of unversioned file support
1289
1296
        tree2 = self.make_to_branch_and_tree('tree2')
1290
1297
        tree2.set_root_id(tree1.get_root_id())
1291
1298
        self.build_tree(['tree2/file', 'tree2/dir/',
1292
 
            'tree1/file', 'tree2/movedfile',
1293
 
            'tree1/dir/', 'tree2/moveddir/'])
 
1299
                         'tree1/file', 'tree2/movedfile',
 
1300
                         'tree1/dir/', 'tree2/moveddir/'])
1294
1301
        if has_symlinks():
1295
1302
            os.symlink('target', 'tree1/link')
1296
1303
            os.symlink('target', 'tree2/link')
1312
1319
            self.unversioned(tree2, 'file'),
1313
1320
            self.unversioned(tree2, 'dir'),
1314
1321
            ]
1315
 
        specific_files=['file', 'dir']
 
1322
        specific_files = ['file', 'dir']
1316
1323
        if links_supported:
1317
1324
            expected.append(self.renamed(tree1, tree2, b'link-id', False))
1318
1325
            expected.append(self.unversioned(tree2, 'link'))
1321
1328
        # run once with, and once without specific files, to catch
1322
1329
        # potentially different code paths.
1323
1330
        self.assertEqual(expected, self.do_iter_changes(tree1, tree2,
1324
 
            require_versioned=False,
1325
 
            want_unversioned=True))
 
1331
                                                        require_versioned=False,
 
1332
                                                        want_unversioned=True))
1326
1333
        self.assertEqual(expected, self.do_iter_changes(tree1, tree2,
1327
 
            specific_files=specific_files, require_versioned=False,
1328
 
            want_unversioned=True))
 
1334
                                                        specific_files=specific_files, require_versioned=False,
 
1335
                                                        want_unversioned=True))
1329
1336
 
1330
1337
    def test_similar_filenames(self):
1331
1338
        """Test when we have a few files with similar names."""
1347
1354
                         'tree2/a/b/c/d/',
1348
1355
                         'tree2/a-c/',
1349
1356
                         'tree2/a-c/e/',
1350
 
                        ])
 
1357
                         ])
1351
1358
        tree1.add(['a', 'a/b', 'a/b/c', 'a/b/c/d', 'a-c', 'a-c/e'],
1352
1359
                  [b'a-id', b'b-id', b'c-id', b'd-id', b'a-c-id', b'e-id'])
1353
1360
        tree2.add(['a', 'a/b', 'a/b/c', 'a/b/c/d', 'a-c', 'a-c/e'],
1372
1379
                                              want_unversioned=True,
1373
1380
                                              include_unchanged=True))
1374
1381
 
1375
 
 
1376
1382
    def test_unversioned_subtree_only_emits_root(self):
1377
1383
        tree1 = self.make_branch_and_tree('tree1')
1378
1384
        tree2 = self.make_to_branch_and_tree('tree2')
1384
1390
            self.unversioned(tree2, 'dir'),
1385
1391
            ]
1386
1392
        self.assertEqual(expected, self.do_iter_changes(tree1, tree2,
1387
 
            want_unversioned=True))
 
1393
                                                        want_unversioned=True))
1388
1394
 
1389
1395
    def make_trees_with_symlinks(self):
1390
1396
        tree1 = self.make_branch_and_tree('tree1')
1399
1405
        # we make the unchanged link point at unknown to catch incorrect
1400
1406
        # symlink-following code in the specified_files test.
1401
1407
        os.symlink('unknown', 'tree1/unchanged')
1402
 
        os.symlink('new',      'tree2/added')
1403
 
        os.symlink('new',      'tree2/changed')
1404
 
        os.symlink('new',      'tree2/fromfile')
1405
 
        os.symlink('new',      'tree2/fromdir')
 
1408
        os.symlink('new', 'tree2/added')
 
1409
        os.symlink('new', 'tree2/changed')
 
1410
        os.symlink('new', 'tree2/fromfile')
 
1411
        os.symlink('new', 'tree2/fromdir')
1406
1412
        os.symlink('unknown', 'tree2/unchanged')
1407
1413
        from_paths_and_ids = [
1408
1414
            'fromdir',
1422
1428
            'tofile',
1423
1429
            'unchanged',
1424
1430
            ]
1425
 
        tree1.add(from_paths_and_ids, [p.encode('utf-8') for p in from_paths_and_ids])
1426
 
        tree2.add(to_paths_and_ids, [p.encode('utf-8') for p in to_paths_and_ids])
 
1431
        tree1.add(from_paths_and_ids, [p.encode('utf-8')
 
1432
                                       for p in from_paths_and_ids])
 
1433
        tree2.add(to_paths_and_ids, [p.encode('utf-8')
 
1434
                                     for p in to_paths_and_ids])
1427
1435
        return self.mutable_trees_to_locked_test_trees(tree1, tree2)
1428
1436
 
1429
1437
    def test_versioned_symlinks(self):
1445
1453
            ]
1446
1454
        expected = self.sorted(expected)
1447
1455
        self.assertEqual(expected,
1448
 
            self.do_iter_changes(tree1, tree2, include_unchanged=True,
1449
 
                want_unversioned=True))
 
1456
                         self.do_iter_changes(tree1, tree2, include_unchanged=True,
 
1457
                                              want_unversioned=True))
1450
1458
        self.check_has_changes(True, tree1, tree2)
1451
1459
 
1452
1460
    def test_versioned_symlinks_specific_files(self):
1467
1475
        # make sure that it is correctly not returned - and neither is the
1468
1476
        # unknown path 'unknown' which it points at.
1469
1477
        self.assertEqual(expected, self.do_iter_changes(tree1, tree2,
1470
 
            specific_files=['added', 'changed', 'fromdir', 'fromfile',
1471
 
            'removed', 'unchanged', 'todir', 'tofile']))
 
1478
                                                        specific_files=['added', 'changed', 'fromdir', 'fromfile',
 
1479
                                                                        'removed', 'unchanged', 'todir', 'tofile']))
1472
1480
        self.check_has_changes(True, tree1, tree2)
1473
1481
 
1474
1482
    def test_tree_with_special_names(self):
1480
1488
    def test_trees_with_special_names(self):
1481
1489
        tree1, tree2, paths, path_ids = self.make_trees_with_special_names()
1482
1490
        expected = self.sorted(self.content_changed(tree2, f_id) for f_id in path_ids
1483
 
                          if f_id.endswith(b'_f-id'))
 
1491
                               if f_id.endswith(b'_f-id'))
1484
1492
        self.assertEqual(expected, self.do_iter_changes(tree1, tree2))
1485
1493
        self.check_has_changes(True, tree1, tree2)
1486
1494
 
1506
1514
            self.deleted(tree1, b'e-id'),
1507
1515
            ]
1508
1516
        self.assertEqualIterChanges(expected,
1509
 
            self.do_iter_changes(tree1, tree2))
 
1517
                                    self.do_iter_changes(tree1, tree2))
1510
1518
        self.check_has_changes(True, tree1, tree2)
1511
1519
 
1512
1520
    def test_added_unicode(self):
1523
1531
            self.build_tree([u'tree1/\u03b1/',
1524
1532
                             u'tree2/\u03b1/',
1525
1533
                             u'tree2/\u03b1/\u03c9-added',
1526
 
                            ])
 
1534
                             ])
1527
1535
        except UnicodeError:
1528
1536
            raise tests.TestSkipped("Could not create Unicode files.")
1529
1537
        tree1.add([u'\u03b1'], [a_id])
1552
1560
            self.build_tree([u'tree1/\u03b1/',
1553
1561
                             u'tree1/\u03b1/\u03c9-deleted',
1554
1562
                             u'tree2/\u03b1/',
1555
 
                            ])
 
1563
                             ])
1556
1564
        except UnicodeError:
1557
1565
            raise tests.TestSkipped("Could not create Unicode files.")
1558
1566
        tree1.add([u'\u03b1', u'\u03b1/\u03c9-deleted'], [a_id, deleted_id])
1582
1590
                             u'tree1/\u03b1/\u03c9-modified',
1583
1591
                             u'tree2/\u03b1/',
1584
1592
                             u'tree2/\u03b1/\u03c9-modified',
1585
 
                            ])
 
1593
                             ])
1586
1594
        except UnicodeError:
1587
1595
            raise tests.TestSkipped("Could not create Unicode files.")
1588
1596
        tree1.add([u'\u03b1', u'\u03b1/\u03c9-modified'], [a_id, mod_id])
1610
1618
        try:
1611
1619
            self.build_tree([u'tree1/\u03b1/',
1612
1620
                             u'tree2/\u03b1/',
1613
 
                            ])
 
1621
                             ])
1614
1622
        except UnicodeError:
1615
1623
            raise tests.TestSkipped("Could not create Unicode files.")
1616
1624
        self.build_tree_contents([(u'tree1/\u03c9-source', b'contents\n'),
1617
1625
                                  (u'tree2/\u03b1/\u03c9-target', b'contents\n'),
1618
 
                                 ])
 
1626
                                  ])
1619
1627
        tree1.add([u'\u03b1', u'\u03c9-source'], [a_id, rename_id])
1620
1628
        tree2.add([u'\u03b1', u'\u03b1/\u03c9-target'], [a_id, rename_id])
1621
1629
 
1641
1649
        try:
1642
1650
            self.build_tree([u'tree1/\u03b1/',
1643
1651
                             u'tree2/\u03b1/',
1644
 
                            ])
 
1652
                             ])
1645
1653
        except UnicodeError:
1646
1654
            raise tests.TestSkipped("Could not create Unicode files.")
1647
1655
        self.build_tree_contents([
1673
1681
            self.unchanged(tree1, subfile_id),
1674
1682
            ])
1675
1683
        self.assertEqual(expected,
1676
 
            self.do_iter_changes(tree1, tree2, specific_files=[u'\u03b1'],
1677
 
                include_unchanged=True))
 
1684
                         self.do_iter_changes(tree1, tree2, specific_files=[u'\u03b1'],
 
1685
                                              include_unchanged=True))
1678
1686
 
1679
1687
    def test_unknown_unicode(self):
1680
1688
        tree1 = self.make_branch_and_tree('tree1')
1691
1699
                             u'tree2/\u03b1/unknown_file',
1692
1700
                             u'tree2/\u03b1/unknown_dir/file',
1693
1701
                             u'tree2/\u03c9-unknown_root_file',
1694
 
                            ])
 
1702
                             ])
1695
1703
        except UnicodeError:
1696
1704
            raise tests.TestSkipped("Could not create Unicode files.")
1697
1705
        tree1.add([u'\u03b1'], [a_id])
1712
1720
                         self.do_iter_changes(tree1, tree2,
1713
1721
                                              require_versioned=False,
1714
1722
                                              want_unversioned=True))
1715
 
        self.assertEqual([], # Without want_unversioned we should get nothing
 
1723
        self.assertEqual([],  # Without want_unversioned we should get nothing
1716
1724
                         self.do_iter_changes(tree1, tree2))
1717
1725
        self.check_has_changes(False, tree1, tree2)
1718
1726
 
1726
1734
                                              specific_files=[u'\u03b1'],
1727
1735
                                              require_versioned=False,
1728
1736
                                              want_unversioned=True))
1729
 
        self.assertEqual([], # Without want_unversioned we should get nothing
 
1737
        self.assertEqual([],  # Without want_unversioned we should get nothing
1730
1738
                         self.do_iter_changes(tree1, tree2,
1731
1739
                                              specific_files=[u'\u03b1']))
1732
1740
 
1747
1755
        # Now create some unknowns in tree2
1748
1756
        # We should find both a/file and a/dir as unknown, but we shouldn't
1749
1757
        # recurse into a/dir to find that a/dir/subfile is also unknown.
1750
 
        self.build_tree(['tree2/a/file', 'tree2/a/dir/', 'tree2/a/dir/subfile'])
 
1758
        self.build_tree(
 
1759
            ['tree2/a/file', 'tree2/a/dir/', 'tree2/a/dir/subfile'])
1751
1760
 
1752
1761
        tree1, tree2 = self.mutable_trees_to_locked_test_trees(tree1, tree2)
1753
1762
        self.not_applicable_if_cannot_represent_unversioned(tree2)
1857
1866
            ('tree2/d', b'c contents\n'),
1858
1867
            ])
1859
1868
        tree1.add(['b', 'c'], [b'b1-id', b'c1-id'])
1860
 
        tree2.add(['a', 'b', 'c', 'd'], [b'b1-id', b'b2-id', b'c2-id', b'c1-id'])
 
1869
        tree2.add(['a', 'b', 'c', 'd'], [
 
1870
                  b'b1-id', b'b2-id', b'c2-id', b'c1-id'])
1861
1871
 
1862
1872
        tree1, tree2 = self.mutable_trees_to_locked_test_trees(tree1, tree2)
1863
1873