/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 bzrlib/tests/workingtree_implementations/test_move.py

First attempt to merge .dev and resolve the conflicts (but tests are 
failing)

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
# Copyright (C) 2006, 2007 Canonical Ltd
 
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
 
15
# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
 
16
 
 
17
"""Tests for interface conformance of 'WorkingTree.move'"""
 
18
 
 
19
import os
 
20
 
 
21
from bzrlib import (
 
22
    errors,
 
23
    osutils,
 
24
    )
 
25
 
 
26
from bzrlib.workingtree_4 import WorkingTreeFormat4
 
27
from bzrlib.tests.workingtree_implementations import TestCaseWithWorkingTree
 
28
 
 
29
 
 
30
class TestMove(TestCaseWithWorkingTree):
 
31
 
 
32
    def get_tree_layout(self, tree):
 
33
        """Get the (path, file_id) pairs for the current tree."""
 
34
        tree.lock_read()
 
35
        try:
 
36
            return [(path, ie.file_id) for path, ie
 
37
                    in tree.iter_entries_by_dir()]
 
38
        finally:
 
39
            tree.unlock()
 
40
 
 
41
    def assertTreeLayout(self, expected, tree):
 
42
        """Check that the tree has the correct layout."""
 
43
        actual = self.get_tree_layout(tree)
 
44
        self.assertEqual(expected, actual)
 
45
 
 
46
    def test_move_correct_call_named(self):
 
47
        """tree.move has the deprecated parameter 'to_name'.
 
48
        It has been replaced by 'to_dir' for consistency.
 
49
        Test the new API using named parameter
 
50
        """
 
51
        self.build_tree(['a1', 'sub1/'])
 
52
        tree = self.make_branch_and_tree('.')
 
53
        tree.add(['a1', 'sub1'])
 
54
        tree.commit('initial commit')
 
55
        self.assertEqual([('a1', 'sub1/a1')],
 
56
            tree.move(['a1'], to_dir='sub1', after=False))
 
57
        tree._validate()
 
58
 
 
59
    def test_move_correct_call_unnamed(self):
 
60
        """tree.move has the deprecated parameter 'to_name'.
 
61
        It has been replaced by 'to_dir' for consistency.
 
62
        Test the new API using unnamed parameter
 
63
        """
 
64
        self.build_tree(['a1', 'sub1/'])
 
65
        tree = self.make_branch_and_tree('.')
 
66
        tree.add(['a1', 'sub1'])
 
67
        tree.commit('initial commit')
 
68
        self.assertEqual([('a1', 'sub1/a1')],
 
69
            tree.move(['a1'], 'sub1', after=False))
 
70
        tree._validate()
 
71
 
 
72
    def test_move_deprecated_wrong_call(self):
 
73
        """tree.move has the deprecated parameter 'to_name'.
 
74
        It has been replaced by 'to_dir' for consistency.
 
75
        Test the new API using wrong parameter
 
76
        """
 
77
        self.build_tree(['a1', 'sub1/'])
 
78
        tree = self.make_branch_and_tree('.')
 
79
        tree.add(['a1', 'sub1'])
 
80
        tree.commit('initial commit')
 
81
        self.assertRaises(TypeError, tree.move, ['a1'],
 
82
                          to_this_parameter_does_not_exist='sub1',
 
83
                          after=False)
 
84
        tree._validate()
 
85
 
 
86
    def test_move_deprecated_call(self):
 
87
        """tree.move has the deprecated parameter 'to_name'.
 
88
        It has been replaced by 'to_dir' for consistency.
 
89
        Test the new API using deprecated parameter
 
90
        """
 
91
        self.build_tree(['a1', 'sub1/'])
 
92
        tree = self.make_branch_and_tree('.')
 
93
        tree.add(['a1', 'sub1'])
 
94
        tree.commit('initial commit')
 
95
 
 
96
        try:
 
97
            self.callDeprecated(['The parameter to_name was deprecated'
 
98
                                 ' in version 0.13. Use to_dir instead'],
 
99
                                tree.move, ['a1'], to_name='sub1',
 
100
                                after=False)
 
101
        except TypeError:
 
102
            # WorkingTreeFormat4 doesn't have to maintain api compatibility
 
103
            # since it was deprecated before the class was introduced.
 
104
            if not isinstance(self.workingtree_format, WorkingTreeFormat4):
 
