/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/blackbox/test_pull.py

  • Committer: Canonical.com Patch Queue Manager
  • Date: 2010-05-27 01:58:44 UTC
  • mfrom: (5193.4.24 gio-transport)
  • Revision ID: pqm@pqm.ubuntu.com-20100527015844-ya4jahnwjx5y8ej2
(lifeless) Add a gio based transport using gio+ as a prefix to get at the
 gio logic. (Mattias Eriksson)

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
 
# Copyright (C) 2005 by Canonical Ltd
2
 
# -*- coding: utf-8 -*-
3
 
 
 
1
# Copyright (C) 2005-2010 Canonical Ltd
 
2
#
4
3
# This program is free software; you can redistribute it and/or modify
5
4
# it under the terms of the GNU General Public License as published by
6
5
# the Free Software Foundation; either version 2 of the License, or
7
6
# (at your option) any later version.
8
 
 
 
7
#
9
8
# This program is distributed in the hope that it will be useful,
10
9
# but WITHOUT ANY WARRANTY; without even the implied warranty of
11
10
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12
11
# GNU General Public License for more details.
13
 
 
 
12
#
14
13
# You should have received a copy of the GNU General Public License
15
14
# along with this program; if not, write to the Free Software
16
 
# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
17
 
 
18
 
 
19
 
"""Black-box tests for bzr pull.
20
 
"""
 
15
# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
 
16
 
 
17
 
 
18
"""Black-box tests for bzr pull."""
21
19
 
22
20
import os
23
21
import sys
24
22
 
 
23
from bzrlib import (
 
24
    debug,
 
25
    remote,
 
26
    urlutils,
 
27
    )
 
28
 
25
29
from bzrlib.branch import Branch
26
 
from bzrlib.osutils import abspath
 
30
from bzrlib.directory_service import directories
 
31
from bzrlib.osutils import pathjoin
27
32
from bzrlib.tests.blackbox import ExternalBase
28
33
from bzrlib.uncommit import uncommit
 
34
from bzrlib.workingtree import WorkingTree
29
35
 
30
36
 
31
37
class TestPull(ExternalBase):
32
38
 
33
 
    def example_branch(test):
34
 
        test.runbzr('init')
35
 
        file('hello', 'wt').write('foo')
36
 
        test.runbzr('add hello')
37
 
        test.runbzr('commit -m setup hello')
38
 
        file('goodbye', 'wt').write('baz')
39
 
        test.runbzr('add goodbye')
40
 
        test.runbzr('commit -m setup goodbye')
 
39
    def example_branch(self, path='.'):
 
40
        tree = self.make_branch_and_tree(path)
 
41
        self.build_tree_contents([
 
42
            (pathjoin(path, 'hello'),   'foo'),
 
43
            (pathjoin(path, 'goodbye'), 'baz')])
 
44
        tree.add('hello')
 
45
        tree.commit(message='setup')
 
46
        tree.add('goodbye')
 
47
        tree.commit(message='setup')
 
48
        return tree
41
49
 
42
50
    def test_pull(self):
43
51
        """Pull changes from one branch to another."""
44
 
        os.mkdir('a')
 
52
        a_tree = self.example_branch('a')
45
53
        os.chdir('a')
46
 
 
47
 
        self.example_branch()
48
 
        self.runbzr('pull', retcode=3)
49
 
        self.runbzr('missing', retcode=3)
50
 
        self.runbzr('missing .')
51
 
        self.runbzr('missing')
52
 
        if sys.platform not in ('win32', 'cygwin'):
53
 
            # This is equivalent to doing "bzr pull ."
54
 
            # Which means that bzr creates 2 branches grabbing
55
 
            # the same location, and tries to pull.
56
 
            # However, 2 branches mean 2 locks on the same file
57
 
            # which ultimately implies a deadlock.
58
 
            # (non windows platforms allow multiple locks on the
59
 
            # same file by the same calling process)
60
 
            self.runbzr('pull')
