140
135
# we need to pass a known file with an unknown file to get this to
141
136
# fail when expected.
142
delta = wt.changes_from(wt.basis_tree(),
137
delta = wt.changes_from(wt.basis_tree(), wt,
143
138
specific_files=['known_file', 'unknown_file'] ,
144
139
require_versioned=False)
145
140
self.assertEqual(len(delta.added), 1)
148
class TestMultiWalker(TestCaseWithTransport):
150
def assertStepOne(self, has_more, path, file_id, iterator):
151
retval = _mod_tree.MultiWalker._step_one(iterator)
153
self.assertIs(None, path)
154
self.assertIs(None, file_id)
155
self.assertEqual((False, None, None), retval)
157
self.assertEqual((has_more, path, file_id),
158
(retval[0], retval[1], retval[2].file_id))
160
def test__step_one_empty(self):
161
tree = self.make_branch_and_tree('empty')
162
repo = tree.branch.repository
163
empty_tree = repo.revision_tree(revision.NULL_REVISION)
165
iterator = empty_tree.iter_entries_by_dir()
166
self.assertStepOne(False, None, None, iterator)
167
self.assertStepOne(False, None, None, iterator)
169
def test__step_one(self):
170
tree = self.make_branch_and_tree('tree')
171
self.build_tree(['tree/a', 'tree/b/', 'tree/b/c'])
172
tree.add(['a', 'b', 'b/c'], ['a-id', 'b-id', 'c-id'])
174
iterator = tree.iter_entries_by_dir()
176
self.addCleanup(tree.unlock)
178
root_id = tree.path2id('')
179
self.assertStepOne(True, '', root_id, iterator)
180
self.assertStepOne(True, 'a', 'a-id', iterator)
181
self.assertStepOne(True, 'b', 'b-id', iterator)
182
self.assertStepOne(True, 'b/c', 'c-id', iterator)
183
self.assertStepOne(False, None, None, iterator)
184
self.assertStepOne(False, None, None, iterator)
186
def assertWalkerNext(self, exp_path, exp_file_id, master_has_node,
187
exp_other_paths, iterator):
188
"""Check what happens when we step the iterator.
190
:param path: The path for this entry
191
:param file_id: The file_id for this entry
192
:param master_has_node: Does the master tree have this entry?
193
:param exp_other_paths: A list of other_path values.
194
:param iterator: The iterator to step
196
path, file_id, master_ie, other_values = iterator.next()
197
self.assertEqual((exp_path, exp_file_id), (path, file_id),
198
'Master entry did not match')
200
self.assertIsNot(None, master_ie, 'master should have an entry')
202
self.assertIs(None, master_ie, 'master should not have an entry')
203
self.assertEqual(len(exp_other_paths), len(other_values),
204
'Wrong number of other entries')
207
for path, ie in other_values:
208
other_paths.append(path)
210
other_file_ids.append(None)
212
other_file_ids.append(ie.file_id)
215
for path in exp_other_paths:
217
exp_file_ids.append(None)
219
exp_file_ids.append(file_id)
220
self.assertEqual(exp_other_paths, other_paths, "Other paths incorrect")
221
self.assertEqual(exp_file_ids, other_file_ids,
222
"Other file_ids incorrect")
224
def lock_and_get_basis_and_root_id(self, tree):
226
self.addCleanup(tree.unlock)
227
basis_tree = tree.basis_tree()
228
basis_tree.lock_read()
229
self.addCleanup(basis_tree.unlock)
230
root_id = tree.path2id('')
231
return basis_tree, root_id
233
def test_simple_stepping(self):
234
tree = self.make_branch_and_tree('tree')
235
self.build_tree(['tree/a', 'tree/b/', 'tree/b/c'])
236
tree.add(['a', 'b', 'b/c'], ['a-id', 'b-id', 'c-id'])
238
tree.commit('first', rev_id='first-rev-id')
240
basis_tree, root_id = self.lock_and_get_basis_and_root_id(tree)
242
walker = _mod_tree.MultiWalker(tree, [basis_tree])
243
iterator = walker.iter_all()
244
self.assertWalkerNext(u'', root_id, True, [u''], iterator)
245
self.assertWalkerNext(u'a', 'a-id', True, [u'a'], iterator)
246
self.assertWalkerNext(u'b', 'b-id', True, [u'b'], iterator)
247
self.assertWalkerNext(u'b/c', 'c-id', True, [u'b/c'], iterator)
248
self.assertRaises(StopIteration, iterator.next)
250
def test_master_has_extra(self):
251
tree = self.make_branch_and_tree('tree')
252
self.build_tree(['tree/a', 'tree/b/', 'tree/c', 'tree/d'])
253
tree.add(['a', 'b', 'd'], ['a-id', 'b-id', 'd-id'])
255
tree.commit('first', rev_id='first-rev-id')
257
tree.add(['c'], ['c-id'])
258
basis_tree, root_id = self.lock_and_get_basis_and_root_id(tree)
260
walker = _mod_tree.MultiWalker(tree, [basis_tree])
261
iterator = walker.iter_all()
262
self.assertWalkerNext(u'', root_id, True, [u''], iterator)
263
self.assertWalkerNext(u'a', 'a-id', True, [u'a'], iterator)
264
self.assertWalkerNext(u'b', 'b-id', True, [u'b'], iterator)
265
self.assertWalkerNext(u'c', 'c-id', True, [None], iterator)
266
self.assertWalkerNext(u'd', 'd-id', True, [u'd'], iterator)
267
self.assertRaises(StopIteration, iterator.next)
269
def test_master_renamed_to_earlier(self):
270
"""The record is still present, it just shows up early."""
271
tree = self.make_branch_and_tree('tree')
272
self.build_tree(['tree/a', 'tree/c', 'tree/d'])
273
tree.add(['a', 'c', 'd'], ['a-id', 'c-id', 'd-id'])
274
tree.commit('first', rev_id='first-rev-id')
275
tree.rename_one('d', 'b')
277
basis_tree, root_id = self.lock_and_get_basis_and_root_id(tree)
279
walker = _mod_tree.MultiWalker(tree, [basis_tree])
280
iterator = walker.iter_all()
281
self.assertWalkerNext(u'', root_id, True, [u''], iterator)
282
self.assertWalkerNext(u'a', 'a-id', True, [u'a'], iterator)
283
self.assertWalkerNext(u'b', 'd-id', True, [u'd'], iterator)
284
self.assertWalkerNext(u'c', 'c-id', True, [u'c'], iterator)
285
self.assertRaises(StopIteration, iterator.next)
287
def test_master_renamed_to_later(self):
288
tree = self.make_branch_and_tree('tree')
289
self.build_tree(['tree/a', 'tree/b', 'tree/d'])
290
tree.add(['a', 'b', 'd'], ['a-id', 'b-id', 'd-id'])
291
tree.commit('first', rev_id='first-rev-id')
292
tree.rename_one('b', 'e')
294
basis_tree, root_id = self.lock_and_get_basis_and_root_id(tree)
296
walker = _mod_tree.MultiWalker(tree, [basis_tree])
297
iterator = walker.iter_all()
298
self.assertWalkerNext(u'', root_id, True, [u''], iterator)
299
self.assertWalkerNext(u'a', 'a-id', True, [u'a'], iterator)
300
self.assertWalkerNext(u'd', 'd-id', True, [u'd'], iterator)
301
self.assertWalkerNext(u'e', 'b-id', True, [u'b'], iterator)
302
self.assertRaises(StopIteration, iterator.next)
304
def test_other_extra_in_middle(self):
305
tree = self.make_branch_and_tree('tree')
306
self.build_tree(['tree/a', 'tree/b', 'tree/d'])
307
tree.add(['a', 'b', 'd'], ['a-id', 'b-id', 'd-id'])
308
tree.commit('first', rev_id='first-rev-id')
311
basis_tree, root_id = self.lock_and_get_basis_and_root_id(tree)
312
walker = _mod_tree.MultiWalker(tree, [basis_tree])
313
iterator = walker.iter_all()
314
self.assertWalkerNext(u'', root_id, True, [u''], iterator)
315
self.assertWalkerNext(u'a', 'a-id', True, [u'a'], iterator)
316
self.assertWalkerNext(u'd', 'd-id', True, [u'd'], iterator)
317
self.assertWalkerNext(u'b', 'b-id', False, [u'b'], iterator)
318
self.assertRaises(StopIteration, iterator.next)
320
def test_other_extra_at_end(self):
321
tree = self.make_branch_and_tree('tree')
322
self.build_tree(['tree/a', 'tree/b', 'tree/d'])
323
tree.add(['a', 'b', 'd'], ['a-id', 'b-id', 'd-id'])
324
tree.commit('first', rev_id='first-rev-id')
327
basis_tree, root_id = self.lock_and_get_basis_and_root_id(tree)
328
walker = _mod_tree.MultiWalker(tree, [basis_tree])
329
iterator = walker.iter_all()
330
self.assertWalkerNext(u'', root_id, True, [u''], iterator)
331
self.assertWalkerNext(u'a', 'a-id', True, [u'a'], iterator)
332
self.assertWalkerNext(u'b', 'b-id', True, [u'b'], iterator)
333
self.assertWalkerNext(u'd', 'd-id', False, [u'd'], iterator)
334
self.assertRaises(StopIteration, iterator.next)
336
def test_others_extra_at_end(self):
337
tree = self.make_branch_and_tree('tree')
338
self.build_tree(['tree/a', 'tree/b', 'tree/c', 'tree/d', 'tree/e'])
339
tree.add(['a', 'b', 'c', 'd', 'e'],
340
['a-id', 'b-id', 'c-id', 'd-id', 'e-id'])
341
tree.commit('first', rev_id='first-rev-id')
343
tree.commit('second', rev_id='second-rev-id')
345
tree.commit('third', rev_id='third-rev-id')
348
basis_tree, root_id = self.lock_and_get_basis_and_root_id(tree)
349
first_tree = tree.branch.repository.revision_tree('first-rev-id')
350
second_tree = tree.branch.repository.revision_tree('second-rev-id')
351
walker = _mod_tree.MultiWalker(tree, [basis_tree, first_tree,
353
iterator = walker.iter_all()
354
self.assertWalkerNext(u'', root_id, True, [u'', u'', u''], iterator)
355
self.assertWalkerNext(u'a', 'a-id', True, [u'a', u'a', u'a'], iterator)
356
self.assertWalkerNext(u'b', 'b-id', True, [u'b', u'b', u'b'], iterator)
357
self.assertWalkerNext(u'c', 'c-id', False, [u'c', u'c', u'c'], iterator)
358
self.assertWalkerNext(u'd', 'd-id', False, [None, u'd', u'd'], iterator)
359
self.assertWalkerNext(u'e', 'e-id', False, [None, u'e', None], iterator)
360
self.assertRaises(StopIteration, iterator.next)
362
def test_different_file_id_in_others(self):
363
tree = self.make_branch_and_tree('tree')
364
self.build_tree(['tree/a', 'tree/b', 'tree/c/'])
365
tree.add(['a', 'b', 'c'], ['a-id', 'b-id', 'c-id'])
366
tree.commit('first', rev_id='first-rev-id')
368
tree.rename_one('b', 'c/d')
369
self.build_tree(['tree/b'])
370
tree.add(['b'], ['b2-id'])
371
tree.commit('second', rev_id='second-rev-id')
373
tree.rename_one('a', 'c/e')
374
self.build_tree(['tree/a'])
375
tree.add(['a'], ['a2-id'])
377
basis_tree, root_id = self.lock_and_get_basis_and_root_id(tree)
378
first_tree = tree.branch.repository.revision_tree('first-rev-id')
379
walker = _mod_tree.MultiWalker(tree, [basis_tree, first_tree])
381
iterator = walker.iter_all()
382
self.assertWalkerNext(u'', root_id, True, [u'', u''], iterator)
383
self.assertWalkerNext(u'a', 'a2-id', True, [None, None], iterator)
384
self.assertWalkerNext(u'b', 'b2-id', True, [u'b', None], iterator)
385
self.assertWalkerNext(u'c', 'c-id', True, [u'c', u'c'], iterator)
386
self.assertWalkerNext(u'c/d', 'b-id', True, [u'c/d', u'b'], iterator)
387
self.assertWalkerNext(u'c/e', 'a-id', True, [u'a', u'a'], iterator)
388
self.assertRaises(StopIteration, iterator.next)
390
def assertCmpByDirblock(self, cmp_val, path1, path2):
391
self.assertEqual(cmp_val,
392
_mod_tree.MultiWalker._cmp_path_by_dirblock(path1, path2))
394
def test__cmp_path_by_dirblock(self):
395
# We only support Unicode strings at this point
396
self.assertRaises(TypeError,
397
_mod_tree.MultiWalker._cmp_path_by_dirblock, '', 'b')
398
self.assertCmpByDirblock(0, u'', u'')
399
self.assertCmpByDirblock(0, u'a', u'a')
400
self.assertCmpByDirblock(0, u'a/b', u'a/b')
401
self.assertCmpByDirblock(0, u'a/b/c', u'a/b/c')
402
self.assertCmpByDirblock(1, u'a-a', u'a')
403
self.assertCmpByDirblock(-1, u'a-a', u'a/a')
404
self.assertCmpByDirblock(-1, u'a=a', u'a/a')
405
self.assertCmpByDirblock(1, u'a-a/a', u'a/a')
406
self.assertCmpByDirblock(1, u'a=a/a', u'a/a')
407
self.assertCmpByDirblock(1, u'a-a/a', u'a/a/a')
408
self.assertCmpByDirblock(1, u'a=a/a', u'a/a/a')
409
self.assertCmpByDirblock(1, u'a-a/a/a', u'a/a/a')
410
self.assertCmpByDirblock(1, u'a=a/a/a', u'a/a/a')
412
def assertPathToKey(self, expected, path):
413
self.assertEqual(expected, _mod_tree.MultiWalker._path_to_key(path))
415
def test__path_to_key(self):
416
self.assertPathToKey(([u''], u''), u'')
417
self.assertPathToKey(([u''], u'a'), u'a')
418
self.assertPathToKey(([u'a'], u'b'), u'a/b')
419
self.assertPathToKey(([u'a', u'b'], u'c'), u'a/b/c')