105
                raise
 
106
        tree._validate()
 
107
 
 
108
    def test_move_target_not_dir(self):
 
109
        tree = self.make_branch_and_tree('.')
 
110
        self.build_tree(['a'])
 
111
        tree.add(['a'])
 
112
        tree.commit('initial', rev_id='rev-1')
 
113
 
 
114
        self.assertRaises(errors.BzrMoveFailedError,
 
115
                          tree.move, ['a'], 'not-a-dir')
 
116
        tree._validate()
 
117
 
 
118
    def test_move_non_existent(self):
 
119
        tree = self.make_branch_and_tree('.')
 
120
        self.build_tree(['a/'])
 
121
        tree.add(['a'])
 
122
        tree.commit('initial', rev_id='rev-1')
 
123
        self.assertRaises(errors.BzrMoveFailedError,
 
124
                          tree.move, ['not-a-file'], 'a')
 
125
        self.assertRaises(errors.BzrMoveFailedError,
 
126
                          tree.move, ['not-a-file'], '')
 
127
        tree._validate()
 
128
 
 
129
    def test_move_target_not_versioned(self):
 
130
        tree = self.make_branch_and_tree('.')
 
131
        self.build_tree(['a/', 'b'])
 
132
        tree.add(['b'])
 
133
        tree.commit('initial', rev_id='rev-1')
 
134
        self.assertRaises(errors.BzrMoveFailedError,
 
135
                          tree.move, ['b'], 'a')
 
136
        tree._validate()
 
137
 
 
138
    def test_move_unversioned(self):
 
139
        tree = self.make_branch_and_tree('.')
 
140
        self.build_tree(['a/', 'b'])
 
141
        tree.add(['a'])
 
142
        tree.commit('initial', rev_id='rev-1')
 
143
        self.assertRaises(errors.BzrMoveFailedError,
 
144
                          tree.move, ['b'], 'a')
 
145
        tree._validate()
 
146
 
 
147
    def test_move_multi_unversioned(self):
 
148
        tree = self.make_branch_and_tree('.')
 
149
        self.build_tree(['a/', 'b', 'c', 'd'])
 
150
        tree.add(['a', 'c', 'd'], ['a-id', 'c-id', 'd-id'])
 
151
        tree.commit('initial', rev_id='rev-1')
 
152
        root_id = tree.get_root_id()
 
153
        self.assertRaises(errors.BzrMoveFailedError,
 
154
                          tree.move, ['c', 'b', 'd'], 'a')
 
155
        self.assertRaises(errors.BzrMoveFailedError,
 
156
                          tree.move, ['b', 'c', 'd'], 'a')
 
157
        self.assertRaises(errors.BzrMoveFailedError,
 
158
                          tree.move, ['d', 'c', 'b'], 'a')
 
159
        if osutils.lexists('a/c'):
 
160
            # If 'c' was actually moved, then 'd' should have also been moved
 
161
            self.assertTreeLayout([('', root_id), ('a', 'a-id'),
 
162
                                   ('a/c', 'c-id'),  ('a/d', 'd-id')], tree)
 
163
        else:
 
164
            self.assertTreeLayout([('', root_id), ('a', 'a-id'), ('c', 'c-id'),
 
165
                                   ('d', 'd-id')], tree)
 
166
        self.assertTreeLayout([('', root_id), ('a', 'a-id'), ('c', 'c-id'),
 
167
                               ('d', 'd-id')], tree.basis_tree())
 
168
        tree._validate()
 
169
 
 
170
    def test_move_over_deleted(self):
 
171
        tree = self.make_branch_and_tree('.')
 
172
        self.build_tree(['a/', 'a/b', 'b'])
 
173
        tree.add(['a', 'a/b', 'b'], ['a-id', 'ab-id', 'b-id'])
 
174
        tree.commit('initial', rev_id='rev-1')
 
175
 
 
176
        root_id = tree.get_root_id()
 
177
        tree.remove(['a/b'], keep_files=False)
 
178
        self.assertEqual([('b', 'a/b')], tree.move(['b'], 'a'))
 
179
        self.assertTreeLayout([('', root_id),
 
180
                               ('a', 'a-id'),
 
181
                               ('a/b', 'b-id'),
 
182
                              ], tree)
 
183
        tree._validate()
 