61
 
        self.runbzr('pull /', retcode=3)
62
 
        if sys.platform not in ('win32', 'cygwin'):
63
 
            self.runbzr('pull')
 
54
        self.run_bzr('pull', retcode=3)
 
55
        self.run_bzr('missing', retcode=3)
 
56
        self.run_bzr('missing .')
 
57
        self.run_bzr('missing')
 
58
        # this will work on windows because we check for the same branch
 
59
        # in pull - if it fails, it is a regression
 
60
        self.run_bzr('pull')
 
61
        self.run_bzr('pull /', retcode=3)
 
62
        if sys.platform not in ('win32', 'cygwin'):
 
63
            self.run_bzr('pull')
64
64
 
65
65
        os.chdir('..')
66
 
        self.runbzr('branch a b')
 
66
        b_tree = a_tree.bzrdir.sprout('b').open_workingtree()
67
67
        os.chdir('b')
68
 
        self.runbzr('pull')
 
68
        self.run_bzr('pull')
69
69
        os.mkdir('subdir')
70
 
        self.runbzr('add subdir')
71
 
        self.runbzr('commit -m blah --unchanged')
72
 
        os.chdir('../a')
73
 
        a = Branch.open('.')
74
 
        b = Branch.open('../b')
75
 
        self.assertEquals(a.revision_history(), b.revision_history()[:-1])
76
 
        self.runbzr('pull ../b')
77
 
        self.assertEquals(a.revision_history(), b.revision_history())
78
 
        self.runbzr('commit -m blah2 --unchanged')
79
 
        os.chdir('../b')
80
 
        self.runbzr('commit -m blah3 --unchanged')
 
70
        b_tree.add('subdir')
 
71
        b_tree.commit(message='blah', allow_pointless=True)
 
72
 
 
73
        os.chdir('..')
 
74
        a = Branch.open('a')
 
75
        b = Branch.open('b')
 
76
        self.assertEqual(a.revision_history(), b.revision_history()[:-1])
 
77
 
 
78
        os.chdir('a')
 
79
        self.run_bzr('pull ../b')
 
80
        self.assertEqual(a.revision_history(), b.revision_history())
 
81
        a_tree.commit(message='blah2', allow_pointless=True)
 
82
        b_tree.commit(message='blah3', allow_pointless=True)
81
83
        # no overwrite
82
 
        self.runbzr('pull ../a', retcode=3)
 
84
        os.chdir('../b')
 
85
        self.run_bzr('pull ../a', retcode=3)
83
86
        os.chdir('..')
84
 
        self.runbzr('branch b overwriteme')
 
87
        b_tree.bzrdir.sprout('overwriteme')
85
88
        os.chdir('overwriteme')
86
 
        self.runbzr('pull --overwrite ../a')
 
89
        self.run_bzr('pull --overwrite ../a')
87
90
        overwritten = Branch.open('.')
88
91
        self.assertEqual(overwritten.revision_history(),
89
92
                         a.revision_history())
90
 
        os.chdir('../a')
91
 
        self.runbzr('merge ../b')
92
 
        self.runbzr('commit -m blah4 --unchanged')
 
93
        a_tree.merge_from_branch(b_tree.branch)
 
94
        a_tree.commit(message="blah4", allow_pointless=True)
93
95
        os.chdir('../b/subdir')
94
 
        self.runbzr('pull ../../a')
95
 
        self.assertEquals(a.revision_history()[-1], b.revision_history()[-1])
96
 
        self.runbzr('commit -m blah5 --unchanged')
97
 
        self.runbzr('commit -m blah6 --unchanged')
 
96
        self.run_bzr('pull ../../a')
 
97
        self.assertEqual(a.revision_history()[-1], b.revision_history()[-1])
 
98
        sub_tree = WorkingTree.open_containing('.')[0]
 
99
        sub_tree.commit(message="blah5", allow_pointless=True)
 
100
        sub_tree.commit(message="blah6", allow_pointless=True)
