~bzr-pqm/bzr/bzr.dev

« back to all changes in this revision

Viewing changes to bzrlib/tests/blackbox/test_pull.py

merge merge tweaks from aaron, which includes latest .dev

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
 
# Copyright (C) 2005, 2006 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
 
 
18
 
"""Black-box tests for bzr pull."""
19
 
 
20
 
import os
21
 
import sys
22
 
 
23
 
from bzrlib.branch import Branch
24
 
from bzrlib.tests.blackbox import ExternalBase
25
 
from bzrlib.uncommit import uncommit
26
 
from bzrlib import urlutils
27
 
 
28
 
 
29
 
class TestPull(ExternalBase):
30
 
 
31
 
    def example_branch(test):
32
 
        test.runbzr('init')
33
 
        file('hello', 'wt').write('foo')
34
 
        test.runbzr('add hello')
35
 
        test.runbzr('commit -m setup hello')
36
 
        file('goodbye', 'wt').write('baz')
37
 
        test.runbzr('add goodbye')
38
 
        test.runbzr('commit -m setup goodbye')
39
 
 
40
 
    def test_pull(self):
41
 
        """Pull changes from one branch to another."""
42
 
        os.mkdir('a')
43
 
        os.chdir('a')
44
 
 
45
 
        self.example_branch()
46
 
        self.runbzr('pull', retcode=3)
47
 
        self.runbzr('missing', retcode=3)
48
 
        self.runbzr('missing .')
49
 
        self.runbzr('missing')
50
 
        # this will work on windows because we check for the same branch
51
 
        # in pull - if it fails, it is a regression
52
 
        self.runbzr('pull')
53
 
        self.runbzr('pull /', retcode=3)
54
 
        if sys.platform not in ('win32', 'cygwin'):
55
 
            self.runbzr('pull')
56
 
 
57
 
        os.chdir('..')
58
 
        self.runbzr('branch a b')
59
 
        os.chdir('b')
60
 
        self.runbzr('pull')
61
 
        os.mkdir('subdir')
62
 
        self.runbzr('add subdir')
63
 
        self.runbzr('commit -m blah --unchanged')
64
 
        os.chdir('../a')
65
 
        a = Branch.open('.')
66
 
        b = Branch.open('../b')
67
 
        self.assertEquals(a.revision_history(), b.revision_history()[:-1])
68
 
        self.runbzr('pull ../b')
69
 
        self.assertEquals(a.revision_history(), b.revision_history())
70
 
        self.runbzr('commit -m blah2 --unchanged')
71
 
        os.chdir('../b')
72
 
        self.runbzr('commit -m blah3 --unchanged')
73
 
        # no overwrite
74
 
        self.runbzr('pull ../a', retcode=3)
75
 
        os.chdir('..')
76
 
        self.runbzr('branch b overwriteme')
77
 
        os.chdir('overwriteme')
78
 
        self.runbzr('pull --overwrite ../a')
79
 
        overwritten = Branch.open('.')
80
 
        self.assertEqual(overwritten.revision_history(),
81
 
                         a.revision_history())
82
 
        os.chdir('../a')
83
 
        self.runbzr('merge ../b')
84
 
        self.runbzr('commit -m blah4 --unchanged')
85
 
        os.chdir('../b/subdir')
86
 
        self.runbzr('pull ../../a')
87
 
        self.assertEquals(a.revision_history()[-1], b.revision_history()[-1])
88
 
        self.runbzr('commit -m blah5 --unchanged')
89
 
        self.runbzr('commit -m blah6 --unchanged')
90
 
        os.chdir('..')
91
 
        self.runbzr('pull ../a')
92
 
        os.chdir('../a')
93
 
        self.runbzr('commit -m blah7 --unchanged')
94
 
        self.runbzr('merge ../b')
95
 
        self.runbzr('commit -m blah8 --unchanged')
96
 
        self.runbzr('pull ../b')
97
 
        self.runbzr('pull ../b')
98
 
 
99
 
    def test_pull_dash_d(self):
100
 
        os.mkdir('a')
101
 
        os.chdir('a')
102
 
        self.example_branch()
103
 
        self.runbzr('init ../b')
104
 
        self.runbzr('init ../c')
105
 
        # pull into that branch
106
 
        self.runbzr('pull -d ../b .')
107
 
        # pull into a branch specified by a url
108
 
        c_url = urlutils.local_path_to_url('../c')
109
 
        self.assertStartsWith(c_url, 'file://')
110
 
        self.runbzr('pull -d %s .' % c_url)
111
 
 
112
 
    def test_pull_revision(self):
113
 
        """Pull some changes from one branch to another."""
114
 
        os.mkdir('a')