184
 
 
185
    def test_move_subdir(self):
 
186
        tree = self.make_branch_and_tree('.')
 
187
        self.build_tree(['a', 'b/', 'b/c'])
 
188
        tree.add(['a', 'b', 'b/c'], ['a-id', 'b-id', 'c-id'])
 
189
        tree.commit('initial', rev_id='rev-1')
 
190
        root_id = tree.get_root_id()
 
191
        self.assertTreeLayout([('', root_id), ('a', 'a-id'), ('b', 'b-id'),
 
192
                               ('b/c', 'c-id')], tree)
 
193
        self.assertTreeLayout([('', root_id), ('a', 'a-id'), ('b', 'b-id'),
 
194
                               ('b/c', 'c-id')], tree.basis_tree())
 
195
        a_contents = tree.get_file_text('a-id')
 
196
        self.assertEqual([('a', 'b/a')],
 
197
            tree.move(['a'], 'b'))
 
198
        self.assertTreeLayout([('', root_id), ('b', 'b-id'), ('b/a', 'a-id'),
 
199
                               ('b/c', 'c-id')], tree)
 
200
        self.assertTreeLayout([('', root_id), ('a', 'a-id'), ('b', 'b-id'),
 
201
                               ('b/c', 'c-id')], tree.basis_tree())
 
202
        self.failIfExists('a')
 
203
        self.assertFileEqual(a_contents, 'b/a')
 
204
        tree._validate()
 
205
 
 
206
    def test_move_parent_dir(self):
 
207
        tree = self.make_branch_and_tree('.')
 
208
        self.build_tree(['a', 'b/', 'b/c'])
 
209
        tree.add(['a', 'b', 'b/c'], ['a-id', 'b-id', 'c-id'])
 
210
        tree.commit('initial', rev_id='rev-1')
 
211
        root_id = tree.get_root_id()
 
212
        c_contents = tree.get_file_text('c-id')
 
213
        self.assertEqual([('b/c', 'c')],
 
214
            tree.move(['b/c'], ''))
 
215
        self.assertTreeLayout([('', root_id), ('a', 'a-id'), ('b', 'b-id'),
 
216
                               ('c', 'c-id')], tree)
 
217
        self.assertTreeLayout([('', root_id), ('a', 'a-id'), ('b', 'b-id'),
 
218
                               ('b/c', 'c-id')], tree.basis_tree())
 
219
        self.failIfExists('b/c')
 
220
        self.assertFileEqual(c_contents, 'c')
 
221
        tree._validate()
 
222
 
 
223
    def test_move_fail_consistent(self):
 
224
        tree = self.make_branch_and_tree('.')
 
225
        self.build_tree(['a', 'b/', 'b/a', 'c'])
 
226
        tree.add(['a', 'b', 'c'], ['a-id', 'b-id', 'c-id'])
 
227
        tree.commit('initial', rev_id='rev-1')
 
228
        root_id = tree.get_root_id()
 
229
        # Target already exists
 
230
        self.assertRaises(errors.RenameFailedFilesExist,
 
231
                          tree.move, ['c', 'a'], 'b')
 
232
        # 'c' may or may not have been moved, but either way the tree should
 
233
        # maintain a consistent state.
 
234
        if osutils.lexists('c'):
 
235
            self.assertTreeLayout([('', root_id), ('a', 'a-id'), ('b', 'b-id'),
 
236
                                   ('c', 'c-id')], tree)
 
237
        else:
 
238
            self.failUnlessExists('b/c')
 
239
            self.assertTreeLayout([('', root_id), ('a', 'a-id'), ('b', 'b-id'),
 
240
                                   ('b/c', 'c-id')], tree)
 
241
        self.assertTreeLayout([('', root_id), ('a', 'a-id'), ('b', 'b-id'),
 
242
                               ('c', 'c-id')], tree.basis_tree())
 
243
        tree._validate()
 
244
 
 
245
    def test_move_onto_self(self):
 
246
        tree = self.make_branch_and_tree('.')
 
247
        self.build_tree(['b/', 'b/a'])
 
248
        tree.add(['b', 'b/a'], ['b-id', 'a-id'])
 
249
        tree.commit('initial', rev_id='rev-1')
 
250
 
 
251
        self.assertRaises(errors.BzrMoveFailedError,
 
252
                          tree.move, ['b/a'], 'b')
 