98
101
        os.chdir('..')
99
 
        self.runbzr('pull ../a')
 
102
        self.run_bzr('pull ../a')
100
103
        os.chdir('../a')
101
 
        self.runbzr('commit -m blah7 --unchanged')
102
 
        self.runbzr('merge ../b')
103
 
        self.runbzr('commit -m blah8 --unchanged')
104
 
        self.runbzr('pull ../b')
105
 
        self.runbzr('pull ../b')
 
104
        a_tree.commit(message="blah7", allow_pointless=True)
 
105
        a_tree.merge_from_branch(b_tree.branch)
 
106
        a_tree.commit(message="blah8", allow_pointless=True)
 
107
        self.run_bzr('pull ../b')
 
108
        self.run_bzr('pull ../b')
 
109
 
 
110
    def test_pull_dash_d(self):
 
111
        self.example_branch('a')
 
112
        self.make_branch_and_tree('b')
 
113
        self.make_branch_and_tree('c')
 
114
        # pull into that branch
 
115
        self.run_bzr('pull -d b a')
 
116
        # pull into a branch specified by a url
 
117
        c_url = urlutils.local_path_to_url('c')
 
118
        self.assertStartsWith(c_url, 'file://')
 
119
        self.run_bzr(['pull', '-d', c_url, 'a'])
106
120
 
107
121
    def test_pull_revision(self):
108
122
        """Pull some changes from one branch to another."""
109
 
        os.mkdir('a')
110
 
        os.chdir('a')
111
 
 
112
 
        self.example_branch()
113
 
        file('hello2', 'wt').write('foo')
114
 
        self.runbzr('add hello2')
115
 
        self.runbzr('commit -m setup hello2')
116
 
        file('goodbye2', 'wt').write('baz')
117
 
        self.runbzr('add goodbye2')
118
 
        self.runbzr('commit -m setup goodbye2')
119
 
 
120
 
        os.chdir('..')
121
 
        self.runbzr('branch -r 1 a b')
 
123
        a_tree = self.example_branch('a')
 
124
        self.build_tree_contents([
 
125
            ('a/hello2',   'foo'),
 
126
            ('a/goodbye2', 'baz')])
 
127
        a_tree.add('hello2')
 
128
        a_tree.commit(message="setup")
 
129
        a_tree.add('goodbye2')
 
130
        a_tree.commit(message="setup")
 
131
 
 
132
        b_tree = a_tree.bzrdir.sprout('b',
 
133
                   revision_id=a_tree.branch.get_rev_id(1)).open_workingtree()
122
134
        os.chdir('b')
123
 
        self.runbzr('pull -r 2')
 
135
        self.run_bzr('pull -r 2')
124
136
        a = Branch.open('../a')
125
137
        b = Branch.open('.')
126
 
        self.assertEquals(a.revno(),4)
127
 
        self.assertEquals(b.revno(),2)
128
 
        self.runbzr('pull -r 3')
129
 
        self.assertEquals(b.revno(),3)
130
 
        self.runbzr('pull -r 4')
131
 
        self.assertEquals(a.revision_history(), b.revision_history())
 
138
        self.assertEqual(a.revno(),4)
 
139
        self.assertEqual(b.revno(),2)
 
140
        self.run_bzr('pull -r 3')
 
141
        self.assertEqual(b.revno(),3)
 
142
        self.run_bzr('pull -r 4')
 
143
        self.assertEqual(a.revision_history(), b.revision_history())
132
144
 
133
145
 
134
146
    def test_overwrite_uptodate(self):
135
147
        # Make sure pull --overwrite overwrites
136
148
        # even if the target branch has merged
137
149
        # everything already.
138
 
        bzr = self.run_bzr
139
 
 
140
 
        def get_rh(expected_len):
141
 
            rh = self.capture('revision-history')
142
 
            # Make sure we don't have trailing empty revisions
143
 
            rh = rh.strip().split('\n')
