258
259
b'': ((b'', b'', b'TREE_ROOT'), [
259
260
(b'd', b'', 0, False, null_stat),
260
261
(b'd', b'', 0, False, revision_id),
262
263
b'a': ((b'', b'a', b'a-id'), [
263
264
(b'f', b'', 0, False, null_stat),
264
265
(b'f', a_sha, a_len, False, revision_id),
266
267
b'b': ((b'', b'b', b'b-id'), [
267
268
(b'd', b'', 0, False, null_stat),
268
269
(b'd', b'', 0, False, revision_id),
270
271
b'b/c': ((b'b', b'c', b'c-id'), [
271
272
(b'f', b'', 0, False, null_stat),
272
273
(b'f', c_sha, c_len, False, revision_id),
274
275
b'b/d': ((b'b', b'd', b'd-id'), [
275
276
(b'd', b'', 0, False, null_stat),
276
277
(b'd', b'', 0, False, revision_id),
278
279
b'b/d/e': ((b'b/d', b'e', b'e-id'), [
279
280
(b'f', b'', 0, False, null_stat),
280
281
(b'f', e_sha, e_len, False, revision_id),
282
283
b'b-c': ((b'', b'b-c', b'b-c-id'), [
283
(b'f', b'', 0, False, null_stat),
284
(b'f', b_c_sha, b_c_len, False, revision_id),
284
(b'f', b'', 0, False, null_stat),
285
(b'f', b_c_sha, b_c_len, False, revision_id),
286
287
b'f': ((b'', b'f', b'f-id'), [
287
(b'f', b'', 0, False, null_stat),
288
(b'f', f_sha, f_len, False, revision_id),
288
(b'f', b'', 0, False, null_stat),
289
(b'f', f_sha, f_len, False, revision_id),
291
292
state = dirstate.DirState.from_tree(tree, 'dirstate')
358
359
tree.rename_one('b/d', 'h')
360
361
old_a = expected[b'a']
361
expected[b'a'] = (old_a[0], [(b'r', b'b/g', 0, False, b''), old_a[1][1]])
363
old_a[0], [(b'r', b'b/g', 0, False, b''), old_a[1][1]])
362
364
expected[b'b/g'] = ((b'b', b'g', b'a-id'), [old_a[1][0],
363
(b'r', b'a', 0, False, b'')])
365
(b'r', b'a', 0, False, b'')])
364
366
old_d = expected[b'b/d']
365
expected[b'b/d'] = (old_d[0], [(b'r', b'h', 0, False, b''), old_d[1][1]])
367
expected[b'b/d'] = (old_d[0],
368
[(b'r', b'h', 0, False, b''), old_d[1][1]])
366
369
expected[b'h'] = ((b'', b'h', b'd-id'), [old_d[1][0],
367
(b'r', b'b/d', 0, False, b'')])
370
(b'r', b'b/d', 0, False, b'')])
369
372
old_e = expected[b'b/d/e']
370
373
expected[b'b/d/e'] = (old_e[0], [(b'r', b'h/e', 0, False, b''),
372
375
expected[b'h/e'] = ((b'h', b'e', b'e-id'), [old_e[1][0],
373
(b'r', b'b/d/e', 0, False, b'')])
376
(b'r', b'b/d/e', 0, False, b'')])
404
407
rev_id = tree.commit('first post')
405
408
root_stat_pack = dirstate.pack_stat(os.stat(tree.basedir))
406
409
expected_result = ([rev_id], [
407
((b'', b'', tree.get_root_id()), # common details
408
[(b'd', b'', 0, False, dirstate.DirState.NULLSTAT), # current tree
409
(b'd', b'', 0, False, rev_id), # first parent details
410
((b'', b'', tree.get_root_id()), # common details
411
[(b'd', b'', 0, False, dirstate.DirState.NULLSTAT), # current tree
412
(b'd', b'', 0, False, rev_id), # first parent details
411
414
state = dirstate.DirState.from_tree(tree, 'dirstate')
412
415
self.check_state_with_reopen(expected_result, state)
413
416
state.lock_read()
424
427
rev_id2 = tree2.commit('second post', allow_pointless=True)
425
428
tree.merge_from_branch(tree2.branch)
426
429
expected_result = ([rev_id, rev_id2], [
427
((b'', b'', tree.get_root_id()), # common details
428
[(b'd', b'', 0, False, dirstate.DirState.NULLSTAT), # current tree
429
(b'd', b'', 0, False, rev_id), # first parent details
430
(b'd', b'', 0, False, rev_id), # second parent details
430
((b'', b'', tree.get_root_id()), # common details
431
[(b'd', b'', 0, False, dirstate.DirState.NULLSTAT), # current tree
432
(b'd', b'', 0, False, rev_id), # first parent details
433
(b'd', b'', 0, False, rev_id), # second parent details
432
435
state = dirstate.DirState.from_tree(tree, 'dirstate')
433
436
self.check_state_with_reopen(expected_result, state)
434
437
state.lock_read()
460
463
# There are files on disk and no parents
461
464
tree = self.get_tree_with_a_file()
462
465
expected_result = ([], [
463
((b'', b'', tree.get_root_id()), # common details
464
[(b'd', b'', 0, False, dirstate.DirState.NULLSTAT), # current tree
466
((b'', b'a file', b'a-file-id'), # common
467
[(b'f', b'', 0, False, dirstate.DirState.NULLSTAT), # current
466
((b'', b'', tree.get_root_id()), # common details
467
[(b'd', b'', 0, False, dirstate.DirState.NULLSTAT), # current tree
469
((b'', b'a file', b'a-file-id'), # common
470
[(b'f', b'', 0, False, dirstate.DirState.NULLSTAT), # current
470
473
state = dirstate.DirState.from_tree(tree, 'dirstate')
471
474
self.check_state_with_reopen(expected_result, state)
479
482
self.build_tree_contents([('tree/a file', b'new content\n')])
480
483
expected_result = ([rev_id], [
481
((b'', b'', tree.get_root_id()), # common details
482
[(b'd', b'', 0, False, dirstate.DirState.NULLSTAT), # current tree
483
(b'd', b'', 0, False, rev_id), # first parent details
485
((b'', b'a file', b'a-file-id'), # common
486
[(b'f', b'', 0, False, dirstate.DirState.NULLSTAT), # current
484
((b'', b'', tree.get_root_id()), # common details
485
[(b'd', b'', 0, False, dirstate.DirState.NULLSTAT), # current tree
486
(b'd', b'', 0, False, rev_id), # first parent details
488
((b'', b'a file', b'a-file-id'), # common
489
[(b'f', b'', 0, False, dirstate.DirState.NULLSTAT), # current
487
490
(b'f', b'c3ed76e4bfd45ff1763ca206055bca8e9fc28aa8', 24, False,
488
rev_id), # first parent
491
rev_id), # first parent
491
494
state = dirstate.DirState.from_tree(tree, 'dirstate')
492
495
self.check_state_with_reopen(expected_result, state)
505
508
# and length again, giving us three distinct values:
506
509
self.build_tree_contents([('tree/a file', b'new content\n')])
507
510
expected_result = ([rev_id, rev_id2], [
508
((b'', b'', tree.get_root_id()), # common details
509
[(b'd', b'', 0, False, dirstate.DirState.NULLSTAT), # current tree
510
(b'd', b'', 0, False, rev_id), # first parent details
511
(b'd', b'', 0, False, rev_id), # second parent details
513
((b'', b'a file', b'a-file-id'), # common
514
[(b'f', b'', 0, False, dirstate.DirState.NULLSTAT), # current
511
((b'', b'', tree.get_root_id()), # common details
512
[(b'd', b'', 0, False, dirstate.DirState.NULLSTAT), # current tree
513
(b'd', b'', 0, False, rev_id), # first parent details
514
(b'd', b'', 0, False, rev_id), # second parent details
516
((b'', b'a file', b'a-file-id'), # common
517
[(b'f', b'', 0, False, dirstate.DirState.NULLSTAT), # current
515
518
(b'f', b'c3ed76e4bfd45ff1763ca206055bca8e9fc28aa8', 24, False,
516
rev_id), # first parent
519
rev_id), # first parent
517
520
(b'f', b'314d796174c9412647c3ce07dfb5d36a94e72958', 14, False,
518
rev_id2), # second parent
521
rev_id2), # second parent
521
524
state = dirstate.DirState.from_tree(tree, 'dirstate')
522
525
self.check_state_with_reopen(expected_result, state)
942
946
state._get_entry(0, fileid_utf8=b'second-root-id'))
943
947
state.set_path_id(b'', b'second-root-id')
944
948
new_root_entry = ((b'', b'', b'second-root-id'),
945
[(b'd', b'', 0, False, b'x'*32)])
949
[(b'd', b'', 0, False, b'x' * 32)])
946
950
expected_rows = [new_root_entry]
947
951
self.assertEqual(expected_rows, list(state._iter_entries()))
948
self.assertEqual(new_root_entry, state._get_entry(0, path_utf8=b''))
953
new_root_entry, state._get_entry(0, path_utf8=b''))
949
954
self.assertEqual(new_root_entry,
950
955
state._get_entry(0, fileid_utf8=b'second-root-id'))
951
956
self.assertEqual((None, None),
1153
1160
state = dirstate.DirState.initialize('dirstate')
1154
1161
expected_entries = [
1155
1162
((b'', b'', b'TREE_ROOT'), [
1156
(b'd', b'', 0, False, dirstate.DirState.NULLSTAT), # current tree
1163
(b'd', b'', 0, False, dirstate.DirState.NULLSTAT), # current tree
1158
1165
((b'', b'a file', b'a-file-id'), [
1159
(b'f', b'1'*20, 19, False, dirstate.pack_stat(stat)), # current tree
1166
(b'f', b'1' * 20, 19, False, dirstate.pack_stat(stat)), # current tree
1163
state.add('a file', b'a-file-id', 'file', stat, b'1'*20)
1170
state.add('a file', b'a-file-id', 'file', stat, b'1' * 20)
1164
1171
# having added it, it should be in the output of iter_entries.
1165
1172
self.assertEqual(expected_entries, list(state._iter_entries()))
1166
1173
# saving and reloading should not affect this.
1259
1267
filestat = os.lstat('a dir/a file')
1260
1268
expected_entries = [
1261
1269
((b'', b'', b'TREE_ROOT'), [
1262
(b'd', b'', 0, False, dirstate.DirState.NULLSTAT), # current tree
1270
(b'd', b'', 0, False, dirstate.DirState.NULLSTAT), # current tree
1264
1272
((b'', b'a dir', b'a dir id'), [
1265
(b'd', b'', 0, False, dirstate.pack_stat(dirstat)), # current tree
1273
(b'd', b'', 0, False, dirstate.pack_stat(dirstat)), # current tree
1267
1275
((b'a dir', b'a file', b'a-file-id'), [
1268
(b'f', b'1'*20, 25, False,
1269
dirstate.pack_stat(filestat)), # current tree details
1276
(b'f', b'1' * 20, 25, False,
1277
dirstate.pack_stat(filestat)), # current tree details
1272
1280
state = dirstate.DirState.initialize('dirstate')
1274
1282
state.add('a dir', b'a dir id', 'directory', dirstat, None)
1275
state.add('a dir/a file', b'a-file-id', 'file', filestat, b'1'*20)
1283
state.add('a dir/a file', b'a-file-id',
1284
'file', filestat, b'1' * 20)
1276
1285
# added it, it should be in the output of iter_entries.
1277
1286
self.assertEqual(expected_entries, list(state._iter_entries()))
1278
1287
# saving and reloading should not affect this.
1457
1467
# / in the tree, at / in one parent and /dirname/basename in the other.
1458
1468
packed_stat = b'AAAAREUHaIpFB2iKAAADAQAtkqUAAIGk'
1459
1469
root_entry = (b'', b'', b'a-root-value'), [
1460
(b'd', b'', 0, False, packed_stat), # current tree details
1461
(b'd', b'', 0, False, b'rev_id'), # first parent details
1462
# second: a pointer to the current location
1470
(b'd', b'', 0, False, packed_stat), # current tree details
1471
(b'd', b'', 0, False, b'rev_id'), # first parent details
1472
# second: a pointer to the current location
1463
1473
(b'a', b'dirname/basename', 0, False, b''),
1465
1475
state = dirstate.DirState.initialize('dirstate')
1479
1489
packed_stat = b'AAAAREUHaIpFB2iKAAADAQAtkqUAAIGk'
1481
1491
root_entries = [((b'', b'', b'a-root-value'), [
1482
(b'd', b'', 0, False, packed_stat), # current tree details
1492
(b'd', b'', 0, False, packed_stat), # current tree details
1484
1494
dirblocks.append(('', root_entries))
1485
1495
# add two files in the root
1486
1496
subdir_entry = (b'', b'subdir', b'subdir-id'), [
1487
(b'd', b'', 0, False, packed_stat), # current tree details
1497
(b'd', b'', 0, False, packed_stat), # current tree details
1489
1499
afile_entry = (b'', b'afile', b'afile-id'), [
1490
(b'f', b'sha1value', 34, False, packed_stat), # current tree details
1500
(b'f', b'sha1value', 34, False, packed_stat), # current tree details
1492
1502
dirblocks.append(('', [subdir_entry, afile_entry]))
1493
1503
# and one in subdir
1494
1504
file_entry2 = (b'subdir', b'2file', b'2file-id'), [
1495
(b'f', b'sha1value', 23, False, packed_stat), # current tree details
1505
(b'f', b'sha1value', 23, False, packed_stat), # current tree details
1497
1507
dirblocks.append(('subdir', [file_entry2]))
1498
1508
state = dirstate.DirState.initialize('dirstate')
1522
1532
def test_simple_structure(self):
1523
1533
state = self.create_dirstate_with_root_and_subdir()
1524
1534
self.addCleanup(state.unlock)
1525
self.assertBlockRowIndexEqual(1, 0, True, True, state, b'', b'subdir', 0)
1526
self.assertBlockRowIndexEqual(1, 0, True, False, state, b'', b'bdir', 0)
1527
self.assertBlockRowIndexEqual(1, 1, True, False, state, b'', b'zdir', 0)
1528
self.assertBlockRowIndexEqual(2, 0, False, False, state, b'a', b'foo', 0)
1535
self.assertBlockRowIndexEqual(
1536
1, 0, True, True, state, b'', b'subdir', 0)
1537
self.assertBlockRowIndexEqual(
1538
1, 0, True, False, state, b'', b'bdir', 0)
1539
self.assertBlockRowIndexEqual(
1540
1, 1, True, False, state, b'', b'zdir', 0)
1541
self.assertBlockRowIndexEqual(
1542
2, 0, False, False, state, b'a', b'foo', 0)
1529
1543
self.assertBlockRowIndexEqual(2, 0, False, False, state,
1530
1544
b'subdir', b'foo', 0)
1555
1569
self.assertBlockRowIndexEqual(1, 4, True, False, state,
1556
1570
b'', b'h\xc3\xa5', 0)
1557
1571
self.assertBlockRowIndexEqual(2, 0, False, False, state, b'_', b'a', 0)
1558
self.assertBlockRowIndexEqual(3, 0, False, False, state, b'aa', b'a', 0)
1559
self.assertBlockRowIndexEqual(4, 0, False, False, state, b'bb', b'a', 0)
1572
self.assertBlockRowIndexEqual(
1573
3, 0, False, False, state, b'aa', b'a', 0)
1574
self.assertBlockRowIndexEqual(
1575
4, 0, False, False, state, b'bb', b'a', 0)
1560
1576
# This would be inserted between a/ and b/
1561
self.assertBlockRowIndexEqual(3, 0, False, False, state, b'a/e', b'a', 0)
1577
self.assertBlockRowIndexEqual(
1578
3, 0, False, False, state, b'a/e', b'a', 0)
1562
1579
# Put at the end
1563
1580
self.assertBlockRowIndexEqual(4, 0, False, False, state, b'e', b'a', 0)
1578
1595
state = self.create_dirstate_with_root_and_subdir()
1579
1596
self.addCleanup(state.unlock)
1580
1597
self.assertEntryEqual(b'', b'', b'a-root-value', state, b'', 0)
1581
self.assertEntryEqual(b'', b'subdir', b'subdir-id', state, b'subdir', 0)
1598
self.assertEntryEqual(
1599
b'', b'subdir', b'subdir-id', state, b'subdir', 0)
1582
1600
self.assertEntryEqual(None, None, None, state, b'missing', 0)
1583
1601
self.assertEntryEqual(None, None, None, state, b'missing/foo', 0)
1584
1602
self.assertEntryEqual(None, None, None, state, b'subdir/foo', 0)
1719
1738
state, dirblocks = self.create_dirstate_with_two_trees()
1720
1739
self.addCleanup(state.unlock)
1721
1740
expected_result = []
1722
expected_result.append(dirblocks[3][1][2]) # h2
1723
expected_result.append(dirblocks[3][1][3]) # i
1724
expected_result.append(dirblocks[3][1][4]) # j
1741
expected_result.append(dirblocks[3][1][2]) # h2
1742
expected_result.append(dirblocks[3][1][3]) # i
1743
expected_result.append(dirblocks[3][1][4]) # j
1725
1744
self.assertEqual(expected_result,
1726
list(state._iter_child_entries(1, b'b')))
1745
list(state._iter_child_entries(1, b'b')))
1728
1747
def test_iter_child_root(self):
1729
1748
state, dirblocks = self.create_dirstate_with_two_trees()
1730
1749
self.addCleanup(state.unlock)
1731
1750
expected_result = []
1732
expected_result.append(dirblocks[1][1][0]) # a
1733
expected_result.append(dirblocks[1][1][1]) # b
1734
expected_result.append(dirblocks[1][1][3]) # d
1735
expected_result.append(dirblocks[2][1][0]) # e
1736
expected_result.append(dirblocks[2][1][1]) # f
1737
expected_result.append(dirblocks[3][1][2]) # h2
1738
expected_result.append(dirblocks[3][1][3]) # i
1739
expected_result.append(dirblocks[3][1][4]) # j
1751
expected_result.append(dirblocks[1][1][0]) # a
1752
expected_result.append(dirblocks[1][1][1]) # b
1753
expected_result.append(dirblocks[1][1][3]) # d
1754
expected_result.append(dirblocks[2][1][0]) # e
1755
expected_result.append(dirblocks[2][1][1]) # f
1756
expected_result.append(dirblocks[3][1][2]) # h2
1757
expected_result.append(dirblocks[3][1][3]) # i
1758
expected_result.append(dirblocks[3][1][4]) # j
1740
1759
self.assertEqual(expected_result,
1741
list(state._iter_child_entries(1, b'')))
1760
list(state._iter_child_entries(1, b'')))
1744
1763
class TestDirstateSortOrder(tests.TestCaseWithTransport):
1754
1773
dirs = ['a', 'a/a', 'a/a/a', 'a/a/a/a',
1755
1774
'a-a', 'a/a-a', 'a/a/a-a', 'a/a/a/a-a',
1758
1777
state = dirstate.DirState.initialize('dirstate')
1759
1778
self.addCleanup(state.unlock)
1761
1780
fake_stat = os.stat('dirstate')
1763
d_id = d.encode('utf-8').replace(b'/', b'_')+b'-id'
1782
d_id = d.encode('utf-8').replace(b'/', b'_') + b'-id'
1764
1783
file_path = d + '/f'
1765
file_id = file_path.encode('utf-8').replace(b'/', b'_')+b'-id'
1784
file_id = file_path.encode('utf-8').replace(b'/', b'_') + b'-id'
1766
1785
state.add(d, d_id, 'directory', fake_stat, null_sha)
1767
1786
state.add(file_path, file_id, 'file', fake_stat, null_sha)
1769
1788
expected = [b'', b'', b'a',
1770
b'a/a', b'a/a/a', b'a/a/a/a',
1771
b'a/a/a/a-a', b'a/a/a-a', b'a/a-a', b'a-a',
1773
split = lambda p:p.split(b'/')
1789
b'a/a', b'a/a/a', b'a/a/a/a',
1790
b'a/a/a/a-a', b'a/a/a-a', b'a/a-a', b'a-a',
1793
def split(p): return p.split(b'/')
1774
1794
self.assertEqual(sorted(expected, key=split), expected)
1775
1795
dirblock_names = [d[0] for d in state._dirblocks]
1776
1796
self.assertEqual(expected, dirblock_names)
2092
2112
def test_bisect_dirblocks(self):
2093
2113
tree, state, expected = self.create_duplicated_dirstate()
2094
2114
self.assertBisectDirBlocks(expected,
2095
[[b'', b'a', b'a2', b'b', b'b2', b'b-c', b'b-c2', b'f', b'f2']],
2097
self.assertBisectDirBlocks(expected,
2098
[[b'b/c', b'b/c2', b'b/d', b'b/d2']], state, [b'b'])
2099
self.assertBisectDirBlocks(expected,
2100
[[b'b/d/e', b'b/d/e2']], state, [b'b/d'])
2101
self.assertBisectDirBlocks(expected,
2102
[[b'', b'a', b'a2', b'b', b'b2', b'b-c', b'b-c2', b'f', b'f2'],
2103
[b'b/c', b'b/c2', b'b/d', b'b/d2'],
2104
[b'b/d/e', b'b/d/e2'],
2105
], state, [b'', b'b', b'b/d'])
2115
[[b'', b'a', b'a2', b'b', b'b2',
2116
b'b-c', b'b-c2', b'f', b'f2']],
2118
self.assertBisectDirBlocks(expected,
2119
[[b'b/c', b'b/c2', b'b/d', b'b/d2']], state, [b'b'])
2120
self.assertBisectDirBlocks(expected,
2121
[[b'b/d/e', b'b/d/e2']], state, [b'b/d'])
2122
self.assertBisectDirBlocks(expected,
2123
[[b'', b'a', b'a2', b'b', b'b2', b'b-c', b'b-c2', b'f', b'f2'],
2124
[b'b/c', b'b/c2', b'b/d', b'b/d2'],
2125
[b'b/d/e', b'b/d/e2'],
2126
], state, [b'', b'b', b'b/d'])
2107
2128
def test_bisect_dirblocks_missing(self):
2108
2129
tree, state, expected = self.create_basic_dirstate()
2109
2130
self.assertBisectDirBlocks(expected, [[b'b/d/e'], None],
2110
state, [b'b/d', b'b/e'])
2131
state, [b'b/d', b'b/e'])
2111
2132
# Files don't show up in this search
2112
2133
self.assertBisectDirBlocks(expected, [None], state, [b'a'])
2113
2134
self.assertBisectDirBlocks(expected, [None], state, [b'b/c'])
2337
2359
(b'', [(root_key, [present_dir, present_dir, present_dir])]),
2338
2360
(b'', [(key_in_1,
2339
[absent, present_file, (b'r', b'file-in-2', b'c-file-id')]),
2341
[absent, (b'r', b'file-in-1', b'c-file-id'), present_file]),
2343
[present_file, present_file, present_file]),
2345
[(b'r', b'file-t', b'b-file-id'), absent, present_file]),
2347
[present_file, absent, (b'r', b'file-s', b'b-file-id')]),
2361
[absent, present_file, (b'r', b'file-in-2', b'c-file-id')]),
2363
[absent, (b'r', b'file-in-1', b'c-file-id'), present_file]),
2365
[present_file, present_file, present_file]),
2367
[(b'r', b'file-t', b'b-file-id'), absent, present_file]),
2369
[present_file, absent, (b'r', b'file-s', b'b-file-id')]),
2350
2372
exp_dirblocks = [
2351
2373
(b'', [(root_key, [present_dir, present_dir])]),
2352
2374
(b'', [(key_in_1, [absent, present_file]),
2353
(file_in_root_key, [present_file, present_file]),
2354
(file_rename_t_key, [present_file, absent]),
2375
(file_in_root_key, [present_file, present_file]),
2376
(file_rename_t_key, [present_file, absent]),
2357
2379
state = self.create_empty_dirstate()
2358
2380
self.addCleanup(state.unlock)
2378
2400
(b'', [(root_key, [present_dir, present_dir, present_dir])]),
2379
2401
(b'', [(subdir_key, [present_dir, present_dir, present_dir])]),
2380
2402
(b'sub', [(child1_key, [absent, absent, present_file]),
2381
(child2_key, [absent, absent, present_file]),
2382
(child3_key, [absent, absent, present_file]),
2403
(child2_key, [absent, absent, present_file]),
2404
(child3_key, [absent, absent, present_file]),
2385
2407
exp_dirblocks = [
2386
2408
(b'', [(root_key, [present_dir, present_dir])]),
2573
2595
inv_delta = self.create_inv_delta(delta, b'target')
2574
2596
state = self.create_empty_dirstate()
2575
2597
state.set_state_from_scratch(active_tree.root_inventory,
2576
[(b'basis', basis_tree)], [])
2598
[(b'basis', basis_tree)], [])
2577
2599
self.assertRaises(errors.InconsistentDelta,
2578
state.update_basis_by_delta, inv_delta, b'target')
2600
state.update_basis_by_delta, inv_delta, b'target')
2580
2602
## state.update_basis_by_delta(inv_delta, b'target')
2581
## except errors.InconsistentDelta, e:
2603
# except errors.InconsistentDelta, e:
2582
2604
## import pdb; pdb.set_trace()
2584
2606
## import pdb; pdb.set_trace()
2585
2607
self.assertTrue(state._changes_aborted)
2587
2609
def test_remove_file_matching_active_state(self):
2588
2610
state = self.assertUpdate(
2590
basis =[('file', b'file-id')],
2612
basis=[('file', b'file-id')],
2594
2616
def test_remove_file_present_in_active_state(self):
2595
2617
state = self.assertUpdate(
2596
2618
active=[('file', b'file-id')],
2597
basis =[('file', b'file-id')],
2619
basis=[('file', b'file-id')],
2601
2623
def test_remove_file_present_elsewhere_in_active_state(self):
2602
2624
state = self.assertUpdate(
2603
2625
active=[('other-file', b'file-id')],
2604
basis =[('file', b'file-id')],
2626
basis=[('file', b'file-id')],
2608
2630
def test_remove_file_active_state_has_diff_file(self):
2609
2631
state = self.assertUpdate(
2610
2632
active=[('file', b'file-id-2')],
2611
basis =[('file', b'file-id')],
2633
basis=[('file', b'file-id')],
2616
2638
state = self.assertUpdate(
2617
2639
active=[('file', b'file-id-2'),
2618
2640
('other-file', b'file-id')],
2619
basis =[('file', b'file-id')],
2641
basis=[('file', b'file-id')],
2623
2645
def test_add_file_matching_active_state(self):
2624
2646
state = self.assertUpdate(
2625
2647
active=[('file', b'file-id')],
2627
2649
target=[('file', b'file-id')],
2630
2652
def test_add_file_in_empty_dir_not_matching_active_state(self):
2631
2653
state = self.assertUpdate(
2633
basis=[('dir/', b'dir-id')],
2634
target=[('dir/', b'dir-id', b'basis'), ('dir/file', b'file-id')],
2655
basis=[('dir/', b'dir-id')],
2656
target=[('dir/', b'dir-id', b'basis'), ('dir/file', b'file-id')],
2637
2659
def test_add_file_missing_in_active_state(self):
2638
2660
state = self.assertUpdate(
2641
2663
target=[('file', b'file-id')],
2644
2666
def test_add_file_elsewhere_in_active_state(self):
2645
2667
state = self.assertUpdate(
2646
2668
active=[('other-file', b'file-id')],
2648
2670
target=[('file', b'file-id')],
2652
2674
state = self.assertUpdate(
2653
2675
active=[('other-file', b'file-id'),
2654
2676
('file', b'file-id-2')],
2656
2678
target=[('file', b'file-id')],
2659
2681
def test_rename_file_matching_active_state(self):
2660
2682
state = self.assertUpdate(
2661
2683
active=[('other-file', b'file-id')],
2662
basis =[('file', b'file-id')],
2684
basis=[('file', b'file-id')],
2663
2685
target=[('other-file', b'file-id')],
2666
2688
def test_rename_file_missing_in_active_state(self):
2667
2689
state = self.assertUpdate(
2669
basis =[('file', b'file-id')],
2691
basis=[('file', b'file-id')],
2670
2692
target=[('other-file', b'file-id')],
2673
2695
def test_rename_file_present_elsewhere_in_active_state(self):
2674
2696
state = self.assertUpdate(
2675
2697
active=[('third', b'file-id')],
2676
basis =[('file', b'file-id')],
2698
basis=[('file', b'file-id')],
2677
2699
target=[('other-file', b'file-id')],
2680
2702
def test_rename_file_active_state_has_diff_source_file(self):
2681
2703
state = self.assertUpdate(
2682
2704
active=[('file', b'file-id-2')],
2683
basis =[('file', b'file-id')],
2705
basis=[('file', b'file-id')],
2684
2706
target=[('other-file', b'file-id')],
2687
2709
def test_rename_file_active_state_has_diff_target_file(self):
2688
2710
state = self.assertUpdate(
2689
2711
active=[('other-file', b'file-id-2')],
2690
basis =[('file', b'file-id')],
2712
basis=[('file', b'file-id')],
2691
2713
target=[('other-file', b'file-id')],
2704
2726
state = self.assertUpdate(
2705
2727
active=[('file', b'file-id'),
2706
2728
('other-file', b'file-id-2')],
2707
basis= [('file', b'file-id-2'),
2708
('other-file', b'file-id')],
2729
basis=[('file', b'file-id-2'),
2730
('other-file', b'file-id')],
2709
2731
target=[('file', b'file-id'),
2710
2732
('other-file', b'file-id-2')])
2712
2734
def test_rename_directory_with_contents(self):
2713
state = self.assertUpdate( # active matches basis
2735
state = self.assertUpdate( # active matches basis
2714
2736
active=[('dir1/', b'dir-id'),
2715
2737
('dir1/file', b'file-id')],
2716
basis= [('dir1/', b'dir-id'),
2717
('dir1/file', b'file-id')],
2738
basis=[('dir1/', b'dir-id'),
2739
('dir1/file', b'file-id')],
2718
2740
target=[('dir2/', b'dir-id'),
2719
2741
('dir2/file', b'file-id')])
2720
state = self.assertUpdate( # active matches target
2742
state = self.assertUpdate( # active matches target
2721
2743
active=[('dir2/', b'dir-id'),
2722
2744
('dir2/file', b'file-id')],
2723
basis= [('dir1/', b'dir-id'),
2724
('dir1/file', b'file-id')],
2745
basis=[('dir1/', b'dir-id'),
2746
('dir1/file', b'file-id')],
2725
2747
target=[('dir2/', b'dir-id'),
2726
2748
('dir2/file', b'file-id')])
2727
state = self.assertUpdate( # active empty
2749
state = self.assertUpdate( # active empty
2729
basis= [('dir1/', b'dir-id'),
2730
('dir1/file', b'file-id')],
2751
basis=[('dir1/', b'dir-id'),
2752
('dir1/file', b'file-id')],
2731
2753
target=[('dir2/', b'dir-id'),
2732
2754
('dir2/file', b'file-id')])
2733
state = self.assertUpdate( # active present at other location
2755
state = self.assertUpdate( # active present at other location
2734
2756
active=[('dir3/', b'dir-id'),
2735
2757
('dir3/file', b'file-id')],
2736
basis= [('dir1/', b'dir-id'),
2737
('dir1/file', b'file-id')],
2758
basis=[('dir1/', b'dir-id'),
2759
('dir1/file', b'file-id')],
2738
2760
target=[('dir2/', b'dir-id'),
2739
2761
('dir2/file', b'file-id')])
2740
state = self.assertUpdate( # active has different ids
2762
state = self.assertUpdate( # active has different ids
2741
2763
active=[('dir1/', b'dir1-id'),
2742
2764
('dir1/file', b'file1-id'),
2743
2765
('dir2/', b'dir2-id'),
2744
2766
('dir2/file', b'file2-id')],
2745
basis= [('dir1/', b'dir-id'),
2746
('dir1/file', b'file-id')],
2767
basis=[('dir1/', b'dir-id'),
2768
('dir1/file', b'file-id')],
2747
2769
target=[('dir2/', b'dir-id'),
2748
2770
('dir2/file', b'file-id')])
2750
2772
def test_invalid_file_not_present(self):
2751
2773
state = self.assertBadDelta(
2752
2774
active=[('file', b'file-id')],
2753
basis= [('file', b'file-id')],
2775
basis=[('file', b'file-id')],
2754
2776
delta=[('other-file', 'file', b'file-id')])
2756
2778
def test_invalid_new_id_same_path(self):
2757
2779
# The bad entry comes after
2758
2780
state = self.assertBadDelta(
2759
2781
active=[('file', b'file-id')],
2760
basis= [('file', b'file-id')],
2782
basis=[('file', b'file-id')],
2761
2783
delta=[(None, 'file', b'file-id-2')])
2762
2784
# The bad entry comes first
2763
2785
state = self.assertBadDelta(
2768
2790
def test_invalid_existing_id(self):
2769
2791
state = self.assertBadDelta(
2770
2792
active=[('file', b'file-id')],
2771
basis= [('file', b'file-id')],
2793
basis=[('file', b'file-id')],
2772
2794
delta=[(None, 'file', b'file-id')])
2774
2796
def test_invalid_parent_missing(self):
2775
2797
state = self.assertBadDelta(
2778
2800
delta=[(None, 'path/path2', b'file-id')])
2779
2801
# Note: we force the active tree to have the directory, by knowing how
2780
2802
# path_to_ie handles entries with missing parents
2781
2803
state = self.assertBadDelta(
2782
2804
active=[('path/', b'path-id')],
2784
2806
delta=[(None, 'path/path2', b'file-id')])
2785
2807
state = self.assertBadDelta(
2786
2808
active=[('path/', b'path-id'),
2787
2809
('path/path2', b'file-id')],
2789
2811
delta=[(None, 'path/path2', b'file-id')])
2791
2813
def test_renamed_dir_same_path(self):
2792
2814
# We replace the parent directory, with another parent dir. But the C
2793
2815
# file doesn't look like it has been moved.
2794
state = self.assertUpdate(# Same as basis
2816
state = self.assertUpdate( # Same as basis
2795
2817
active=[('dir/', b'A-id'),
2796
2818
('dir/B', b'B-id')],
2797
basis= [('dir/', b'A-id'),
2798
('dir/B', b'B-id')],
2819
basis=[('dir/', b'A-id'),
2820
('dir/B', b'B-id')],
2799
2821
target=[('dir/', b'C-id'),
2800
2822
('dir/B', b'B-id')])
2801
state = self.assertUpdate(# Same as target
2823
state = self.assertUpdate( # Same as target
2802
2824
active=[('dir/', b'C-id'),
2803
2825
('dir/B', b'B-id')],
2804
basis= [('dir/', b'A-id'),
2805
('dir/B', b'B-id')],
2826
basis=[('dir/', b'A-id'),
2827
('dir/B', b'B-id')],
2806
2828
target=[('dir/', b'C-id'),
2807
2829
('dir/B', b'B-id')])
2808
state = self.assertUpdate(# empty active
2830
state = self.assertUpdate( # empty active
2810
basis= [('dir/', b'A-id'),
2811
('dir/B', b'B-id')],
2832
basis=[('dir/', b'A-id'),
2833
('dir/B', b'B-id')],
2812
2834
target=[('dir/', b'C-id'),
2813
2835
('dir/B', b'B-id')])
2814
state = self.assertUpdate(# different active
2836
state = self.assertUpdate( # different active
2815
2837
active=[('dir/', b'D-id'),
2816
2838
('dir/B', b'B-id')],
2817
basis= [('dir/', b'A-id'),
2818
('dir/B', b'B-id')],
2839
basis=[('dir/', b'A-id'),
2840
('dir/B', b'B-id')],
2819
2841
target=[('dir/', b'C-id'),
2820
2842
('dir/B', b'B-id')])
2822
2844
def test_parent_child_swap(self):
2823
state = self.assertUpdate(# Same as basis
2845
state = self.assertUpdate( # Same as basis
2824
2846
active=[('A/', b'A-id'),
2825
2847
('A/B/', b'B-id'),
2826
2848
('A/B/C', b'C-id')],
2827
basis= [('A/', b'A-id'),
2829
('A/B/C', b'C-id')],
2849
basis=[('A/', b'A-id'),
2851
('A/B/C', b'C-id')],
2830
2852
target=[('A/', b'B-id'),
2831
2853
('A/B/', b'A-id'),
2832
2854
('A/B/C', b'C-id')])
2833
state = self.assertUpdate(# Same as target
2855
state = self.assertUpdate( # Same as target
2834
2856
active=[('A/', b'B-id'),
2835
2857
('A/B/', b'A-id'),
2836
2858
('A/B/C', b'C-id')],
2837
basis= [('A/', b'A-id'),
2839
('A/B/C', b'C-id')],
2859
basis=[('A/', b'A-id'),
2861
('A/B/C', b'C-id')],
2840
2862
target=[('A/', b'B-id'),
2841
2863
('A/B/', b'A-id'),
2842
2864
('A/B/C', b'C-id')])
2843
state = self.assertUpdate(# empty active
2865
state = self.assertUpdate( # empty active
2845
basis= [('A/', b'A-id'),
2847
('A/B/C', b'C-id')],
2867
basis=[('A/', b'A-id'),
2869
('A/B/C', b'C-id')],
2848
2870
target=[('A/', b'B-id'),
2849
2871
('A/B/', b'A-id'),
2850
2872
('A/B/C', b'C-id')])
2851
state = self.assertUpdate(# different active
2873
state = self.assertUpdate( # different active
2852
2874
active=[('D/', b'A-id'),
2853
2875
('D/E/', b'B-id'),
2854
2876
('F', b'C-id')],
2855
basis= [('A/', b'A-id'),
2857
('A/B/C', b'C-id')],
2877
basis=[('A/', b'A-id'),
2879
('A/B/C', b'C-id')],
2858
2880
target=[('A/', b'B-id'),
2859
2881
('A/B/', b'A-id'),
2860
2882
('A/B/C', b'C-id')])
2862
2884
def test_change_root_id(self):
2863
state = self.assertUpdate( # same as basis
2885
state = self.assertUpdate( # same as basis
2864
2886
active=[('', b'root-id'),
2865
2887
('file', b'file-id')],
2866
basis= [('', b'root-id'),
2867
('file', b'file-id')],
2888
basis=[('', b'root-id'),
2889
('file', b'file-id')],
2868
2890
target=[('', b'target-root-id'),
2869
2891
('file', b'file-id')])
2870
state = self.assertUpdate( # same as target
2892
state = self.assertUpdate( # same as target
2871
2893
active=[('', b'target-root-id'),
2872
2894
('file', b'file-id')],
2873
basis= [('', b'root-id'),
2874
('file', b'file-id')],
2895
basis=[('', b'root-id'),
2896
('file', b'file-id')],
2875
2897
target=[('', b'target-root-id'),
2876
2898
('file', b'root-id')])
2877
state = self.assertUpdate( # all different
2899
state = self.assertUpdate( # all different
2878
2900
active=[('', b'active-root-id'),
2879
2901
('file', b'file-id')],
2880
basis= [('', b'root-id'),
2881
('file', b'file-id')],
2902
basis=[('', b'root-id'),
2903
('file', b'file-id')],
2882
2904
target=[('', b'target-root-id'),
2883
2905
('file', b'root-id')])
2885
2907
def test_change_file_absent_in_active(self):
2886
2908
state = self.assertUpdate(
2888
basis= [('file', b'file-id')],
2910
basis=[('file', b'file-id')],
2889
2911
target=[('file', b'file-id')])
2891
2913
def test_invalid_changed_file(self):
2892
state = self.assertBadDelta( # Not present in basis
2914
state = self.assertBadDelta( # Not present in basis
2893
2915
active=[('file', b'file-id')],
2895
2917
delta=[('file', 'file', b'file-id')])
2896
state = self.assertBadDelta( # present at another location in basis
2918
state = self.assertBadDelta( # present at another location in basis
2897
2919
active=[('file', b'file-id')],
2898
basis= [('other-file', b'file-id')],
2920
basis=[('other-file', b'file-id')],
2899
2921
delta=[('file', 'file', b'file-id')])