253
        tree._validate()
 
254
 
 
255
    def test_move_onto_self_root(self):
 
256
        tree = self.make_branch_and_tree('.')
 
257
        self.build_tree(['a'])
 
258
        tree.add(['a'], ['a-id'])
 
259
        tree.commit('initial', rev_id='rev-1')
 
260
 
 
261
        self.assertRaises(errors.BzrMoveFailedError,
 
262
                          tree.move, ['a'], 'a')
 
263
        tree._validate()
 
264
 
 
265
    def test_move_after(self):
 
266
        tree = self.make_branch_and_tree('.')
 
267
        self.build_tree(['a', 'b/'])
 
268
        tree.add(['a', 'b'], ['a-id', 'b-id'])
 
269
        tree.commit('initial', rev_id='rev-1')
 
270
        root_id = tree.get_root_id()
 
271
        os.rename('a', 'b/a')
 
272
 
 
273
        self.assertTreeLayout([('', root_id), ('a', 'a-id'), ('b', 'b-id')],
 
274
                              tree)
 
275
        # We don't need after=True as long as source is missing and target
 
276
        # exists.
 
277
        self.assertEqual([('a', 'b/a')],
 
278
            tree.move(['a'], 'b'))
 
279
        self.assertTreeLayout([('', root_id), ('b', 'b-id'), ('b/a', 'a-id')],
 
280
                              tree)
 
281
        self.assertTreeLayout([('', root_id), ('a', 'a-id'), ('b', 'b-id')],
 
282
                              tree.basis_tree())
 
283
        tree._validate()
 
284
 
 
285
    def test_move_after_with_after(self):
 
286
        tree = self.make_branch_and_tree('.')
 
287
        self.build_tree(['a', 'b/'])
 
288
        tree.add(['a', 'b'], ['a-id', 'b-id'])
 
289
        tree.commit('initial', rev_id='rev-1')
 
290
        root_id = tree.get_root_id()
 
291
        os.rename('a', 'b/a')
 
292
 
 
293
        self.assertTreeLayout([('', root_id), ('a', 'a-id'), ('b', 'b-id')],
 
294
                              tree)
 
295
        # Passing after=True should work as well
 
296
        self.assertEqual([('a', 'b/a')],
 
297
            tree.move(['a'], 'b', after=True))
 
298
        self.assertTreeLayout([('', root_id), ('b', 'b-id'), ('b/a', 'a-id')],
 
299
                              tree)
 
300
        self.assertTreeLayout([('', root_id), ('a', 'a-id'), ('b', 'b-id')],
 
301
                              tree.basis_tree())
 
302
        tree._validate()
 
303
 
 
304
    def test_move_after_no_target(self):
 
305
        tree = self.make_branch_and_tree('.')
 
306
        self.build_tree(['a', 'b/'])
 
307
        tree.add(['a', 'b'], ['a-id', 'b-id'])
 
308
        tree.commit('initial', rev_id='rev-1')
 
309
        root_id = tree.get_root_id()
 
310
 
 
311
        # Passing after when the file hasn't been move raises an exception
 
312
        self.assertRaises(errors.BzrMoveFailedError,
 
313
                          tree.move, ['a'], 'b', after=True)
 
314
        self.assertTreeLayout([('', root_id), ('a', 'a-id'), ('b', 'b-id')],
 
315
                              tree.basis_tree())
 
316
        tree._validate()
 
317
 
 
318
    def test_move_after_source_and_dest(self):
 
319
        tree = self.make_branch_and_tree('.')
 
320
        self.build_tree(['a', 'b/', 'b/a'])
 
321
        tree.add(['a', 'b'], ['a-id', 'b-id'])
 
322
        tree.commit('initial', rev_id='rev-1')
 
323
        root_id = tree.get_root_id()
 
324
 
 
325
        # TODO: jam 20070225 I would usually use 'rb', but assertFileEqual
 
326
        #       uses 'r'.
 
327
        a_file = open('a', 'r')
 
328
        try:
 
329
            a_text = a_file.read()
 
330
        finally:
 
331
            a_file.close()
 
332
        ba_file = open('b/a', 'r')
 
333
        try:
 
334
            ba_text = ba_file.read()
 
335
        finally:
 
336
            ba_file.close()
 
