/brz/remove-bazaar

To get this branch, use:
bzr branch http://gegoxaren.bato24.eu/bzr/brz/remove-bazaar
5557.1.15 by John Arbash Meinel
Merge bzr.dev 5597 to resolve NEWS, aka bzr-2.3.txt
1
# Copyright (C) 2007, 2009, 2011 Canonical Ltd
2520.4.85 by Aaron Bentley
Get all test passing (which just proves there aren't enough tests!)
2
#
3
# This program is free software; you can redistribute it and/or modify
4
# it under the terms of the GNU General Public License as published by
5
# the Free Software Foundation; either version 2 of the License, or
6
# (at your option) any later version.
7
#
8
# This program is distributed in the hope that it will be useful,
9
# but WITHOUT ANY WARRANTY; without even the implied warranty of
10
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
11
# GNU General Public License for more details.
12
#
13
# You should have received a copy of the GNU General Public License
14
# along with this program; if not, write to the Free Software
4183.7.1 by Sabin Iacob
update FSF mailing address
15
# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
2520.4.85 by Aaron Bentley
Get all test passing (which just proves there aren't enough tests!)
16
0.9.1 by Aaron Bentley
Get trivial case passing
17
from unittest import TestCase
18
6624 by Jelmer Vernooij
Merge Python3 porting work ('py3 pokes')
19
from .. import (
2520.4.2 by Aaron Bentley
Integrate mpdiff into bazaar
20
    multiparent,
2520.4.41 by Aaron Bentley
Accelerate mpdiff generation
21
    patiencediff,
2520.4.2 by Aaron Bentley
Integrate mpdiff into bazaar
22
    tests,
23
    )
6973.7.9 by Jelmer Vernooij
Port multiparent.
24
from ..sixish import int2byte
25
26
27
LINES_1 = b"a\nb\nc\nd\ne\n".splitlines(True)
28
LINES_2 = b"a\nc\nd\ne\n".splitlines(True)
29
LINES_3 = b"a\nb\nc\nd\n".splitlines(True)
30
LF_SPLIT_LINES = [b'\x00\n', b'\x00\r\x01\n', b'\x02\r\xff']
0.9.2 by Aaron Bentley
Get single-parent comparison working
31
32
33
class Mock(object):
34
35
    def __init__(self, **kwargs):
36
        self.__dict__ = kwargs
37
0.9.1 by Aaron Bentley
Get trivial case passing
38
39
class TestMulti(TestCase):
40
0.9.2 by Aaron Bentley
Get single-parent comparison working
41
    def test_compare_no_parent(self):
42
        diff = multiparent.MultiParent.from_lines(LINES_1)
43
        self.assertEqual([multiparent.NewText(LINES_1)], diff.hunks)
44
45
    def test_compare_one_parent(self):
46
        diff = multiparent.MultiParent.from_lines(LINES_1, [LINES_2])
47
        self.assertEqual([multiparent.ParentText(0, 0, 0, 1),
6973.7.9 by Jelmer Vernooij
Port multiparent.
48
                          multiparent.NewText([b'b\n']),
0.9.2 by Aaron Bentley
Get single-parent comparison working
49
                          multiparent.ParentText(0, 1, 2, 3)],
50
                         diff.hunks)
51
2520.4.138 by Aaron Bentley
Fix benign off-by-one error generating mpdiffs
52
        diff = multiparent.MultiParent.from_lines(LINES_2, [LINES_1])
53
        self.assertEqual([multiparent.ParentText(0, 0, 0, 1),
54
                          multiparent.ParentText(0, 2, 1, 3)],
55
                         diff.hunks)
56
0.9.3 by Aaron Bentley
Get three-parent comparisions under test
57
    def test_compare_two_parents(self):
58
        diff = multiparent.MultiParent.from_lines(LINES_1, [LINES_2, LINES_3])
59
        self.assertEqual([multiparent.ParentText(1, 0, 0, 4),
60
                          multiparent.ParentText(0, 3, 4, 1)],
61
                         diff.hunks)
62
2520.4.41 by Aaron Bentley
Accelerate mpdiff generation
63
    def test_compare_two_parents_blocks(self):
64
        matcher = patiencediff.PatienceSequenceMatcher(None, LINES_2, LINES_1)
65
        blocks = matcher.get_matching_blocks()
66
        diff = multiparent.MultiParent.from_lines(LINES_1, [LINES_2, LINES_3],
67
                                                  left_blocks=blocks)
68
        self.assertEqual([multiparent.ParentText(1, 0, 0, 4),
69
                          multiparent.ParentText(0, 3, 4, 1)],
70
                         diff.hunks)
71
2520.4.139 by Aaron Bentley
Support Multiparent.get_matching_blocks
72
    def test_get_matching_blocks(self):
73
        diff = multiparent.MultiParent.from_lines(LINES_1, [LINES_2])
74
        self.assertEqual([(0, 0, 1), (1, 2, 3), (4, 5, 0)],
75
                         list(diff.get_matching_blocks(0, len(LINES_2))))
76
77
        diff = multiparent.MultiParent.from_lines(LINES_2, [LINES_1])
78
        self.assertEqual([(0, 0, 1), (2, 1, 3), (5, 4, 0)],
79
                         list(diff.get_matching_blocks(0, len(LINES_1))))
80
0.9.9 by Aaron Bentley
Much progress on non-naive text reconstruction
81
    def test_range_iterator(self):
82
        diff = multiparent.MultiParent.from_lines(LINES_1, [LINES_2, LINES_3])
6973.7.9 by Jelmer Vernooij
Port multiparent.
83
        diff.hunks.append(multiparent.NewText([b'q\n']))
0.9.9 by Aaron Bentley
Much progress on non-naive text reconstruction
84
        self.assertEqual([(0, 4, 'parent', (1, 0, 4)),
85
                          (4, 5, 'parent', (0, 3, 4)),
6973.7.9 by Jelmer Vernooij
Port multiparent.
86
                          (5, 6, 'new', [b'q\n'])],
0.9.9 by Aaron Bentley
Much progress on non-naive text reconstruction
87
                         list(diff.range_iterator()))
88
0.9.2 by Aaron Bentley
Get single-parent comparison working
89
    def test_eq(self):
90
        diff = multiparent.MultiParent.from_lines(LINES_1)
91
        diff2 = multiparent.MultiParent.from_lines(LINES_1)
92
        self.assertEqual(diff, diff2)
93
        diff3 = multiparent.MultiParent.from_lines(LINES_2)
94
        self.assertFalse(diff == diff3)
95
        self.assertFalse(diff == Mock(hunks=[multiparent.NewText(LINES_1)]))
96
        self.assertEqual(multiparent.MultiParent(
97
                         [multiparent.NewText(LINES_1),
98
                          multiparent.ParentText(0, 1, 2, 3)]),
99
                         multiparent.MultiParent(
100
                         [multiparent.NewText(LINES_1),
101
                          multiparent.ParentText(0, 1, 2, 3)]))
0.9.1 by Aaron Bentley
Get trivial case passing
102
0.9.4 by Aaron Bentley
Start supporting serialization
103
    def test_to_patch(self):
6973.7.9 by Jelmer Vernooij
Port multiparent.
104
        self.assertEqual([b'i 1\n', b'a\n', b'\n', b'c 0 1 2 3\n'],
7143.15.2 by Jelmer Vernooij
Run autopep8.
105
                         list(multiparent.MultiParent([multiparent.NewText([b'a\n']),
106
                                                       multiparent.ParentText(0, 1, 2, 3)]).to_patch()))
0.9.4 by Aaron Bentley
Start supporting serialization
107
0.9.18 by Aaron Bentley
Implement from_patch
108
    def test_from_patch(self):
109
        self.assertEqual(multiparent.MultiParent(
6973.7.9 by Jelmer Vernooij
Port multiparent.
110
            [multiparent.NewText([b'a\n']),
0.9.18 by Aaron Bentley
Implement from_patch
111
             multiparent.ParentText(0, 1, 2, 3)]),
7143.15.2 by Jelmer Vernooij
Run autopep8.
112
            multiparent.MultiParent.from_patch(b'i 1\na\n\nc 0 1 2 3'))
0.9.18 by Aaron Bentley
Implement from_patch
113
        self.assertEqual(multiparent.MultiParent(
6973.7.9 by Jelmer Vernooij
Port multiparent.
114
            [multiparent.NewText([b'a']),
0.9.18 by Aaron Bentley
Implement from_patch
115
             multiparent.ParentText(0, 1, 2, 3)]),
7143.15.2 by Jelmer Vernooij
Run autopep8.
116
            multiparent.MultiParent.from_patch(b'i 1\na\nc 0 1 2 3\n'))
2520.4.30 by Aaron Bentley
Do our own line splitting for mp-diffs
117
118
    def test_binary_content(self):
119
        patch = list(
120
            multiparent.MultiParent.from_lines(LF_SPLIT_LINES).to_patch())
6973.7.9 by Jelmer Vernooij
Port multiparent.
121
        multiparent.MultiParent.from_patch(b''.join(patch))
0.9.18 by Aaron Bentley
Implement from_patch
122
2520.4.90 by Aaron Bentley
Handle \r terminated lines in Weaves properly
123
    def test_make_patch_from_binary(self):
6973.7.9 by Jelmer Vernooij
Port multiparent.
124
        patch = multiparent.MultiParent.from_texts(b''.join(LF_SPLIT_LINES))
2520.4.92 by Aaron Bentley
fix line-splitting in MultiParent.from_texts
125
        expected = multiparent.MultiParent([
126
            multiparent.NewText(LF_SPLIT_LINES)])
127
        self.assertEqual(expected, patch)
2520.4.90 by Aaron Bentley
Handle \r terminated lines in Weaves properly
128
0.9.11 by Aaron Bentley
Implement reconstruct_version, handle all hunks through that
129
    def test_num_lines(self):
6973.7.9 by Jelmer Vernooij
Port multiparent.
130
        mp = multiparent.MultiParent([multiparent.NewText([b'a\n'])])
0.9.11 by Aaron Bentley
Implement reconstruct_version, handle all hunks through that
131
        self.assertEqual(1, mp.num_lines())
6973.7.9 by Jelmer Vernooij
Port multiparent.
132
        mp.hunks.append(multiparent.NewText([b'b\n', b'c\n']))
0.9.11 by Aaron Bentley
Implement reconstruct_version, handle all hunks through that
133
        self.assertEqual(3, mp.num_lines())
134
        mp.hunks.append(multiparent.ParentText(0, 0, 3, 2))
135
        self.assertEqual(5, mp.num_lines())
6973.7.9 by Jelmer Vernooij
Port multiparent.
136
        mp.hunks.append(multiparent.NewText([b'f\n', b'g\n']))
0.9.11 by Aaron Bentley
Implement reconstruct_version, handle all hunks through that
137
        self.assertEqual(7, mp.num_lines())
138
2520.4.103 by Aaron Bentley
Add MultiParent.to_lines
139
    def test_to_lines(self):
6973.7.9 by Jelmer Vernooij
Port multiparent.
140
        mpdiff = multiparent.MultiParent.from_texts(b'a\nb\nc\n', (b'b\nc\n',))
141
        lines = mpdiff.to_lines((b'b\ne\n',))
142
        self.assertEqual([b'a\n', b'b\n', b'e\n'], lines)
2520.4.103 by Aaron Bentley
Add MultiParent.to_lines
143
0.9.1 by Aaron Bentley
Get trivial case passing
144
145
class TestNewText(TestCase):
146
147
    def test_eq(self):
148
        self.assertEqual(multiparent.NewText([]), multiparent.NewText([]))
7143.15.2 by Jelmer Vernooij
Run autopep8.
149
        self.assertFalse(multiparent.NewText([b'a'])
150
                         == multiparent.NewText([b'b']))
6973.7.9 by Jelmer Vernooij
Port multiparent.
151
        self.assertFalse(multiparent.NewText([b'a']) == Mock(lines=[b'a']))
0.9.2 by Aaron Bentley
Get single-parent comparison working
152
0.9.4 by Aaron Bentley
Start supporting serialization
153
    def test_to_patch(self):
6973.7.9 by Jelmer Vernooij
Port multiparent.
154
        self.assertEqual([b'i 0\n', b'\n'],
0.9.4 by Aaron Bentley
Start supporting serialization
155
                         list(multiparent.NewText([]).to_patch()))
6973.7.9 by Jelmer Vernooij
Port multiparent.
156
        self.assertEqual([b'i 1\n', b'a', b'\n'],
157
                         list(multiparent.NewText([b'a']).to_patch()))
158
        self.assertEqual([b'i 1\n', b'a\n', b'\n'],
159
                         list(multiparent.NewText([b'a\n']).to_patch()))
0.9.4 by Aaron Bentley
Start supporting serialization
160
0.9.2 by Aaron Bentley
Get single-parent comparison working
161
162
class TestParentText(TestCase):
163
164
    def test_eq(self):
165
        self.assertEqual(multiparent.ParentText(1, 2, 3, 4),
166
                         multiparent.ParentText(1, 2, 3, 4))
7143.15.2 by Jelmer Vernooij
Run autopep8.
167
        self.assertFalse(multiparent.ParentText(1, 2, 3, 4)
168
                         == multiparent.ParentText(2, 2, 3, 4))
169
        self.assertFalse(multiparent.ParentText(1, 2, 3, 4)
170
                         == Mock(parent=1, parent_pos=2, child_pos=3,
7143.15.5 by Jelmer Vernooij
More PEP8 fixes.
171
                                 num_lines=4))
0.9.4 by Aaron Bentley
Start supporting serialization
172
173
    def test_to_patch(self):
6973.7.9 by Jelmer Vernooij
Port multiparent.
174
        self.assertEqual([b'c 0 1 2 3\n'],
0.9.4 by Aaron Bentley
Start supporting serialization
175
                         list(multiparent.ParentText(0, 1, 2, 3).to_patch()))
0.9.8 by Aaron Bentley
get add_version working
176
177
6973.7.9 by Jelmer Vernooij
Port multiparent.
178
REV_A = [b'a\n', b'b\n', b'c\n', b'd\n']
179
REV_B = [b'a\n', b'c\n', b'd\n', b'e\n']
180
REV_C = [b'a\n', b'b\n', b'e\n', b'f\n']
0.9.9 by Aaron Bentley
Much progress on non-naive text reconstruction
181
182
0.9.8 by Aaron Bentley
get add_version working
183
class TestVersionedFile(TestCase):
184
185
    def add_version(self, vf, text, version_id, parent_ids):
6973.7.9 by Jelmer Vernooij
Port multiparent.
186
        vf.add_version(
7143.15.2 by Jelmer Vernooij
Run autopep8.
187
            [(int2byte(t) + b'\n') for t in bytearray(text)],
188
            version_id, parent_ids)
0.9.8 by Aaron Bentley
get add_version working
189
0.9.9 by Aaron Bentley
Much progress on non-naive text reconstruction
190
    def make_vf(self):
0.9.30 by Aaron Bentley
Split into MultiVersionedFile and MultiMemoryVersionedFile
191
        vf = multiparent.MultiMemoryVersionedFile()
6973.7.9 by Jelmer Vernooij
Port multiparent.
192
        self.add_version(vf, b'abcd', b'rev-a', [])
193
        self.add_version(vf, b'acde', b'rev-b', [])
194
        self.add_version(vf, b'abef', b'rev-c', [b'rev-a', b'rev-b'])
0.9.9 by Aaron Bentley
Much progress on non-naive text reconstruction
195
        return vf
196
197
    def test_add_version(self):
198
        vf = self.make_vf()
6973.7.9 by Jelmer Vernooij
Port multiparent.
199
        self.assertEqual(REV_A, vf._lines[b'rev-a'])
0.9.8 by Aaron Bentley
get add_version working
200
        vf.clear_cache()
201
        self.assertEqual(vf._lines, {})
0.9.9 by Aaron Bentley
Much progress on non-naive text reconstruction
202
203
    def test_get_line_list(self):
204
        vf = self.make_vf()
205
        vf.clear_cache()
6973.7.9 by Jelmer Vernooij
Port multiparent.
206
        self.assertEqual(REV_A, vf.get_line_list([b'rev-a'])[0])
7143.15.2 by Jelmer Vernooij
Run autopep8.
207
        self.assertEqual(
208
            [REV_B, REV_C], vf.get_line_list([b'rev-b', b'rev-c']))
0.9.9 by Aaron Bentley
Much progress on non-naive text reconstruction
209
2520.4.16 by Aaron Bentley
Handle empty versions correctly
210
    def test_reconstruct_empty(self):
211
        vf = multiparent.MultiMemoryVersionedFile()
6973.7.9 by Jelmer Vernooij
Port multiparent.
212
        vf.add_version([], b'a', [])
213
        self.assertEqual([], self.reconstruct_version(vf, b'a'))
2520.4.16 by Aaron Bentley
Handle empty versions correctly
214
0.9.9 by Aaron Bentley
Much progress on non-naive text reconstruction
215
    @staticmethod
216
    def reconstruct(vf, revision_id, start, end):
0.9.30 by Aaron Bentley
Split into MultiVersionedFile and MultiMemoryVersionedFile
217
        reconstructor = multiparent._Reconstructor(vf, vf._lines,
0.9.9 by Aaron Bentley
Much progress on non-naive text reconstruction
218
                                                   vf._parents)
219
        lines = []
220
        reconstructor._reconstruct(lines, revision_id, start, end)
221
        return lines
222
0.9.11 by Aaron Bentley
Implement reconstruct_version, handle all hunks through that
223
    @staticmethod
224
    def reconstruct_version(vf, revision_id):
0.9.30 by Aaron Bentley
Split into MultiVersionedFile and MultiMemoryVersionedFile
225
        reconstructor = multiparent._Reconstructor(vf, vf._lines,
0.9.11 by Aaron Bentley
Implement reconstruct_version, handle all hunks through that
226
                                                   vf._parents)
227
        lines = []
228
        reconstructor.reconstruct_version(lines, revision_id)
229
        return lines
230
0.9.9 by Aaron Bentley
Much progress on non-naive text reconstruction
231
    def test_reconstructor(self):
232
        vf = self.make_vf()
7143.15.2 by Jelmer Vernooij
Run autopep8.
233
        self.assertEqual([b'a\n', b'b\n'],
234
                         self.reconstruct(vf, b'rev-a', 0, 2))
235
        self.assertEqual([b'c\n', b'd\n'],
236
                         self.reconstruct(vf, b'rev-a', 2, 4))
237
        self.assertEqual([b'e\n', b'f\n'],
238
                         self.reconstruct(vf, b'rev-c', 2, 4))
239
        self.assertEqual([b'a\n', b'b\n', b'e\n', b'f\n'],
240
                         self.reconstruct(vf, b'rev-c', 0, 4))
241
        self.assertEqual([b'a\n', b'b\n', b'e\n', b'f\n'],
242
                         self.reconstruct_version(vf, b'rev-c'))
0.9.22 by Aaron Bentley
Fix restoration bug
243
244
    def test_reordered(self):
245
        """Check for a corner case that requires re-starting the cursor"""
0.9.30 by Aaron Bentley
Split into MultiVersionedFile and MultiMemoryVersionedFile
246
        vf = multiparent.MultiMemoryVersionedFile()
0.9.22 by Aaron Bentley
Fix restoration bug
247
        # rev-b must have at least two hunks, so split a and b with c.
6973.7.9 by Jelmer Vernooij
Port multiparent.
248
        self.add_version(vf, b'c', b'rev-a', [])
249
        self.add_version(vf, b'acb', b'rev-b', [b'rev-a'])
0.9.22 by Aaron Bentley
Fix restoration bug
250
        # rev-c and rev-d must each have a line from a different rev-b hunk
6973.7.9 by Jelmer Vernooij
Port multiparent.
251
        self.add_version(vf, b'b', b'rev-c', [b'rev-b'])
252
        self.add_version(vf, b'a', b'rev-d', [b'rev-b'])
0.9.22 by Aaron Bentley
Fix restoration bug
253
        # The lines from rev-c and rev-d must appear in the opposite order
6973.7.9 by Jelmer Vernooij
Port multiparent.
254
        self.add_version(vf, b'ba', b'rev-e', [b'rev-c', b'rev-d'])
0.9.22 by Aaron Bentley
Fix restoration bug
255
        vf.clear_cache()
6973.7.9 by Jelmer Vernooij
Port multiparent.
256
        lines = vf.get_line_list([b'rev-e'])[0]
257
        self.assertEqual([b'b\n', b'a\n'], lines)
0.9.34 by Aaron Bentley
Implement save, load, snapshot-by-size
258
259
260
class TestMultiVersionedFile(tests.TestCaseInTempDir):
261
262
    def test_save_load(self):
263
        vf = multiparent.MultiVersionedFile('foop')
6973.7.9 by Jelmer Vernooij
Port multiparent.
264
        vf.add_version(b'a\nb\nc\nd'.splitlines(True), b'a', [])
265
        vf.add_version(b'a\ne\nd\n'.splitlines(True), b'b', [b'a'])
0.9.34 by Aaron Bentley
Implement save, load, snapshot-by-size
266
        vf.save()
267
        newvf = multiparent.MultiVersionedFile('foop')
268
        newvf.load()
7143.15.2 by Jelmer Vernooij
Run autopep8.
269
        self.assertEqual(b'a\nb\nc\nd', b''.join(
270
            newvf.get_line_list([b'a'])[0]))
271
        self.assertEqual(b'a\ne\nd\n', b''.join(
272
            newvf.get_line_list([b'b'])[0]))
0.9.34 by Aaron Bentley
Implement save, load, snapshot-by-size
273
274
    def test_filenames(self):
275
        vf = multiparent.MultiVersionedFile('foop')
6973.7.9 by Jelmer Vernooij
Port multiparent.
276
        vf.add_version(b'a\nb\nc\nd'.splitlines(True), b'a', [])
5784.1.3 by Martin Pool
Switch away from using failUnlessExists and failIfExists
277
        self.assertPathExists('foop.mpknit')
278
        self.assertPathDoesNotExist('foop.mpidx')
0.9.34 by Aaron Bentley
Implement save, load, snapshot-by-size
279
        vf.save()
5784.1.3 by Martin Pool
Switch away from using failUnlessExists and failIfExists
280
        self.assertPathExists('foop.mpidx')
0.9.34 by Aaron Bentley
Implement save, load, snapshot-by-size
281
        vf.destroy()
5784.1.3 by Martin Pool
Switch away from using failUnlessExists and failIfExists
282
        self.assertPathDoesNotExist('foop.mpknit')
283
        self.assertPathDoesNotExist('foop.mpidx')