115
 
        os.chdir('a')
116
 
 
117
 
        self.example_branch()
118
 
        file('hello2', 'wt').write('foo')
119
 
        self.runbzr('add hello2')
120
 
        self.runbzr('commit -m setup hello2')
121
 
        file('goodbye2', 'wt').write('baz')
122
 
        self.runbzr('add goodbye2')
123
 
        self.runbzr('commit -m setup goodbye2')
124
 
 
125
 
        os.chdir('..')
126
 
        self.runbzr('branch -r 1 a b')
127
 
        os.chdir('b')
128
 
        self.runbzr('pull -r 2')
129
 
        a = Branch.open('../a')
130
 
        b = Branch.open('.')
131
 
        self.assertEquals(a.revno(),4)
132
 
        self.assertEquals(b.revno(),2)
133
 
        self.runbzr('pull -r 3')
134
 
        self.assertEquals(b.revno(),3)
135
 
        self.runbzr('pull -r 4')
136
 
        self.assertEquals(a.revision_history(), b.revision_history())
137
 
 
138
 
 
139
 
    def test_overwrite_uptodate(self):
140
 
        # Make sure pull --overwrite overwrites
141
 
        # even if the target branch has merged
142
 
        # everything already.
143
 
        bzr = self.run_bzr
144
 
 
145
 
        def get_rh(expected_len):
146
 
            rh = self.capture('revision-history')
147
 
            # Make sure we don't have trailing empty revisions
148
 
            rh = rh.strip().split('\n')
149
 
            self.assertEqual(len(rh), expected_len)
150
 
            return rh
151
 
 
152
 
        os.mkdir('a')
153
 
        os.chdir('a')
154
 
        bzr('init')
155
 
        open('foo', 'wb').write('original\n')
156
 
        bzr('add', 'foo')
157
 
        bzr('commit', '-m', 'initial commit')
158
 
 
159
 
        os.chdir('..')
160
 
        bzr('branch', 'a', 'b')
161
 
 
162
 
        os.chdir('a')
163
 
        open('foo', 'wb').write('changed\n')
164
 
        bzr('commit', '-m', 'later change')
165
 
 
166
 
        open('foo', 'wb').write('another\n')
167
 
        bzr('commit', '-m', 'a third change')
168
 
 
169
 
        rev_history_a = get_rh(3)
170
 
 
171
 
        os.chdir('../b')
172
 
        bzr('merge', '../a')
173
 
        bzr('commit', '-m', 'merge')
174
 
 
175
 
        rev_history_b = get_rh(2)
176
 
 
177
 
        bzr('pull', '--overwrite', '../a')
178
 
        rev_history_b = get_rh(3)
179
 
 
180
 
        self.assertEqual(rev_history_b, rev_history_a)
181
 
 
182
 
    def test_overwrite_children(self):
183
 
        # Make sure pull --overwrite sets the revision-history
184
 
        # to be identical to the pull source, even if we have convergence
185
 
        bzr = self.run_bzr
186
 
 
187
 
        def get_rh(expected_len):
188
 
            rh = self.capture('revision-history')
189
 
            # Make sure we don't have trailing empty revisions
190
 
            rh = rh.strip().split('\n')
191
 
            self.assertEqual(len(rh), expected_len)
192
 
            return rh
193
 
 
194
 
        os.mkdir('a')
195
 
        os.chdir('a')
196
 
        bzr('init')
197
 
        open('foo', 'wb').write('original\n')
198
 
        bzr('add', 'foo')
199
 
        bzr('commit', '-m', 'initial commit')
200
 
 
201
 
        os.chdir('..')
202
 
        bzr('branch', 'a', 'b')
203
 
 
204
 
        os.chdir('a')
205
 
        open('foo', 'wb').write('changed\n')
206
 
        bzr('commit', '-m', 'later change')
207
 
 
208
 
        open('foo', 'wb').write('another\n')
209
 
        bzr('commit', '-m', 'a third change')
210
 
 
211
 
        rev_history_a = get_rh(3)
212
 
 
213
 
        os.chdir('../b')
214
 
        bzr('merge', '../a')
215
 
        bzr('commit', '-m', 'merge')
216
 
 
217
 
        rev_history_b = get_rh(2)
218
 
 
219
 
        os.chdir('../a')
220
 
        open('foo', 'wb').write('a fourth change\n')
221
 
        bzr('commit', '-m', 'a fourth change')
222
 
 
223
 
        rev_history_a = get_rh(4)
224
 
 
225
 
        # With convergence, we could just pull over the
226
 
        # new change, but with --overwrite, we want to switch our history
227
 
        os.chdir('../b')