337
 
 
338
        self.assertTreeLayout([('', root_id), ('a', 'a-id'), ('b', 'b-id')],
 
339
                              tree)
 
340
        self.assertRaises(errors.RenameFailedFilesExist,
 
341
                          tree.move, ['a'], 'b', after=False)
 
342
        self.assertTreeLayout([('', root_id), ('a', 'a-id'), ('b', 'b-id')],
 
343
                              tree)
 
344
        self.assertFileEqual(a_text, 'a')
 
345
        self.assertFileEqual(ba_text, 'b/a')
 
346
        # But you can pass after=True
 
347
        self.assertEqual([('a', 'b/a')],
 
348
            tree.move(['a'], 'b', after=True))
 
349
        self.assertTreeLayout([('', root_id), ('b', 'b-id'), ('b/a', 'a-id')],
 
350
                              tree)
 
351
        self.assertTreeLayout([('', root_id), ('a', 'a-id'), ('b', 'b-id')],
 
352
                              tree.basis_tree())
 
353
        # But it shouldn't actually move anything
 
354
        self.assertFileEqual(a_text, 'a')
 
355
        self.assertFileEqual(ba_text, 'b/a')
 
356
        tree._validate()
 
357
 
 
358
    def test_move_directory(self):
 
359
        tree = self.make_branch_and_tree('.')
 
360
        self.build_tree(['a/', 'a/b', 'a/c/', 'a/c/d', 'e/'])
 
361
        tree.add(['a', 'a/b', 'a/c', 'a/c/d', 'e'],
 
362
                 ['a-id', 'b-id', 'c-id', 'd-id', 'e-id'])
 
363
        tree.commit('initial', rev_id='rev-1')
 
364
        root_id = tree.get_root_id()
 
365
 
 
366
        self.assertEqual([('a', 'e/a')],
 
367
            tree.move(['a'], 'e'))
 
368
        self.assertTreeLayout([('', root_id), ('e', 'e-id'), ('e/a', 'a-id'),
 
369
                               ('e/a/b', 'b-id'), ('e/a/c', 'c-id'),
 
370
                               ('e/a/c/d', 'd-id')], tree)
 
371
        self.assertTreeLayout([('', root_id), ('a', 'a-id'), ('e', 'e-id'),
 
372
                               ('a/b', 'b-id'), ('a/c', 'c-id'),
 
373
                               ('a/c/d', 'd-id')], tree.basis_tree())
 
374
        tree._validate()
 
375
 
 
376
    def test_move_directory_into_parent(self):
 
377
        tree = self.make_branch_and_tree('.')
 
378
        self.build_tree(['c/', 'c/b/', 'c/b/d/'])
 
379
        tree.add(['c', 'c/b', 'c/b/d'],
 
380
                 ['c-id', 'b-id', 'd-id'])
 
381
        tree.commit('initial', rev_id='rev-1')
 
382
        root_id = tree.get_root_id()
 
383
 
 
384
        self.assertEqual([('c/b', 'b')],
 
385
                         tree.move(['c/b'], ''))
 
386
        self.assertTreeLayout([('', root_id),
 
387
                               ('b', 'b-id'),
 
388
                               ('c', 'c-id'),
 
389
                               ('b/d', 'd-id'),
 
390
                              ], tree)
 
391
        tree._validate()
 
392
 
 
393
    def test_move_directory_with_children_in_subdir(self):
 
394
        tree = self.make_branch_and_tree('.')
 
395
        self.build_tree(['a/', 'a/b', 'a/c/', 'd/'])
 
396
        tree.add(['a', 'a/b', 'a/c', 'd'],
 
397
                 ['a-id', 'b-id', 'c-id', 'd-id'])
 
398
        tree.commit('initial', rev_id='rev-1')
 
399
        root_id = tree.get_root_id()
 
400
 
 
401
 
 
402
        tree.rename_one('a/b', 'a/c/b')
 
403
        self.assertTreeLayout([('', root_id),
 
404
                               ('a', 'a-id'),
 
405
                               ('d', 'd-id'),
 
406
                               ('a/c', 'c-id'),
 
407
                               ('a/c/b', 'b-id'),
 
408
                              ], tree)
 
409
        self.assertEqual([('a', 'd/a')],
 
410
                         tree.move(['a'], 'd'))
 