144
 
            self.assertEqual(len(rh), expected_len)
145
 
            return rh
146
 
 
147
 
        os.mkdir('a')
148
 
        os.chdir('a')
149
 
        bzr('init')
150
 
        open('foo', 'wb').write('original\n')
151
 
        bzr('add', 'foo')
152
 
        bzr('commit', '-m', 'initial commit')
153
 
 
154
 
        os.chdir('..')
155
 
        bzr('branch', 'a', 'b')
156
 
 
157
 
        os.chdir('a')
158
 
        open('foo', 'wb').write('changed\n')
159
 
        bzr('commit', '-m', 'later change')
160
 
 
161
 
        open('foo', 'wb').write('another\n')
162
 
        bzr('commit', '-m', 'a third change')
163
 
 
164
 
        rev_history_a = get_rh(3)
165
 
 
166
 
        os.chdir('../b')
167
 
        bzr('merge', '../a')
168
 
        bzr('commit', '-m', 'merge')
169
 
 
170
 
        rev_history_b = get_rh(2)
171
 
 
172
 
        bzr('pull', '--overwrite', '../a')
173
 
        rev_history_b = get_rh(3)
 
150
        a_tree = self.make_branch_and_tree('a')
 
151
        self.build_tree_contents([('a/foo', 'original\n')])
 
152
        a_tree.add('foo')
 
153
        a_tree.commit(message='initial commit')
 
154
 
 
155
        b_tree = a_tree.bzrdir.sprout('b').open_workingtree()
 
156
 
 
157
        self.build_tree_contents([('a/foo', 'changed\n')])
 
158
        a_tree.commit(message='later change')
 
159
 
 
160
        self.build_tree_contents([('a/foo', 'a third change')])
 
161
        a_tree.commit(message='a third change')
 
162
 
 
163
        rev_history_a = a_tree.branch.revision_history()
 
164
        self.assertEqual(len(rev_history_a), 3)
 
165
 
 
166
        b_tree.merge_from_branch(a_tree.branch)
 
167
        b_tree.commit(message='merge')
 
168
 
 
169
        self.assertEqual(len(b_tree.branch.revision_history()), 2)
 
170
 
 
171
        os.chdir('b')
 
172
        self.run_bzr('pull --overwrite ../a')
 
173
        rev_history_b = b_tree.branch.revision_history()
 
174
        self.assertEqual(len(rev_history_b), 3)
174
175
 
175
176
        self.assertEqual(rev_history_b, rev_history_a)
176
177
 
177
178
    def test_overwrite_children(self):
178
179
        # Make sure pull --overwrite sets the revision-history
179
180
        # to be identical to the pull source, even if we have convergence
180
 
        bzr = self.run_bzr
181
 
 
182
 
        def get_rh(expected_len):
183
 
            rh = self.capture('revision-history')
184
 
            # Make sure we don't have trailing empty revisions
185
 
            rh = rh.strip().split('\n')
186
 
            self.assertEqual(len(rh), expected_len)
187
 
            return rh
188
 
 
189
 
        os.mkdir('a')
190
 
        os.chdir('a')
191
 
        bzr('init')
192
 
        open('foo', 'wb').write('original\n')
193
 
        bzr('add', 'foo')
194
 
        bzr('commit', '-m', 'initial commit')
195
 
 
196
 
        os.chdir('..')
197
 
        bzr('branch', 'a', 'b')
198
 
 
199
 
        os.chdir('a')
200
 
        open('foo', 'wb').write('changed\n')
201
 
        bzr('commit', '-m', 'later change')
202
 
 
203
 
        open('foo', 'wb').write('another\n')
204
 
        bzr('commit', '-m', 'a third change')
205
 
 
206
 
        rev_history_a = get_rh(3)
207
 
 
208
 
        os.chdir('../b')
209
 
        bzr('merge', '../a')
210
 
        bzr('commit', '-m', 'merge')
211
 
 
212
 
        rev_history_b = get_rh(2)