228
 
        bzr('pull', '--overwrite', '../a')
229
 
        rev_history_b = get_rh(4)
230
 
 
231
 
        self.assertEqual(rev_history_b, rev_history_a)
232
 
 
233
 
    def test_pull_remember(self):
234
 
        """Pull changes from one branch to another and test parent location."""
235
 
        transport = self.get_transport()
236
 
        tree_a = self.make_branch_and_tree('branch_a')
237
 
        branch_a = tree_a.branch
238
 
        self.build_tree(['branch_a/a'])
239
 
        tree_a.add('a')
240
 
        tree_a.commit('commit a')
241
 
        tree_b = branch_a.bzrdir.sprout('branch_b').open_workingtree()
242
 
        branch_b = tree_b.branch
243
 
        tree_c = branch_a.bzrdir.sprout('branch_c').open_workingtree()
244
 
        branch_c = tree_c.branch
245
 
        self.build_tree(['branch_a/b'])
246
 
        tree_a.add('b')
247
 
        tree_a.commit('commit b')
248
 
        # reset parent
249
 
        parent = branch_b.get_parent()
250
 
        branch_b.set_parent(None)
251
 
        self.assertEqual(None, branch_b.get_parent())
252
 
        # test pull for failure without parent set
253
 
        os.chdir('branch_b')
254
 
        out = self.runbzr('pull', retcode=3)
255
 
        self.assertEquals(out,
256
 
                ('','bzr: ERROR: No pull location known or specified.\n'))
257
 
        # test implicit --remember when no parent set, this pull conflicts
258
 
        self.build_tree(['d'])
259
 
        tree_b.add('d')
260
 
        tree_b.commit('commit d')
261
 
        out = self.runbzr('pull ../branch_a', retcode=3)
262
 
        self.assertEquals(out,
263
 
                ('','bzr: ERROR: These branches have diverged.  Use the merge command to reconcile them.\n'))
264
 
        self.assertEquals(branch_b.get_parent(), parent)
265
 
        # test implicit --remember after resolving previous failure
266
 
        uncommit(branch=branch_b, tree=tree_b)
267
 
        transport.delete('branch_b/d')
268
 
        self.runbzr('pull')
269
 
        self.assertEquals(branch_b.get_parent(), parent)
270
 
        # test explicit --remember
271
 
        self.runbzr('pull ../branch_c --remember')
272
 
        self.assertEquals(branch_b.get_parent(),
273
 
                          branch_c.bzrdir.root_transport.base)
274
 
 
275
 
    def test_pull_bundle(self):
276
 
        from bzrlib.testament import Testament
277
 
        # Build up 2 trees and prepare for a pull
278
 
        tree_a = self.make_branch_and_tree('branch_a')
279
 
        f = open('branch_a/a', 'wb')
280
 
        f.write('hello')
281
 
        f.close()
282
 
        tree_a.add('a')
283
 
        tree_a.commit('message')
284
 
 
285
 
        tree_b = tree_a.bzrdir.sprout('branch_b').open_workingtree()
286
 
 
287
 
        # Make a change to 'a' that 'b' can pull
288
 
        f = open('branch_a/a', 'wb')
289
 
        f.write('hey there')
290
 
        f.close()
291
 
        tree_a.commit('message')
292
 
 
293
 
        # Create the bundle for 'b' to pull
294
 
        os.chdir('branch_a')
295
 
        bundle_file = open('../bundle', 'wb')
296
 
        bundle_file.write(self.run_bzr('bundle', '../branch_b')[0])
297
 
        bundle_file.close()
298
 
 
299
 
        os.chdir('../branch_b')
300
 
        out, err = self.run_bzr('pull', '../bundle')
301
 
        self.assertEqual(out,
302
 
                         'Now on revision 2.\n')
303
 
        self.assertEqual(err,
304
 
                ' M  a\nAll changes applied successfully.\n')
305
 
 
306
 
        self.assertEqualDiff(tree_a.branch.revision_history(),
307
 
                             tree_b.branch.revision_history())
308
 
 
309
 
        testament_a = Testament.from_revision(tree_a.branch.repository,
310
 
                                              tree_a.get_parent_ids()[0])
311
 
        testament_b = Testament.from_revision(tree_b.branch.repository,
312
 
                                              tree_b.get_parent_ids()[0])
313
 
        self.assertEqualDiff(testament_a.as_text(),
314
 
                             testament_b.as_text())
315
 
 
316
 
        # it is legal to attempt to pull an already-merged bundle
317
 
        out, err = self.run_bzr('pull', '../bundle')
318
 
        self.assertEqual(err, '')
319
 
        self.assertEqual(out, 'No revisions to pull.\n')