411
        self.assertTreeLayout([('', root_id),
 
412
                               ('d', 'd-id'),
 
413
                               ('d/a', 'a-id'),
 
414
                               ('d/a/c', 'c-id'),
 
415
                               ('d/a/c/b', 'b-id'),
 
416
                              ], tree)
 
417
        tree._validate()
 
418
 
 
419
    def test_move_directory_with_deleted_children(self):
 
420
        tree = self.make_branch_and_tree('.')
 
421
        self.build_tree(['a/', 'a/b', 'a/c', 'a/d', 'b/'])
 
422
        tree.add(['a', 'b', 'a/b', 'a/c', 'a/d'],
 
423
                 ['a-id', 'b-id', 'ab-id', 'ac-id', 'ad-id'])
 
424
        tree.commit('initial', rev_id='rev-1')
 
425
        root_id = tree.get_root_id()
 
426
 
 
427
        tree.remove(['a/b', 'a/d'])
 
428
 
 
429
        self.assertEqual([('a', 'b/a')],
 
430
                         tree.move(['a'], 'b'))
 
431
        self.assertTreeLayout([('', root_id),
 
432
                               ('b', 'b-id'),
 
433
                               ('b/a', 'a-id'),
 
434
                               ('b/a/c', 'ac-id'),
 
435
                              ], tree)
 
436
        tree._validate()
 
437
 
 
438
    def test_move_directory_with_new_children(self):
 
439
        tree = self.make_branch_and_tree('.')
 
440
        self.build_tree(['a/', 'a/c', 'b/'])
 
441
        tree.add(['a', 'b', 'a/c'], ['a-id', 'b-id', 'ac-id'])
 
442
        tree.commit('initial', rev_id='rev-1')
 
443
        root_id = tree.get_root_id()
 
444
 
 
445
        self.build_tree(['a/b', 'a/d'])
 
446
        tree.add(['a/b', 'a/d'], ['ab-id', 'ad-id'])
 
447
 
 
448
        self.assertEqual([('a', 'b/a')],
 
449
                         tree.move(['a'], 'b'))
 
450
        self.assertTreeLayout([('', root_id),
 
451
                               ('b', 'b-id'),
 
452
                               ('b/a', 'a-id'),
 
453
                               ('b/a/b', 'ab-id'),
 
454
                               ('b/a/c', 'ac-id'),
 
455
                               ('b/a/d', 'ad-id'),
 
456
                              ], tree)
 
457
        tree._validate()
 
458
 
 
459
    def test_move_directory_with_moved_children(self):
 
460
        tree = self.make_branch_and_tree('.')
 
461
        self.build_tree(['a/', 'a/b', 'a/c', 'd', 'e/'])
 
462
        tree.add(['a', 'a/b', 'a/c', 'd', 'e'],
 
463
                 ['a-id', 'b-id', 'c-id', 'd-id', 'e-id'])
 
464
        tree.commit('initial', rev_id='rev-1')
 
465
        root_id = tree.get_root_id()
 
466
 
 
467
        self.assertEqual([('a/b', 'b')],
 
468
                         tree.move(['a/b'], ''))
 
469
        self.assertTreeLayout([('', root_id),
 
470
                               ('a', 'a-id'),
 
471
                               ('b', 'b-id'),
 
472
                               ('d', 'd-id'),
 
473
                               ('e', 'e-id'),
 
474
                               ('a/c', 'c-id'),
 
475
                              ], tree)
 
476
        self.assertEqual([('d', 'a/d')],
 
477
                         tree.move(['d'], 'a'))
 
478
        self.assertTreeLayout([('', root_id),
 
479
                               ('a', 'a-id'),
 
480
                               ('b', 'b-id'),
 
481
                               ('e', 'e-id'),
 
482
                               ('a/c', 'c-id'),
 
483
                               ('a/d', 'd-id'),
 
484
                              ], tree)
 
485
        self.assertEqual([('a', 'e/a')],
 
486
                         tree.move(['a'], 'e'))
 
487
        self.assertTreeLayout([('', root_id),
 
488
                               ('b', 'b-id'),
 
489
                               ('e', 'e-id'),
 
490
                               ('e/a', 'a-id'),
 
491
                               ('e/a/c', 'c-id'),
 
492
                               ('e/a/d', 'd-id'),
 
493
                              ], tree)
 
494
        tree._validate()
 