213
 
 
214
 
        os.chdir('../a')
215
 
        open('foo', 'wb').write('a fourth change\n')
216
 
        bzr('commit', '-m', 'a fourth change')
217
 
 
218
 
        rev_history_a = get_rh(4)
 
181
        a_tree = self.make_branch_and_tree('a')
 
182
        self.build_tree_contents([('a/foo', 'original\n')])
 
183
        a_tree.add('foo')
 
184
        a_tree.commit(message='initial commit')
 
185
 
 
186
        b_tree = a_tree.bzrdir.sprout('b').open_workingtree()
 
187
 
 
188
        self.build_tree_contents([('a/foo', 'changed\n')])
 
189
        a_tree.commit(message='later change')
 
190
 
 
191
        self.build_tree_contents([('a/foo', 'a third change')])
 
192
        a_tree.commit(message='a third change')
 
193
 
 
194
        self.assertEqual(len(a_tree.branch.revision_history()), 3)
 
195
 
 
196
        b_tree.merge_from_branch(a_tree.branch)
 
197
        b_tree.commit(message='merge')
 
198
 
 
199
        self.assertEqual(len(b_tree.branch.revision_history()), 2)
 
200
 
 
201
        self.build_tree_contents([('a/foo', 'a fourth change\n')])
 
202
        a_tree.commit(message='a fourth change')
 
203
 
 
204
        rev_history_a = a_tree.branch.revision_history()
 
205
        self.assertEqual(len(rev_history_a), 4)
219
206
 
220
207
        # With convergence, we could just pull over the
221
208
        # new change, but with --overwrite, we want to switch our history
222
 
        os.chdir('../b')
223
 
        bzr('pull', '--overwrite', '../a')
224
 
        rev_history_b = get_rh(4)
 
209
        os.chdir('b')
 
210
        self.run_bzr('pull --overwrite ../a')
 
211
        rev_history_b = b_tree.branch.revision_history()
 
212
        self.assertEqual(len(rev_history_b), 4)
225
213
 
226
214
        self.assertEqual(rev_history_b, rev_history_a)
227
215
 
233
221
        self.build_tree(['branch_a/a'])
234
222
        tree_a.add('a')
235
223
        tree_a.commit('commit a')
236
 
        branch_b = branch_a.bzrdir.sprout('branch_b').open_branch()
237
 
        tree_b = branch_b.bzrdir.open_workingtree()
238
 
        branch_c = branch_a.bzrdir.sprout('branch_c').open_branch()
239
 
        tree_c = branch_c.bzrdir.open_workingtree()
 
224
        tree_b = branch_a.bzrdir.sprout('branch_b').open_workingtree()
 
225
        branch_b = tree_b.branch
 
226
        tree_c = branch_a.bzrdir.sprout('branch_c').open_workingtree()
 
227
        branch_c = tree_c.branch
240
228
        self.build_tree(['branch_a/b'])
241
229
        tree_a.add('b')
242
230
        tree_a.commit('commit b')
246
234
        self.assertEqual(None, branch_b.get_parent())
247
235
        # test pull for failure without parent set
248
236
        os.chdir('branch_b')
249
 
        out = self.runbzr('pull', retcode=3)