495
 
 
496
    def test_move_directory_with_renamed_child(self):
 
497
        tree = self.make_branch_and_tree('.')
 
498
        self.build_tree(['a/', 'a/b', 'a/c', 'd/'])
 
499
        tree.add(['a', 'a/b', 'a/c', 'd'],
 
500
                 ['a-id', 'b-id', 'c-id', 'd-id'])
 
501
        tree.commit('initial', rev_id='rev-1')
 
502
        root_id = tree.get_root_id()
 
503
 
 
504
        tree.rename_one('a/b', 'a/d')
 
505
        self.assertTreeLayout([('', root_id),
 
506
                               ('a', 'a-id'),
 
507
                               ('d', 'd-id'),
 
508
                               ('a/c', 'c-id'),
 
509
                               ('a/d', 'b-id'),
 
510
                              ], tree)
 
511
        self.assertEqual([('a', 'd/a')],
 
512
                         tree.move(['a'], 'd'))
 
513
        self.assertTreeLayout([('', root_id),
 
514
                               ('d', 'd-id'),
 
515
                               ('d/a', 'a-id'),
 
516
                               ('d/a/c', 'c-id'),
 
517
                               ('d/a/d', 'b-id'),
 
518
                              ], tree)
 
519
        tree._validate()
 
520
 
 
521
    def test_move_directory_with_swapped_children(self):
 
522
        tree = self.make_branch_and_tree('.')
 
523
        self.build_tree(['a/', 'a/b', 'a/c', 'a/d', 'e/'])
 
524
        tree.add(['a', 'a/b', 'a/c', 'a/d', 'e'],
 
525
                 ['a-id', 'b-id', 'c-id', 'd-id', 'e-id'])
 
526
        tree.commit('initial', rev_id='rev-1')
 
527
        root_id = tree.get_root_id()
 
528
 
 
529
        tree.rename_one('a/b', 'a/bb')
 
530
        tree.rename_one('a/d', 'a/b')
 
531
        tree.rename_one('a/bb', 'a/d')
 
532
        self.assertTreeLayout([('', root_id),
 
533
                               ('a', 'a-id'),
 
534
                               ('e', 'e-id'),
 
535
                               ('a/b', 'd-id'),
 
536
                               ('a/c', 'c-id'),
 
537
                               ('a/d', 'b-id'),
 
538
                              ], tree)
 
539
        self.assertEqual([('a', 'e/a')],
 
540
                         tree.move(['a'], 'e'))
 
541
        self.assertTreeLayout([('', root_id),
 
542
                               ('e', 'e-id'),
 
543
                               ('e/a', 'a-id'),
 
544
                               ('e/a/b', 'd-id'),
 
545
                               ('e/a/c', 'c-id'),
 
546
                               ('e/a/d', 'b-id'),
 
547
                              ], tree)
 
548
        tree._validate()
 
549
 
 
550
    def test_move_moved(self):
 
551
        """Moving a moved entry works as expected."""
 
552
        tree = self.make_branch_and_tree('.')
 
553
        self.build_tree(['a/', 'a/b', 'c/'])
 
554
        tree.add(['a', 'a/b', 'c'], ['a-id', 'b-id', 'c-id'])
 
555
        tree.commit('initial', rev_id='rev-1')
 
556
        root_id = tree.get_root_id()
 
557
 
 
558
        self.assertEqual([('a/b', 'c/b')],
 
559
            tree.move(['a/b'], 'c'))
 
560
        self.assertTreeLayout([('', root_id), ('a', 'a-id'), ('c', 'c-id'),
 
561
                               ('c/b', 'b-id')], tree)
 
562
        self.assertTreeLayout([('', root_id), ('a', 'a-id'), ('c', 'c-id'),
 
563
                               ('a/b', 'b-id')], tree.basis_tree())
 
564
 
 
565
        self.assertEqual([('c/b', 'b')],
 
566
            tree.move(['c/b'], ''))
 
567
        self.assertTreeLayout([('', root_id), ('a', 'a-id'), ('b', 'b-id'),
 
568
                               ('c', 'c-id')], tree)
 
569
        self.assertTreeLayout([('', root_id), ('a', 'a-id'), ('c', 'c-id'),
 
570
                               ('a/b', 'b-id')], tree.basis_tree())
 
571
        tree._validate()