250
 
        self.assertEquals(out,
 
237
        out = self.run_bzr('pull', retcode=3)
 
238
        self.assertEqual(out,
251
239
                ('','bzr: ERROR: No pull location known or specified.\n'))
252
240
        # test implicit --remember when no parent set, this pull conflicts
253
241
        self.build_tree(['d'])
254
242
        tree_b.add('d')
255
243
        tree_b.commit('commit d')
256
 
        out = self.runbzr('pull ../branch_a', retcode=3)
257
 
        self.assertEquals(out,
258
 
                ('','bzr: ERROR: These branches have diverged.  Try merge.\n'))
259
 
        self.assertEquals(abspath(branch_b.get_parent()), abspath(parent))
 
244
        out = self.run_bzr('pull ../branch_a', retcode=3)
 
245
        self.assertEqual(out,
 
246
                ('','bzr: ERROR: These branches have diverged.'
 
247
                    ' Use the missing command to see how.\n'
 
248
                    'Use the merge command to reconcile them.\n'))
 
249
        self.assertEqual(branch_b.get_parent(), parent)
260
250
        # test implicit --remember after resolving previous failure
261
251
        uncommit(branch=branch_b, tree=tree_b)
262
252
        transport.delete('branch_b/d')
263
 
        self.runbzr('pull')
264
 
        self.assertEquals(abspath(branch_b.get_parent()), abspath(parent))
 
253
        self.run_bzr('pull')
 
254
        self.assertEqual(branch_b.get_parent(), parent)
265
255
        # test explicit --remember
266
 
        self.runbzr('pull ../branch_c --remember')
267
 
        self.assertEquals(abspath(branch_b.get_parent()),
268
 
                          abspath(branch_c.bzrdir.root_transport.base))
 
256
        self.run_bzr('pull ../branch_c --remember')
 
257
        self.assertEqual(branch_b.get_parent(),
 
258
                          branch_c.bzrdir.root_transport.base)
 
259
 
 
260
    def test_pull_bundle(self):
 
261
        from bzrlib.testament import Testament
 
262
        # Build up 2 trees and prepare for a pull
 
263
        tree_a = self.make_branch_and_tree('branch_a')
 
264
        f = open('branch_a/a', 'wb')
 
265
        f.write('hello')
 
266
        f.close()
 
267
        tree_a.add('a')
 
268
        tree_a.commit('message')
 
269
 
 
270
        tree_b = tree_a.bzrdir.sprout('branch_b').open_workingtree()
 
271
 
 
272
        # Make a change to 'a' that 'b' can pull
 
273
        f = open('branch_a/a', 'wb')
 
274
        f.write('hey there')
 
275
        f.close()
 
276
        tree_a.commit('message')
 
277
 
 
278
        # Create the bundle for 'b' to pull
 
279
        os.chdir('branch_a')
 
280
        self.run_bzr('bundle ../branch_b -o ../bundle')
 
281
 
 
282
        os.chdir('../branch_b')
 
283
        out, err = self.run_bzr('pull ../bundle')
 
284
        self.assertEqual(out,
 
285
                         'Now on revision 2.\n')
 
286
        self.assertEqual(err,
 
287
                ' M  a\nAll changes applied successfully.\n')
 
288
 
 
289
        self.assertEqualDiff(tree_a.branch.revision_history(),
 
290
                             tree_b.branch.revision_history())
 
291
 
 
292
        testament_a = Testament.from_revision(tree_a.branch.repository,
 
293
                                              tree_a.get_parent_ids()[0])
 
294
        testament_b = Testament.from_revision(tree_b.branch.repository,
 
295
                                              tree_b.get_parent_ids()[0])
 
296
        self.assertEqualDiff(testament_a.as_text(),
 
297
                             testament_b.as_text())
 
298
 
 
299
        # it is legal to attempt to pull an already-merged bundle
 
300
        out, err = self.run_bzr('pull ../bundle')
 
301
        self.assertEqual(err, '')
 
302
        self.assertEqual(out, 'No revisions to pull.\n')
 
303
 
 
304
    def test_pull_verbose_no_files(self):
 
305
        """Pull --verbose should not list modified files"""
 
306
        tree_a = self.make_branch_and_tree('tree_a')
 
307
        self.build_tree(['tree_a/foo'])
 
308
        tree_a.add('foo')
 
309
        tree_a.commit('bar')
 
310
        tree_b = self.make_branch_and_tree('tree_b')
 
311
        out = self.run_bzr('pull --verbose -d tree_b tree_a')[0]
 
312
        self.assertContainsRe(out, 'bar')
 
313
        self.assertNotContainsRe(out, 'added:')
 
314
        self.assertNotContainsRe(out, 'foo')
 
315
 
 
316
    def test_pull_quiet(self):
 
317
        """Check that bzr pull --quiet does not print anything"""
 
318
        tree_a = self.make_branch_and_tree('tree_a')
 
319
        self.build_tree(['tree_a/foo'])
 
320
        tree_a.add('foo')
 
321
        revision_id = tree_a.commit('bar')
 
322
        tree_b = tree_a.bzrdir.sprout('tree_b').open_workingtree()
 
323
        out, err = self.run_bzr('pull --quiet -d tree_b')
 
324
        self.assertEqual(out, '')
 
325
        self.assertEqual(err, '')
 
326
        self.assertEqual(tree_b.last_revision(), revision_id)
 
327
        self.build_tree(['tree_a/moo'])
 
328
        tree_a.add('moo')
 
329
        revision_id = tree_a.commit('quack')
 
330
        out, err = self.run_bzr('pull --quiet -d tree_b')
 
331
        self.assertEqual(out, '')
 
332
        self.assertEqual(err, '')
 
333
        self.assertEqual(tree_b.last_revision(), revision_id)
 
334
 
 
335
    def test_pull_from_directory_service(self):
 
336
        source = self.make_branch_and_tree('source')
 
337
        source.commit('commit 1')
 
338
        target = source.bzrdir.sprout('target').open_workingtree()
 
339
        source_last = source.commit('commit 2')
 
340
        class FooService(object):
 
341
            """A directory service that always returns source"""
 
342
 
 
343
            def look_up(self, name, url):
 
344
                return 'source'
 
345
        directories.register('foo:', FooService, 'Testing directory service')
 
346
        self.addCleanup(directories.remove, 'foo:')
 
347
        self.run_bzr('pull foo:bar -d target')
 
348
        self.assertEqual(source_last, target.last_revision())
 
349
 
 
350
    def test_pull_verbose_defaults_to_long(self):
 
351
        tree = self.example_branch('source')
 
352
        target = self.make_branch_and_tree('target')
 
353
        out = self.run_bzr('pull -v source -d target')[0]
 
354
        self.assertContainsRe(out,
 
355
                              r'revno: 1\ncommitter: .*\nbranch nick: source')
 
356
        self.assertNotContainsRe(out, r'\n {4}1 .*\n {6}setup\n')
 
357
 
 
358
    def test_pull_verbose_uses_default_log(self):
 
359
        tree = self.example_branch('source')
 
360
        target = self.make_branch_and_tree('target')
 
361
        target_config = target.branch.get_config()
 
362
        target_config.set_user_option('log_format', 'short')
 
363
        out = self.run_bzr('pull -v source -d target')[0]
 
364
        self.assertContainsRe(out, r'\n {4}1 .*\n {6}setup\n')
 
365
        self.assertNotContainsRe(
 
366
            out, r'revno: 1\ncommitter: .*\nbranch nick: source')
 
367
 
 
368
    def test_pull_smart_stacked_streaming_acceptance(self):
 
369
        """'bzr pull -r 123' works on stacked, smart branches, even when the
 
370
        revision specified by the revno is only present in the fallback
 
371
        repository.
 
372
 
 
373
        See <https://launchpad.net/bugs/380314>
 
374
        """
 
375
        self.setup_smart_server_with_call_log()
 
376
        # Make a stacked-on branch with two commits so that the
 
377
        # revision-history can't be determined just by looking at the parent
 
378
        # field in the revision in the stacked repo.
 
379
        parent = self.make_branch_and_tree('parent', format='1.9')
 
380
        parent.commit(message='first commit')
 
381
        parent.commit(message='second commit')
 
382
        local = parent.bzrdir.sprout('local').open_workingtree()
 
383
        local.commit(message='local commit')
 
384
        local.branch.create_clone_on_transport(
 
385
            self.get_transport('stacked'), stacked_on=self.get_url('parent'))
 
386
        empty = self.make_branch_and_tree('empty', format='1.9')
 
387
        self.reset_smart_call_log()
 
388
        self.run_bzr(['pull', '-r', '1', self.get_url('stacked')],
 
389
            working_dir='empty')
 
390
        # This figure represent the amount of work to perform this use case. It
 
391
        # is entirely ok to reduce this number if a test fails due to rpc_count
 
392
        # being too low. If rpc_count increases, more network roundtrips have
 
393
        # become necessary for this use case. Please do not adjust this number
 
394
        # upwards without agreement from bzr's network support maintainers.
 
395
        self.assertLength(18, self.hpss_calls)
 
396
        remote = Branch.open('stacked')
 
397
        self.assertEndsWith(remote.get_stacked_on_url(), '/parent')
 
398
    
 
399
    def test_pull_cross_format_warning(self):
 
400
        """You get a warning for probably slow cross-format pulls.
 
401
        """
 
402
        # this is assumed to be going through InterDifferingSerializer
 
403
        from_tree = self.make_branch_and_tree('from', format='2a')
 
404
        to_tree = self.make_branch_and_tree('to', format='1.14-rich-root')
 
405
        from_tree.commit(message='first commit')
 
406
        out, err = self.run_bzr(['pull', '-d', 'to', 'from'])
 
407
        self.assertContainsRe(err,
 
408
            "(?m)Doing on-the-fly conversion")
 
409
 
 
410
    def test_pull_cross_format_warning_no_IDS(self):
 
411
        """You get a warning for probably slow cross-format pulls.
 
412
        """
 
413
        # this simulates what would happen across the network, where
 
414
        # interdifferingserializer is not active
 
415
 
 
416
        debug.debug_flags.add('IDS_never')
 
417
        # TestCase take care of restoring them
 
418
 
 
419
        from_tree = self.make_branch_and_tree('from', format='2a')
 
420
        to_tree = self.make_branch_and_tree('to', format='1.14-rich-root')
 
421
        from_tree.commit(message='first commit')
 
422
        out, err = self.run_bzr(['pull', '-d', 'to', 'from'])
 
423
        self.assertContainsRe(err,
 
424
            "(?m)Doing on-the-fly conversion")
 
425
 
 
426
    def test_pull_cross_format_from_network(self):
 
427
        self.setup_smart_server_with_call_log()
 
428
        from_tree = self.make_branch_and_tree('from', format='2a')
 
429
        to_tree = self.make_branch_and_tree('to', format='1.14-rich-root')
 
430
        self.assertIsInstance(from_tree.branch, remote.RemoteBranch)
 
431
        from_tree.commit(message='first commit')
 
432
        out, err = self.run_bzr(['pull', '-d', 'to',
 
433
            from_tree.branch.bzrdir.root_transport.base])
 
434
        self.assertContainsRe(err,
 
435
            "(?m)Doing on-the-fly conversion")
 
436
 
 
437
    def test_pull_to_experimental_format_warning(self):
 
438
        """You get a warning for pulling into experimental formats.
 
439
        """
 
440
        from_tree = self.make_branch_and_tree('from', format='development-subtree')
 
441
        to_tree = self.make_branch_and_tree('to', format='development-subtree')
 
442
        from_tree.commit(message='first commit')
 
443
        out, err = self.run_bzr(['pull', '-d', 'to', 'from'])
 
444
        self.assertContainsRe(err,
 
445
            "(?m)Fetching into experimental format")
 
446
 
 
447
    def test_pull_cross_to_experimental_format_warning(self):
 
448
        """You get a warning for pulling into experimental formats.
 
449
        """
 
450
        from_tree = self.make_branch_and_tree('from', format='2a')
 
451
        to_tree = self.make_branch_and_tree('to', format='development-subtree')
 
452
        from_tree.commit(message='first commit')
 
453
        out, err = self.run_bzr(['pull', '-d', 'to', 'from'])
 
454
        self.assertContainsRe(err,
 
455
            "(?m)Fetching into experimental format")