/brz/remove-bazaar

To get this branch, use:
bzr branch http://gegoxaren.bato24.eu/bzr/brz/remove-bazaar
5557.1.15 by John Arbash Meinel
Merge bzr.dev 5597 to resolve NEWS, aka bzr-2.3.txt
1
# Copyright (C) 2006-2011 Canonical Ltd
2018.6.1 by Robert Collins
Implement a BzrDir.open_branch smart server method for opening a branch without VFS.
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
4183.7.1 by Sabin Iacob
update FSF mailing address
15
# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
2018.6.1 by Robert Collins
Implement a BzrDir.open_branch smart server method for opening a branch without VFS.
16
2748.4.1 by Andrew Bennetts
Implement a ChunkedBodyDecoder.
17
"""Tests for the smart wire/domain protocol.
18
19
This module contains tests for the domain-level smart requests and responses,
3015.2.12 by Robert Collins
Make test_smart use specific formats as needed to exercise locked and unlocked repositories.
20
such as the 'Branch.lock_write' request. Many of these use specific disk
21
formats to exercise calls that only make sense for formats with specific
22
properties.
2748.4.1 by Andrew Bennetts
Implement a ChunkedBodyDecoder.
23
24
Tests for low-level protocol encoding are found in test_smart_transport.
25
"""
2018.6.1 by Robert Collins
Implement a BzrDir.open_branch smart server method for opening a branch without VFS.
26
3211.5.2 by Robert Collins
Change RemoteRepository.get_parent_map to use bz2 not gzip for compression.
27
import bz2
2018.18.2 by Martin Pool
smart method Repository.tarball actually returns the tarball
28
2692.1.2 by Andrew Bennetts
Merge from bzr.dev.
29
from bzrlib import (
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
30
    branch as _mod_branch,
2692.1.2 by Andrew Bennetts
Merge from bzr.dev.
31
    bzrdir,
32
    errors,
6265.1.1 by Jelmer Vernooij
Add new HPSS call ``Repository.has_signature_for_revision_id``.
33
    gpg,
2692.1.2 by Andrew Bennetts
Merge from bzr.dev.
34
    tests,
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
35
    transport,
2692.1.2 by Andrew Bennetts
Merge from bzr.dev.
36
    urlutils,
4634.19.1 by Robert Collins
Combine adjacent substreams of the same type in bzrlib.smart.repository._byte_stream_to_stream.
37
    versionedfile,
2692.1.2 by Andrew Bennetts
Merge from bzr.dev.
38
    )
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
39
from bzrlib.smart import (
40
    branch as smart_branch,
41
    bzrdir as smart_dir,
42
    repository as smart_repo,
43
    packrepository as smart_packrepo,
44
    request as smart_req,
5611.1.2 by Jelmer Vernooij
Add some tests for the hooks.
45
    server,
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
46
    vfs,
47
    )
5017.3.25 by Vincent Ladeuil
selftest -s bt.test_smart_transport passing
48
from bzrlib.tests import test_server
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
49
from bzrlib.transport import (
50
    chroot,
5017.3.45 by Vincent Ladeuil
Move MemoryServer back into bzrlib.transport.memory as it's needed as soon as a MemoryTransport is used. Add a NEWS entry.
51
    memory,
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
52
    )
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
53
54
3221.3.2 by Robert Collins
* New remote method ``RemoteBzrDir.find_repositoryV2`` adding support for
55
def load_tests(standard_tests, module, loader):
56
    """Multiply tests version and protocol consistency."""
57
    # FindRepository tests.
4084.5.1 by Robert Collins
Bulk update all test adaptation into a single approach, using multiply_tests rather than test adapters.
58
    scenarios = [
3221.3.2 by Robert Collins
* New remote method ``RemoteBzrDir.find_repositoryV2`` adding support for
59
        ("find_repository", {
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
60
            "_request_class": smart_dir.SmartServerRequestFindRepositoryV1}),
3221.3.2 by Robert Collins
* New remote method ``RemoteBzrDir.find_repositoryV2`` adding support for
61
        ("find_repositoryV2", {
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
62
            "_request_class": smart_dir.SmartServerRequestFindRepositoryV2}),
4053.1.4 by Robert Collins
Move the fetch control attributes from Repository to RepositoryFormat.
63
        ("find_repositoryV3", {
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
64
            "_request_class": smart_dir.SmartServerRequestFindRepositoryV3}),
3221.3.2 by Robert Collins
* New remote method ``RemoteBzrDir.find_repositoryV2`` adding support for
65
        ]
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
66
    to_adapt, result = tests.split_suite_by_re(standard_tests,
3221.3.2 by Robert Collins
* New remote method ``RemoteBzrDir.find_repositoryV2`` adding support for
67
        "TestSmartServerRequestFindRepository")
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
68
    v2_only, v1_and_2 = tests.split_suite_by_re(to_adapt,
3221.3.2 by Robert Collins
* New remote method ``RemoteBzrDir.find_repositoryV2`` adding support for
69
        "_v2")
4084.5.1 by Robert Collins
Bulk update all test adaptation into a single approach, using multiply_tests rather than test adapters.
70
    tests.multiply_tests(v1_and_2, scenarios, result)
71
    # The first scenario is only applicable to v1 protocols, it is deleted
72
    # since.
73
    tests.multiply_tests(v2_only, scenarios[1:], result)
3221.3.2 by Robert Collins
* New remote method ``RemoteBzrDir.find_repositoryV2`` adding support for
74
    return result
75
76
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
77
class TestCaseWithChrootedTransport(tests.TestCaseWithTransport):
78
79
    def setUp(self):
5017.3.45 by Vincent Ladeuil
Move MemoryServer back into bzrlib.transport.memory as it's needed as soon as a MemoryTransport is used. Add a NEWS entry.
80
        self.vfs_transport_factory = memory.MemoryServer
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
81
        tests.TestCaseWithTransport.setUp(self)
82
        self._chroot_server = None
83
84
    def get_transport(self, relpath=None):
85
        if self._chroot_server is None:
86
            backing_transport = tests.TestCaseWithTransport.get_transport(self)
87
            self._chroot_server = chroot.ChrootServer(backing_transport)
4659.1.2 by Robert Collins
Refactor creation and shutdown of test servers to use a common helper,
88
            self.start_server(self._chroot_server)
6083.1.1 by Jelmer Vernooij
Use get_transport_from_{url,path} in more places.
89
        t = transport.get_transport_from_url(self._chroot_server.get_url())
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
90
        if relpath is not None:
91
            t = t.clone(relpath)
92
        return t
2018.6.1 by Robert Collins
Implement a BzrDir.open_branch smart server method for opening a branch without VFS.
93
94
4634.47.4 by Andrew Bennetts
Make more of bzrlib/tests/test_smart.py use MemoryTransport.
95
class TestCaseWithSmartMedium(tests.TestCaseWithMemoryTransport):
2018.5.59 by Robert Collins
Get BranchConfig working somewhat on RemoteBranches (Robert Collins, Vincent Ladeuil).
96
97
    def setUp(self):
98
        super(TestCaseWithSmartMedium, self).setUp()
99
        # We're allowed to set  the transport class here, so that we don't use
100
        # the default or a parameterized class, but rather use the
101
        # TestCaseWithTransport infrastructure to set up a smart server and
102
        # transport.
5340.15.1 by John Arbash Meinel
supersede exc-info branch
103
        self.overrideAttr(self, "transport_server", self.make_transport_server)
3245.4.28 by Andrew Bennetts
Remove another XXX, and include test ID in smart server thread names.
104
105
    def make_transport_server(self):
5017.3.25 by Vincent Ladeuil
selftest -s bt.test_smart_transport passing
106
        return test_server.SmartTCPServer_for_testing('-' + self.id())
2018.5.59 by Robert Collins
Get BranchConfig working somewhat on RemoteBranches (Robert Collins, Vincent Ladeuil).
107
108
    def get_smart_medium(self):
109
        """Get a smart medium to use in tests."""
110
        return self.get_transport().get_smart_medium()
111
112
4634.19.1 by Robert Collins
Combine adjacent substreams of the same type in bzrlib.smart.repository._byte_stream_to_stream.
113
class TestByteStreamToStream(tests.TestCase):
114
115
    def test_repeated_substreams_same_kind_are_one_stream(self):
116
        # Make a stream - an iterable of bytestrings.
117
        stream = [('text', [versionedfile.FulltextContentFactory(('k1',), None,
118
            None, 'foo')]),('text', [
119
            versionedfile.FulltextContentFactory(('k2',), None, None, 'bar')])]
120
        fmt = bzrdir.format_registry.get('pack-0.92')().repository_format
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
121
        bytes = smart_repo._stream_to_byte_stream(stream, fmt)
4634.19.1 by Robert Collins
Combine adjacent substreams of the same type in bzrlib.smart.repository._byte_stream_to_stream.
122
        streams = []
123
        # Iterate the resulting iterable; checking that we get only one stream
124
        # out.
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
125
        fmt, stream = smart_repo._byte_stream_to_stream(bytes)
4634.19.1 by Robert Collins
Combine adjacent substreams of the same type in bzrlib.smart.repository._byte_stream_to_stream.
126
        for kind, substream in stream:
127
            streams.append((kind, list(substream)))
128
        self.assertLength(1, streams)
129
        self.assertLength(2, streams[0][1])
130
131
2018.6.1 by Robert Collins
Implement a BzrDir.open_branch smart server method for opening a branch without VFS.
132
class TestSmartServerResponse(tests.TestCase):
133
134
    def test__eq__(self):
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
135
        self.assertEqual(smart_req.SmartServerResponse(('ok', )),
136
            smart_req.SmartServerResponse(('ok', )))
137
        self.assertEqual(smart_req.SmartServerResponse(('ok', ), 'body'),
138
            smart_req.SmartServerResponse(('ok', ), 'body'))
139
        self.assertNotEqual(smart_req.SmartServerResponse(('ok', )),
140
            smart_req.SmartServerResponse(('notok', )))
141
        self.assertNotEqual(smart_req.SmartServerResponse(('ok', ), 'body'),
142
            smart_req.SmartServerResponse(('ok', )))
2018.5.41 by Robert Collins
Fix SmartServerResponse.__eq__ to handle None.
143
        self.assertNotEqual(None,
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
144
            smart_req.SmartServerResponse(('ok', )))
2018.6.1 by Robert Collins
Implement a BzrDir.open_branch smart server method for opening a branch without VFS.
145
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
146
    def test__str__(self):
147
        """SmartServerResponses can be stringified."""
148
        self.assertEqual(
3691.2.6 by Martin Pool
Disable RemoteBranch stacking, but get get_stacked_on_url working, and passing back exceptions
149
            "<SuccessfulSmartServerResponse args=('args',) body='body'>",
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
150
            str(smart_req.SuccessfulSmartServerResponse(('args',), 'body')))
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
151
        self.assertEqual(
3691.2.6 by Martin Pool
Disable RemoteBranch stacking, but get get_stacked_on_url working, and passing back exceptions
152
            "<FailedSmartServerResponse args=('args',) body='body'>",
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
153
            str(smart_req.FailedSmartServerResponse(('args',), 'body')))
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
154
155
156
class TestSmartServerRequest(tests.TestCaseWithMemoryTransport):
157
158
    def test_translate_client_path(self):
159
        transport = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
160
        request = smart_req.SmartServerRequest(transport, 'foo/')
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
161
        self.assertEqual('./', request.translate_client_path('foo/'))
162
        self.assertRaises(
163
            errors.InvalidURLJoin, request.translate_client_path, 'foo/..')
164
        self.assertRaises(
165
            errors.PathNotChild, request.translate_client_path, '/')
166
        self.assertRaises(
167
            errors.PathNotChild, request.translate_client_path, 'bar/')
168
        self.assertEqual('./baz', request.translate_client_path('foo/baz'))
4760.2.2 by Michael Hudson
test
169
        e_acute = u'\N{LATIN SMALL LETTER E WITH ACUTE}'.encode('utf-8')
170
        self.assertEqual('./' + urlutils.escape(e_acute),
171
                         request.translate_client_path('foo/' + e_acute))
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
172
4760.2.5 by Andrew Bennetts
Add some more tests.
173
    def test_translate_client_path_vfs(self):
174
        """VfsRequests receive escaped paths rather than raw UTF-8."""
175
        transport = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
176
        request = vfs.VfsRequest(transport, 'foo/')
4760.2.5 by Andrew Bennetts
Add some more tests.
177
        e_acute = u'\N{LATIN SMALL LETTER E WITH ACUTE}'.encode('utf-8')
178
        escaped = urlutils.escape('foo/' + e_acute)
179
        self.assertEqual('./' + urlutils.escape(e_acute),
180
                         request.translate_client_path(escaped))
181
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
182
    def test_transport_from_client_path(self):
183
        transport = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
184
        request = smart_req.SmartServerRequest(transport, 'foo/')
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
185
        self.assertEqual(
186
            transport.base,
187
            request.transport_from_client_path('foo/').base)
188
189
4070.2.3 by Robert Collins
Get BzrDir.cloning_metadir working.
190
class TestSmartServerBzrDirRequestCloningMetaDir(
191
    tests.TestCaseWithMemoryTransport):
192
    """Tests for BzrDir.cloning_metadir."""
193
194
    def test_cloning_metadir(self):
195
        """When there is a bzrdir present, the call succeeds."""
196
        backing = self.get_transport()
197
        dir = self.make_bzrdir('.')
198
        local_result = dir.cloning_metadir()
199
        request_class = smart_dir.SmartServerBzrDirRequestCloningMetaDir
200
        request = request_class(backing)
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
201
        expected = smart_req.SuccessfulSmartServerResponse(
4070.2.3 by Robert Collins
Get BzrDir.cloning_metadir working.
202
            (local_result.network_name(),
203
            local_result.repository_format.network_name(),
4084.2.2 by Robert Collins
Review feedback.
204
            ('branch', local_result.get_branch_format().network_name())))
4070.7.4 by Andrew Bennetts
Deal with branch references better in BzrDir.cloning_metadir RPC (changes protocol).
205
        self.assertEqual(expected, request.execute('', 'False'))
206
207
    def test_cloning_metadir_reference(self):
4160.2.9 by Andrew Bennetts
Fix BzrDir.cloning_metadir RPC to fail on branch references, and make
208
        """The request fails when bzrdir contains a branch reference."""
4070.7.4 by Andrew Bennetts
Deal with branch references better in BzrDir.cloning_metadir RPC (changes protocol).
209
        backing = self.get_transport()
210
        referenced_branch = self.make_branch('referenced')
211
        dir = self.make_bzrdir('.')
212
        local_result = dir.cloning_metadir()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
213
        reference = _mod_branch.BranchReferenceFormat().initialize(
5051.3.10 by Jelmer Vernooij
Pass colocated branch name around in more places.
214
            dir, target_branch=referenced_branch)
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
215
        reference_url = _mod_branch.BranchReferenceFormat().get_reference(dir)
4070.7.4 by Andrew Bennetts
Deal with branch references better in BzrDir.cloning_metadir RPC (changes protocol).
216
        # The server shouldn't try to follow the branch reference, so it's fine
217
        # if the referenced branch isn't reachable.
218
        backing.rename('referenced', 'moved')
219
        request_class = smart_dir.SmartServerBzrDirRequestCloningMetaDir
220
        request = request_class(backing)
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
221
        expected = smart_req.FailedSmartServerResponse(('BranchReference',))
4070.2.3 by Robert Collins
Get BzrDir.cloning_metadir working.
222
        self.assertEqual(expected, request.execute('', 'False'))
223
224
6266.3.1 by Jelmer Vernooij
Add HPSS call for BzrDir.has_workingtree.
225
class TestSmartServerBzrDirRequestHasWorkingTree(
226
    tests.TestCaseWithTransport):
227
    """Tests for BzrDir.has_workingtree."""
228
229
    def test_has_workingtree_yes(self):
230
        """A working tree is present."""
231
        backing = self.get_transport()
232
        dir = self.make_branch_and_tree('.').bzrdir
233
        request_class = smart_dir.SmartServerBzrDirRequestHasWorkingTree
234
        request = request_class(backing)
235
        expected = smart_req.SuccessfulSmartServerResponse(('yes',))
236
        self.assertEqual(expected, request.execute(''))
237
238
    def test_has_workingtree_no(self):
239
        """A working tree is missing."""
240
        backing = self.get_transport()
241
        dir = self.make_bzrdir('.')
242
        request_class = smart_dir.SmartServerBzrDirRequestHasWorkingTree
243
        request = request_class(backing)
244
        expected = smart_req.SuccessfulSmartServerResponse(('no',))
245
        self.assertEqual(expected, request.execute(''))
246
247
6266.2.1 by Jelmer Vernooij
New HPSS call BzrDir.destroy_repository.
248
class TestSmartServerBzrDirRequestDestroyRepository(
249
    tests.TestCaseWithMemoryTransport):
250
    """Tests for BzrDir.destroy_repository."""
251
252
    def test_destroy_repository_default(self):
253
        """The repository can be removed."""
254
        backing = self.get_transport()
255
        dir = self.make_repository('.').bzrdir
6266.2.2 by Jelmer Vernooij
Fix tests.
256
        request_class = smart_dir.SmartServerBzrDirRequestDestroyRepository
6266.2.1 by Jelmer Vernooij
New HPSS call BzrDir.destroy_repository.
257
        request = request_class(backing)
258
        expected = smart_req.SuccessfulSmartServerResponse(('ok',))
259
        self.assertEqual(expected, request.execute(''))
260
261
    def test_destroy_repository_missing(self):
262
        """An error is raised if the repository didn't exist."""
263
        backing = self.get_transport()
264
        dir = self.make_bzrdir('.')
6266.2.2 by Jelmer Vernooij
Fix tests.
265
        request_class = smart_dir.SmartServerBzrDirRequestDestroyRepository
6266.2.1 by Jelmer Vernooij
New HPSS call BzrDir.destroy_repository.
266
        request = request_class(backing)
6266.2.2 by Jelmer Vernooij
Fix tests.
267
        expected = smart_req.FailedSmartServerResponse(
268
            ('norepository',), None)
6266.2.1 by Jelmer Vernooij
New HPSS call BzrDir.destroy_repository.
269
        self.assertEqual(expected, request.execute(''))
270
271
4017.3.2 by Robert Collins
Reduce the number of round trips required to create a repository over the network.
272
class TestSmartServerRequestCreateRepository(tests.TestCaseWithMemoryTransport):
273
    """Tests for BzrDir.create_repository."""
274
275
    def test_makes_repository(self):
276
        """When there is a bzrdir present, the call succeeds."""
277
        backing = self.get_transport()
278
        self.make_bzrdir('.')
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
279
        request_class = smart_dir.SmartServerRequestCreateRepository
4017.3.2 by Robert Collins
Reduce the number of round trips required to create a repository over the network.
280
        request = request_class(backing)
4606.3.1 by Robert Collins
Make test_smart tests more stable when the default format changes.
281
        reference_bzrdir_format = bzrdir.format_registry.get('pack-0.92')()
4017.3.2 by Robert Collins
Reduce the number of round trips required to create a repository over the network.
282
        reference_format = reference_bzrdir_format.repository_format
283
        network_name = reference_format.network_name()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
284
        expected = smart_req.SuccessfulSmartServerResponse(
4017.3.2 by Robert Collins
Reduce the number of round trips required to create a repository over the network.
285
            ('ok', 'no', 'no', 'no', network_name))
286
        self.assertEqual(expected, request.execute('', network_name, 'True'))
287
288
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
289
class TestSmartServerRequestFindRepository(tests.TestCaseWithMemoryTransport):
2018.5.118 by Robert Collins
Fix RemoteRepositoryFormat to have appropriate rich_root_data and support_tree_reference.
290
    """Tests for BzrDir.find_repository."""
2018.5.34 by Robert Collins
Get test_remote.BasicRemoteObjectTests.test_open_remote_branch passing by implementing a remote method BzrDir.find_repository.
291
292
    def test_no_repository(self):
293
        """When there is no repository to be found, ('norepository', ) is returned."""
294
        backing = self.get_transport()
3221.3.2 by Robert Collins
* New remote method ``RemoteBzrDir.find_repositoryV2`` adding support for
295
        request = self._request_class(backing)
2018.5.34 by Robert Collins
Get test_remote.BasicRemoteObjectTests.test_open_remote_branch passing by implementing a remote method BzrDir.find_repository.
296
        self.make_bzrdir('.')
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
297
        self.assertEqual(smart_req.SmartServerResponse(('norepository', )),
2692.1.19 by Andrew Bennetts
Tweak for consistency suggested by John's review.
298
            request.execute(''))
2018.5.34 by Robert Collins
Get test_remote.BasicRemoteObjectTests.test_open_remote_branch passing by implementing a remote method BzrDir.find_repository.
299
300
    def test_nonshared_repository(self):
3943.8.1 by Marius Kruger
remove all trailing whitespace from bzr source
301
        # nonshared repositorys only allow 'find' to return a handle when the
302
        # path the repository is being searched on is the same as that that
2018.5.34 by Robert Collins
Get test_remote.BasicRemoteObjectTests.test_open_remote_branch passing by implementing a remote method BzrDir.find_repository.
303
        # the repository is at.
304
        backing = self.get_transport()
3221.3.2 by Robert Collins
* New remote method ``RemoteBzrDir.find_repositoryV2`` adding support for
305
        request = self._request_class(backing)
2018.5.118 by Robert Collins
Fix RemoteRepositoryFormat to have appropriate rich_root_data and support_tree_reference.
306
        result = self._make_repository_and_result()
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
307
        self.assertEqual(result, request.execute(''))
2018.5.34 by Robert Collins
Get test_remote.BasicRemoteObjectTests.test_open_remote_branch passing by implementing a remote method BzrDir.find_repository.
308
        self.make_bzrdir('subdir')
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
309
        self.assertEqual(smart_req.SmartServerResponse(('norepository', )),
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
310
            request.execute('subdir'))
2018.5.34 by Robert Collins
Get test_remote.BasicRemoteObjectTests.test_open_remote_branch passing by implementing a remote method BzrDir.find_repository.
311
2018.5.118 by Robert Collins
Fix RemoteRepositoryFormat to have appropriate rich_root_data and support_tree_reference.
312
    def _make_repository_and_result(self, shared=False, format=None):
313
        """Convenience function to setup a repository.
314
315
        :result: The SmartServerResponse to expect when opening it.
316
        """
317
        repo = self.make_repository('.', shared=shared, format=format)
318
        if repo.supports_rich_root():
2018.5.166 by Andrew Bennetts
Small changes in response to Aaron's review.
319
            rich_root = 'yes'
2018.5.118 by Robert Collins
Fix RemoteRepositoryFormat to have appropriate rich_root_data and support_tree_reference.
320
        else:
2018.5.166 by Andrew Bennetts
Small changes in response to Aaron's review.
321
            rich_root = 'no'
2018.5.138 by Robert Collins
Merge bzr.dev.
322
        if repo._format.supports_tree_reference:
2018.5.166 by Andrew Bennetts
Small changes in response to Aaron's review.
323
            subtrees = 'yes'
2018.5.118 by Robert Collins
Fix RemoteRepositoryFormat to have appropriate rich_root_data and support_tree_reference.
324
        else:
2018.5.166 by Andrew Bennetts
Small changes in response to Aaron's review.
325
            subtrees = 'no'
4606.3.1 by Robert Collins
Make test_smart tests more stable when the default format changes.
326
        if repo._format.supports_external_lookups:
327
            external = 'yes'
328
        else:
329
            external = 'no'
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
330
        if (smart_dir.SmartServerRequestFindRepositoryV3 ==
4053.1.4 by Robert Collins
Move the fetch control attributes from Repository to RepositoryFormat.
331
            self._request_class):
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
332
            return smart_req.SuccessfulSmartServerResponse(
4606.3.1 by Robert Collins
Make test_smart tests more stable when the default format changes.
333
                ('ok', '', rich_root, subtrees, external,
4053.1.4 by Robert Collins
Move the fetch control attributes from Repository to RepositoryFormat.
334
                 repo._format.network_name()))
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
335
        elif (smart_dir.SmartServerRequestFindRepositoryV2 ==
3221.3.2 by Robert Collins
* New remote method ``RemoteBzrDir.find_repositoryV2`` adding support for
336
            self._request_class):
337
            # All tests so far are on formats, and for non-external
338
            # repositories.
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
339
            return smart_req.SuccessfulSmartServerResponse(
4606.3.1 by Robert Collins
Make test_smart tests more stable when the default format changes.
340
                ('ok', '', rich_root, subtrees, external))
3221.3.2 by Robert Collins
* New remote method ``RemoteBzrDir.find_repositoryV2`` adding support for
341
        else:
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
342
            return smart_req.SuccessfulSmartServerResponse(
343
                ('ok', '', rich_root, subtrees))
2018.5.118 by Robert Collins
Fix RemoteRepositoryFormat to have appropriate rich_root_data and support_tree_reference.
344
2018.5.34 by Robert Collins
Get test_remote.BasicRemoteObjectTests.test_open_remote_branch passing by implementing a remote method BzrDir.find_repository.
345
    def test_shared_repository(self):
346
        """When there is a shared repository, we get 'ok', 'relpath-to-repo'."""
347
        backing = self.get_transport()
3221.3.2 by Robert Collins
* New remote method ``RemoteBzrDir.find_repositoryV2`` adding support for
348
        request = self._request_class(backing)
2018.5.118 by Robert Collins
Fix RemoteRepositoryFormat to have appropriate rich_root_data and support_tree_reference.
349
        result = self._make_repository_and_result(shared=True)
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
350
        self.assertEqual(result, request.execute(''))
2018.5.34 by Robert Collins
Get test_remote.BasicRemoteObjectTests.test_open_remote_branch passing by implementing a remote method BzrDir.find_repository.
351
        self.make_bzrdir('subdir')
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
352
        result2 = smart_req.SmartServerResponse(
353
            result.args[0:1] + ('..', ) + result.args[2:])
2018.5.118 by Robert Collins
Fix RemoteRepositoryFormat to have appropriate rich_root_data and support_tree_reference.
354
        self.assertEqual(result2,
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
355
            request.execute('subdir'))
2018.5.34 by Robert Collins
Get test_remote.BasicRemoteObjectTests.test_open_remote_branch passing by implementing a remote method BzrDir.find_repository.
356
        self.make_bzrdir('subdir/deeper')
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
357
        result3 = smart_req.SmartServerResponse(
358
            result.args[0:1] + ('../..', ) + result.args[2:])
2018.5.118 by Robert Collins
Fix RemoteRepositoryFormat to have appropriate rich_root_data and support_tree_reference.
359
        self.assertEqual(result3,
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
360
            request.execute('subdir/deeper'))
2018.5.34 by Robert Collins
Get test_remote.BasicRemoteObjectTests.test_open_remote_branch passing by implementing a remote method BzrDir.find_repository.
361
2018.5.118 by Robert Collins
Fix RemoteRepositoryFormat to have appropriate rich_root_data and support_tree_reference.
362
    def test_rich_root_and_subtree_encoding(self):
363
        """Test for the format attributes for rich root and subtree support."""
364
        backing = self.get_transport()
3221.3.2 by Robert Collins
* New remote method ``RemoteBzrDir.find_repositoryV2`` adding support for
365
        request = self._request_class(backing)
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
366
        result = self._make_repository_and_result(
367
            format='dirstate-with-subtree')
2018.5.118 by Robert Collins
Fix RemoteRepositoryFormat to have appropriate rich_root_data and support_tree_reference.
368
        # check the test will be valid
2018.5.166 by Andrew Bennetts
Small changes in response to Aaron's review.
369
        self.assertEqual('yes', result.args[2])
370
        self.assertEqual('yes', result.args[3])
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
371
        self.assertEqual(result, request.execute(''))
372
3221.3.2 by Robert Collins
* New remote method ``RemoteBzrDir.find_repositoryV2`` adding support for
373
    def test_supports_external_lookups_no_v2(self):
374
        """Test for the supports_external_lookups attribute."""
375
        backing = self.get_transport()
376
        request = self._request_class(backing)
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
377
        result = self._make_repository_and_result(
378
            format='dirstate-with-subtree')
3221.3.2 by Robert Collins
* New remote method ``RemoteBzrDir.find_repositoryV2`` adding support for
379
        # check the test will be valid
380
        self.assertEqual('no', result.args[4])
2692.1.24 by Andrew Bennetts
Merge from bzr.dev.
381
        self.assertEqual(result, request.execute(''))
382
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
383
4288.1.2 by Robert Collins
Create a server verb for doing BzrDir.get_config()
384
class TestSmartServerBzrDirRequestGetConfigFile(
385
    tests.TestCaseWithMemoryTransport):
386
    """Tests for BzrDir.get_config_file."""
387
388
    def test_present(self):
389
        backing = self.get_transport()
390
        dir = self.make_bzrdir('.')
391
        dir.get_config().set_default_stack_on("/")
392
        local_result = dir._get_config()._get_config_file().read()
393
        request_class = smart_dir.SmartServerBzrDirRequestConfigFile
394
        request = request_class(backing)
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
395
        expected = smart_req.SuccessfulSmartServerResponse((), local_result)
4288.1.2 by Robert Collins
Create a server verb for doing BzrDir.get_config()
396
        self.assertEqual(expected, request.execute(''))
397
398
    def test_missing(self):
399
        backing = self.get_transport()
400
        dir = self.make_bzrdir('.')
401
        request_class = smart_dir.SmartServerBzrDirRequestConfigFile
402
        request = request_class(backing)
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
403
        expected = smart_req.SuccessfulSmartServerResponse((), '')
4288.1.2 by Robert Collins
Create a server verb for doing BzrDir.get_config()
404
        self.assertEqual(expected, request.execute(''))
405
406
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
407
class TestSmartServerRequestInitializeBzrDir(tests.TestCaseWithMemoryTransport):
2018.5.42 by Robert Collins
Various hopefully improvements, but wsgi is broken, handing over to spiv :).
408
409
    def test_empty_dir(self):
410
        """Initializing an empty dir should succeed and do it."""
411
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
412
        request = smart_dir.SmartServerRequestInitializeBzrDir(backing)
413
        self.assertEqual(smart_req.SmartServerResponse(('ok', )),
2692.1.20 by Andrew Bennetts
Tweak for consistency suggested by John's review.
414
            request.execute(''))
2018.5.42 by Robert Collins
Various hopefully improvements, but wsgi is broken, handing over to spiv :).
415
        made_dir = bzrdir.BzrDir.open_from_transport(backing)
3943.8.1 by Marius Kruger
remove all trailing whitespace from bzr source
416
        # no branch, tree or repository is expected with the current
2018.5.42 by Robert Collins
Various hopefully improvements, but wsgi is broken, handing over to spiv :).
417
        # default formart.
418
        self.assertRaises(errors.NoWorkingTree, made_dir.open_workingtree)
419
        self.assertRaises(errors.NotBranchError, made_dir.open_branch)
420
        self.assertRaises(errors.NoRepositoryPresent, made_dir.open_repository)
421
422
    def test_missing_dir(self):
423
        """Initializing a missing directory should fail like the bzrdir api."""
424
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
425
        request = smart_dir.SmartServerRequestInitializeBzrDir(backing)
2018.5.42 by Robert Collins
Various hopefully improvements, but wsgi is broken, handing over to spiv :).
426
        self.assertRaises(errors.NoSuchFile,
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
427
            request.execute, 'subdir')
2018.5.42 by Robert Collins
Various hopefully improvements, but wsgi is broken, handing over to spiv :).
428
429
    def test_initialized_dir(self):
430
        """Initializing an extant bzrdir should fail like the bzrdir api."""
431
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
432
        request = smart_dir.SmartServerRequestInitializeBzrDir(backing)
2018.5.42 by Robert Collins
Various hopefully improvements, but wsgi is broken, handing over to spiv :).
433
        self.make_bzrdir('subdir')
434
        self.assertRaises(errors.FileExists,
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
435
            request.execute, 'subdir')
436
437
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
438
class TestSmartServerRequestBzrDirInitializeEx(
439
    tests.TestCaseWithMemoryTransport):
4436.1.1 by Andrew Bennetts
Rename BzrDirFormat.initialize_ex verb to BzrDirFormat.initialize_ex_1.16.
440
    """Basic tests for BzrDir.initialize_ex_1.16 in the smart server.
4294.2.7 by Robert Collins
Start building up a BzrDir.initialize_ex verb for the smart server.
441
4294.2.10 by Robert Collins
Review feedback.
442
    The main unit tests in test_bzrdir exercise the API comprehensively.
4294.2.7 by Robert Collins
Start building up a BzrDir.initialize_ex verb for the smart server.
443
    """
444
445
    def test_empty_dir(self):
446
        """Initializing an empty dir should succeed and do it."""
447
        backing = self.get_transport()
4294.2.8 by Robert Collins
Reduce round trips pushing new branches substantially.
448
        name = self.make_bzrdir('reference')._format.network_name()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
449
        request = smart_dir.SmartServerRequestBzrDirInitializeEx(backing)
450
        self.assertEqual(
451
            smart_req.SmartServerResponse(('', '', '', '', '', '', name,
452
                                           'False', '', '', '')),
4294.2.8 by Robert Collins
Reduce round trips pushing new branches substantially.
453
            request.execute(name, '', 'True', 'False', 'False', '', '', '', '',
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
454
                            'False'))
4294.2.7 by Robert Collins
Start building up a BzrDir.initialize_ex verb for the smart server.
455
        made_dir = bzrdir.BzrDir.open_from_transport(backing)
456
        # no branch, tree or repository is expected with the current
4294.2.10 by Robert Collins
Review feedback.
457
        # default format.
4294.2.7 by Robert Collins
Start building up a BzrDir.initialize_ex verb for the smart server.
458
        self.assertRaises(errors.NoWorkingTree, made_dir.open_workingtree)
459
        self.assertRaises(errors.NotBranchError, made_dir.open_branch)
460
        self.assertRaises(errors.NoRepositoryPresent, made_dir.open_repository)
461
462
    def test_missing_dir(self):
463
        """Initializing a missing directory should fail like the bzrdir api."""
464
        backing = self.get_transport()
4294.2.8 by Robert Collins
Reduce round trips pushing new branches substantially.
465
        name = self.make_bzrdir('reference')._format.network_name()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
466
        request = smart_dir.SmartServerRequestBzrDirInitializeEx(backing)
4294.2.8 by Robert Collins
Reduce round trips pushing new branches substantially.
467
        self.assertRaises(errors.NoSuchFile, request.execute, name,
468
            'subdir/dir', 'False', 'False', 'False', '', '', '', '', 'False')
4294.2.7 by Robert Collins
Start building up a BzrDir.initialize_ex verb for the smart server.
469
470
    def test_initialized_dir(self):
4416.3.4 by Jonathan Lange
Fix a typo.
471
        """Initializing an extant directory should fail like the bzrdir api."""
4294.2.7 by Robert Collins
Start building up a BzrDir.initialize_ex verb for the smart server.
472
        backing = self.get_transport()
4294.2.8 by Robert Collins
Reduce round trips pushing new branches substantially.
473
        name = self.make_bzrdir('reference')._format.network_name()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
474
        request = smart_dir.SmartServerRequestBzrDirInitializeEx(backing)
4294.2.7 by Robert Collins
Start building up a BzrDir.initialize_ex verb for the smart server.
475
        self.make_bzrdir('subdir')
4294.2.8 by Robert Collins
Reduce round trips pushing new branches substantially.
476
        self.assertRaises(errors.FileExists, request.execute, name, 'subdir',
477
            'False', 'False', 'False', '', '', '', '', 'False')
4294.2.7 by Robert Collins
Start building up a BzrDir.initialize_ex verb for the smart server.
478
4634.47.5 by Andrew Bennetts
Add tests, and fix BzrDirMeta1.has_workingtree which was failing if the local transport is decorated with a ChrootTransport or similar.
479
480
class TestSmartServerRequestOpenBzrDir(tests.TestCaseWithMemoryTransport):
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
481
4634.47.5 by Andrew Bennetts
Add tests, and fix BzrDirMeta1.has_workingtree which was failing if the local transport is decorated with a ChrootTransport or similar.
482
    def test_no_directory(self):
483
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
484
        request = smart_dir.SmartServerRequestOpenBzrDir(backing)
485
        self.assertEqual(smart_req.SmartServerResponse(('no', )),
4634.47.5 by Andrew Bennetts
Add tests, and fix BzrDirMeta1.has_workingtree which was failing if the local transport is decorated with a ChrootTransport or similar.
486
            request.execute('does-not-exist'))
487
488
    def test_empty_directory(self):
489
        backing = self.get_transport()
490
        backing.mkdir('empty')
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
491
        request = smart_dir.SmartServerRequestOpenBzrDir(backing)
492
        self.assertEqual(smart_req.SmartServerResponse(('no', )),
4634.47.5 by Andrew Bennetts
Add tests, and fix BzrDirMeta1.has_workingtree which was failing if the local transport is decorated with a ChrootTransport or similar.
493
            request.execute('empty'))
494
495
    def test_outside_root_client_path(self):
496
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
497
        request = smart_dir.SmartServerRequestOpenBzrDir(backing,
4634.47.5 by Andrew Bennetts
Add tests, and fix BzrDirMeta1.has_workingtree which was failing if the local transport is decorated with a ChrootTransport or similar.
498
            root_client_path='root')
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
499
        self.assertEqual(smart_req.SmartServerResponse(('no', )),
4634.47.5 by Andrew Bennetts
Add tests, and fix BzrDirMeta1.has_workingtree which was failing if the local transport is decorated with a ChrootTransport or similar.
500
            request.execute('not-root'))
501
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
502
4634.47.5 by Andrew Bennetts
Add tests, and fix BzrDirMeta1.has_workingtree which was failing if the local transport is decorated with a ChrootTransport or similar.
503
class TestSmartServerRequestOpenBzrDir_2_1(tests.TestCaseWithMemoryTransport):
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
504
4634.47.5 by Andrew Bennetts
Add tests, and fix BzrDirMeta1.has_workingtree which was failing if the local transport is decorated with a ChrootTransport or similar.
505
    def test_no_directory(self):
506
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
507
        request = smart_dir.SmartServerRequestOpenBzrDir_2_1(backing)
508
        self.assertEqual(smart_req.SmartServerResponse(('no', )),
4634.47.5 by Andrew Bennetts
Add tests, and fix BzrDirMeta1.has_workingtree which was failing if the local transport is decorated with a ChrootTransport or similar.
509
            request.execute('does-not-exist'))
510
511
    def test_empty_directory(self):
512
        backing = self.get_transport()
513
        backing.mkdir('empty')
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
514
        request = smart_dir.SmartServerRequestOpenBzrDir_2_1(backing)
515
        self.assertEqual(smart_req.SmartServerResponse(('no', )),
4634.47.5 by Andrew Bennetts
Add tests, and fix BzrDirMeta1.has_workingtree which was failing if the local transport is decorated with a ChrootTransport or similar.
516
            request.execute('empty'))
517
518
    def test_present_without_workingtree(self):
519
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
520
        request = smart_dir.SmartServerRequestOpenBzrDir_2_1(backing)
4634.47.5 by Andrew Bennetts
Add tests, and fix BzrDirMeta1.has_workingtree which was failing if the local transport is decorated with a ChrootTransport or similar.
521
        self.make_bzrdir('.')
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
522
        self.assertEqual(smart_req.SmartServerResponse(('yes', 'no')),
4634.47.5 by Andrew Bennetts
Add tests, and fix BzrDirMeta1.has_workingtree which was failing if the local transport is decorated with a ChrootTransport or similar.
523
            request.execute(''))
524
4634.47.6 by Andrew Bennetts
Give 'no' response for paths outside the root_client_path.
525
    def test_outside_root_client_path(self):
4634.47.5 by Andrew Bennetts
Add tests, and fix BzrDirMeta1.has_workingtree which was failing if the local transport is decorated with a ChrootTransport or similar.
526
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
527
        request = smart_dir.SmartServerRequestOpenBzrDir_2_1(backing,
4634.47.5 by Andrew Bennetts
Add tests, and fix BzrDirMeta1.has_workingtree which was failing if the local transport is decorated with a ChrootTransport or similar.
528
            root_client_path='root')
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
529
        self.assertEqual(smart_req.SmartServerResponse(('no',)),
4634.47.6 by Andrew Bennetts
Give 'no' response for paths outside the root_client_path.
530
            request.execute('not-root'))
4634.47.5 by Andrew Bennetts
Add tests, and fix BzrDirMeta1.has_workingtree which was failing if the local transport is decorated with a ChrootTransport or similar.
531
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
532
4634.47.5 by Andrew Bennetts
Add tests, and fix BzrDirMeta1.has_workingtree which was failing if the local transport is decorated with a ChrootTransport or similar.
533
class TestSmartServerRequestOpenBzrDir_2_1_disk(TestCaseWithChrootedTransport):
534
535
    def test_present_with_workingtree(self):
5017.3.26 by Vincent Ladeuil
./bzr selftest -s bt.test_smart passing
536
        self.vfs_transport_factory = test_server.LocalURLServer
4634.47.5 by Andrew Bennetts
Add tests, and fix BzrDirMeta1.has_workingtree which was failing if the local transport is decorated with a ChrootTransport or similar.
537
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
538
        request = smart_dir.SmartServerRequestOpenBzrDir_2_1(backing)
4634.47.5 by Andrew Bennetts
Add tests, and fix BzrDirMeta1.has_workingtree which was failing if the local transport is decorated with a ChrootTransport or similar.
539
        bd = self.make_bzrdir('.')
540
        bd.create_repository()
541
        bd.create_branch()
542
        bd.create_workingtree()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
543
        self.assertEqual(smart_req.SmartServerResponse(('yes', 'yes')),
4634.47.5 by Andrew Bennetts
Add tests, and fix BzrDirMeta1.has_workingtree which was failing if the local transport is decorated with a ChrootTransport or similar.
544
            request.execute(''))
545
546
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
547
class TestSmartServerRequestOpenBranch(TestCaseWithChrootedTransport):
2018.6.1 by Robert Collins
Implement a BzrDir.open_branch smart server method for opening a branch without VFS.
548
549
    def test_no_branch(self):
550
        """When there is no branch, ('nobranch', ) is returned."""
551
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
552
        request = smart_dir.SmartServerRequestOpenBranch(backing)
2018.6.1 by Robert Collins
Implement a BzrDir.open_branch smart server method for opening a branch without VFS.
553
        self.make_bzrdir('.')
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
554
        self.assertEqual(smart_req.SmartServerResponse(('nobranch', )),
2692.1.20 by Andrew Bennetts
Tweak for consistency suggested by John's review.
555
            request.execute(''))
2018.6.1 by Robert Collins
Implement a BzrDir.open_branch smart server method for opening a branch without VFS.
556
557
    def test_branch(self):
558
        """When there is a branch, 'ok' is returned."""
559
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
560
        request = smart_dir.SmartServerRequestOpenBranch(backing)
2018.6.1 by Robert Collins
Implement a BzrDir.open_branch smart server method for opening a branch without VFS.
561
        self.make_branch('.')
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
562
        self.assertEqual(smart_req.SmartServerResponse(('ok', '')),
2692.1.20 by Andrew Bennetts
Tweak for consistency suggested by John's review.
563
            request.execute(''))
2018.6.1 by Robert Collins
Implement a BzrDir.open_branch smart server method for opening a branch without VFS.
564
565
    def test_branch_reference(self):
566
        """When there is a branch reference, the reference URL is returned."""
5017.3.26 by Vincent Ladeuil
./bzr selftest -s bt.test_smart passing
567
        self.vfs_transport_factory = test_server.LocalURLServer
2018.6.1 by Robert Collins
Implement a BzrDir.open_branch smart server method for opening a branch without VFS.
568
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
569
        request = smart_dir.SmartServerRequestOpenBranch(backing)
2018.6.1 by Robert Collins
Implement a BzrDir.open_branch smart server method for opening a branch without VFS.
570
        branch = self.make_branch('branch')
571
        checkout = branch.create_checkout('reference',lightweight=True)
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
572
        reference_url = _mod_branch.BranchReferenceFormat().get_reference(
573
            checkout.bzrdir)
2018.6.1 by Robert Collins
Implement a BzrDir.open_branch smart server method for opening a branch without VFS.
574
        self.assertFileEqual(reference_url, 'reference/.bzr/branch/location')
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
575
        self.assertEqual(smart_req.SmartServerResponse(('ok', reference_url)),
2692.1.20 by Andrew Bennetts
Tweak for consistency suggested by John's review.
576
            request.execute('reference'))
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
577
4734.4.5 by Brian de Alwis
Address comments from Aaron Bentley
578
    def test_notification_on_branch_from_repository(self):
4734.4.4 by Brian de Alwis
Added tests to ensure branching-from-repository error returns detail
579
        """When there is a repository, the error should return details."""
580
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
581
        request = smart_dir.SmartServerRequestOpenBranch(backing)
4734.4.4 by Brian de Alwis
Added tests to ensure branching-from-repository error returns detail
582
        repo = self.make_repository('.')
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
583
        self.assertEqual(smart_req.SmartServerResponse(('nobranch',)),
4734.4.4 by Brian de Alwis
Added tests to ensure branching-from-repository error returns detail
584
            request.execute(''))
585
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
586
4084.2.1 by Robert Collins
Make accessing a branch.tags.get_tag_dict use a smart[er] method rather than VFS calls and real objects.
587
class TestSmartServerRequestOpenBranchV2(TestCaseWithChrootedTransport):
588
589
    def test_no_branch(self):
590
        """When there is no branch, ('nobranch', ) is returned."""
591
        backing = self.get_transport()
592
        self.make_bzrdir('.')
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
593
        request = smart_dir.SmartServerRequestOpenBranchV2(backing)
594
        self.assertEqual(smart_req.SmartServerResponse(('nobranch', )),
4084.2.1 by Robert Collins
Make accessing a branch.tags.get_tag_dict use a smart[er] method rather than VFS calls and real objects.
595
            request.execute(''))
596
597
    def test_branch(self):
598
        """When there is a branch, 'ok' is returned."""
599
        backing = self.get_transport()
600
        expected = self.make_branch('.')._format.network_name()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
601
        request = smart_dir.SmartServerRequestOpenBranchV2(backing)
602
        self.assertEqual(smart_req.SuccessfulSmartServerResponse(
603
                ('branch', expected)),
604
                         request.execute(''))
4084.2.1 by Robert Collins
Make accessing a branch.tags.get_tag_dict use a smart[er] method rather than VFS calls and real objects.
605
606
    def test_branch_reference(self):
607
        """When there is a branch reference, the reference URL is returned."""
5017.3.26 by Vincent Ladeuil
./bzr selftest -s bt.test_smart passing
608
        self.vfs_transport_factory = test_server.LocalURLServer
4084.2.1 by Robert Collins
Make accessing a branch.tags.get_tag_dict use a smart[er] method rather than VFS calls and real objects.
609
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
610
        request = smart_dir.SmartServerRequestOpenBranchV2(backing)
4084.2.1 by Robert Collins
Make accessing a branch.tags.get_tag_dict use a smart[er] method rather than VFS calls and real objects.
611
        branch = self.make_branch('branch')
612
        checkout = branch.create_checkout('reference',lightweight=True)
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
613
        reference_url = _mod_branch.BranchReferenceFormat().get_reference(
614
            checkout.bzrdir)
4084.2.1 by Robert Collins
Make accessing a branch.tags.get_tag_dict use a smart[er] method rather than VFS calls and real objects.
615
        self.assertFileEqual(reference_url, 'reference/.bzr/branch/location')
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
616
        self.assertEqual(smart_req.SuccessfulSmartServerResponse(
617
                ('ref', reference_url)),
618
                         request.execute('reference'))
4084.2.1 by Robert Collins
Make accessing a branch.tags.get_tag_dict use a smart[er] method rather than VFS calls and real objects.
619
4160.2.1 by Andrew Bennetts
Failing test for BzrDir.open_branchV2 RPC not opening stacked-on branch.
620
    def test_stacked_branch(self):
621
        """Opening a stacked branch does not open the stacked-on branch."""
622
        trunk = self.make_branch('trunk')
4599.4.30 by Robert Collins
Remove hard coded format in test_smart's test_stacked_branch now the default format stacks.
623
        feature = self.make_branch('feature')
4160.2.1 by Andrew Bennetts
Failing test for BzrDir.open_branchV2 RPC not opening stacked-on branch.
624
        feature.set_stacked_on_url(trunk.base)
625
        opened_branches = []
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
626
        _mod_branch.Branch.hooks.install_named_hook(
627
            'open', opened_branches.append, None)
4160.2.1 by Andrew Bennetts
Failing test for BzrDir.open_branchV2 RPC not opening stacked-on branch.
628
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
629
        request = smart_dir.SmartServerRequestOpenBranchV2(backing)
4160.2.4 by Andrew Bennetts
Use BzrDir pre_open hook to jail request code from accessing transports other than the backing transport.
630
        request.setup_jail()
631
        try:
632
            response = request.execute('feature')
633
        finally:
634
            request.teardown_jail()
4160.2.1 by Andrew Bennetts
Failing test for BzrDir.open_branchV2 RPC not opening stacked-on branch.
635
        expected_format = feature._format.network_name()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
636
        self.assertEqual(smart_req.SuccessfulSmartServerResponse(
637
                ('branch', expected_format)),
638
                         response)
4160.2.1 by Andrew Bennetts
Failing test for BzrDir.open_branchV2 RPC not opening stacked-on branch.
639
        self.assertLength(1, opened_branches)
640
4734.4.5 by Brian de Alwis
Address comments from Aaron Bentley
641
    def test_notification_on_branch_from_repository(self):
4734.4.4 by Brian de Alwis
Added tests to ensure branching-from-repository error returns detail
642
        """When there is a repository, the error should return details."""
643
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
644
        request = smart_dir.SmartServerRequestOpenBranchV2(backing)
4734.4.4 by Brian de Alwis
Added tests to ensure branching-from-repository error returns detail
645
        repo = self.make_repository('.')
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
646
        self.assertEqual(smart_req.SmartServerResponse(('nobranch',)),
4734.4.8 by Andrew Bennetts
Fix HPSS tests; pass 'location is a repository' message via smart server when possible (adds BzrDir.open_branchV3 verb).
647
            request.execute(''))
648
649
650
class TestSmartServerRequestOpenBranchV3(TestCaseWithChrootedTransport):
651
652
    def test_no_branch(self):
653
        """When there is no branch, ('nobranch', ) is returned."""
654
        backing = self.get_transport()
655
        self.make_bzrdir('.')
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
656
        request = smart_dir.SmartServerRequestOpenBranchV3(backing)
657
        self.assertEqual(smart_req.SmartServerResponse(('nobranch',)),
4734.4.8 by Andrew Bennetts
Fix HPSS tests; pass 'location is a repository' message via smart server when possible (adds BzrDir.open_branchV3 verb).
658
            request.execute(''))
659
660
    def test_branch(self):
661
        """When there is a branch, 'ok' is returned."""
662
        backing = self.get_transport()
663
        expected = self.make_branch('.')._format.network_name()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
664
        request = smart_dir.SmartServerRequestOpenBranchV3(backing)
665
        self.assertEqual(smart_req.SuccessfulSmartServerResponse(
666
                ('branch', expected)),
667
                         request.execute(''))
4734.4.8 by Andrew Bennetts
Fix HPSS tests; pass 'location is a repository' message via smart server when possible (adds BzrDir.open_branchV3 verb).
668
669
    def test_branch_reference(self):
670
        """When there is a branch reference, the reference URL is returned."""
5017.3.26 by Vincent Ladeuil
./bzr selftest -s bt.test_smart passing
671
        self.vfs_transport_factory = test_server.LocalURLServer
4734.4.8 by Andrew Bennetts
Fix HPSS tests; pass 'location is a repository' message via smart server when possible (adds BzrDir.open_branchV3 verb).
672
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
673
        request = smart_dir.SmartServerRequestOpenBranchV3(backing)
4734.4.8 by Andrew Bennetts
Fix HPSS tests; pass 'location is a repository' message via smart server when possible (adds BzrDir.open_branchV3 verb).
674
        branch = self.make_branch('branch')
675
        checkout = branch.create_checkout('reference',lightweight=True)
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
676
        reference_url = _mod_branch.BranchReferenceFormat().get_reference(
677
            checkout.bzrdir)
4734.4.8 by Andrew Bennetts
Fix HPSS tests; pass 'location is a repository' message via smart server when possible (adds BzrDir.open_branchV3 verb).
678
        self.assertFileEqual(reference_url, 'reference/.bzr/branch/location')
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
679
        self.assertEqual(smart_req.SuccessfulSmartServerResponse(
680
                ('ref', reference_url)),
681
                         request.execute('reference'))
4734.4.8 by Andrew Bennetts
Fix HPSS tests; pass 'location is a repository' message via smart server when possible (adds BzrDir.open_branchV3 verb).
682
683
    def test_stacked_branch(self):
684
        """Opening a stacked branch does not open the stacked-on branch."""
685
        trunk = self.make_branch('trunk')
686
        feature = self.make_branch('feature')
687
        feature.set_stacked_on_url(trunk.base)
688
        opened_branches = []
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
689
        _mod_branch.Branch.hooks.install_named_hook(
690
            'open', opened_branches.append, None)
4734.4.8 by Andrew Bennetts
Fix HPSS tests; pass 'location is a repository' message via smart server when possible (adds BzrDir.open_branchV3 verb).
691
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
692
        request = smart_dir.SmartServerRequestOpenBranchV3(backing)
4734.4.8 by Andrew Bennetts
Fix HPSS tests; pass 'location is a repository' message via smart server when possible (adds BzrDir.open_branchV3 verb).
693
        request.setup_jail()
694
        try:
695
            response = request.execute('feature')
696
        finally:
697
            request.teardown_jail()
698
        expected_format = feature._format.network_name()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
699
        self.assertEqual(smart_req.SuccessfulSmartServerResponse(
700
                ('branch', expected_format)),
701
                         response)
4734.4.8 by Andrew Bennetts
Fix HPSS tests; pass 'location is a repository' message via smart server when possible (adds BzrDir.open_branchV3 verb).
702
        self.assertLength(1, opened_branches)
703
704
    def test_notification_on_branch_from_repository(self):
705
        """When there is a repository, the error should return details."""
706
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
707
        request = smart_dir.SmartServerRequestOpenBranchV3(backing)
4734.4.8 by Andrew Bennetts
Fix HPSS tests; pass 'location is a repository' message via smart server when possible (adds BzrDir.open_branchV3 verb).
708
        repo = self.make_repository('.')
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
709
        self.assertEqual(smart_req.SmartServerResponse(
710
                ('nobranch', 'location is a repository')),
711
                         request.execute(''))
4734.4.4 by Brian de Alwis
Added tests to ensure branching-from-repository error returns detail
712
4084.2.1 by Robert Collins
Make accessing a branch.tags.get_tag_dict use a smart[er] method rather than VFS calls and real objects.
713
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
714
class TestSmartServerRequestRevisionHistory(tests.TestCaseWithMemoryTransport):
2018.5.38 by Robert Collins
Implement RemoteBranch.revision_history().
715
716
    def test_empty(self):
717
        """For an empty branch, the body is empty."""
718
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
719
        request = smart_branch.SmartServerRequestRevisionHistory(backing)
2018.5.38 by Robert Collins
Implement RemoteBranch.revision_history().
720
        self.make_branch('.')
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
721
        self.assertEqual(smart_req.SmartServerResponse(('ok', ), ''),
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
722
            request.execute(''))
2018.5.38 by Robert Collins
Implement RemoteBranch.revision_history().
723
724
    def test_not_empty(self):
725
        """For a non-empty branch, the body is empty."""
726
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
727
        request = smart_branch.SmartServerRequestRevisionHistory(backing)
2018.5.38 by Robert Collins
Implement RemoteBranch.revision_history().
728
        tree = self.make_branch_and_memory_tree('.')
729
        tree.lock_write()
730
        tree.add('')
731
        r1 = tree.commit('1st commit')
2018.5.148 by Andrew Bennetts
Fix all the DeprecationWarnings in test_smart caused by unicode revision IDs.
732
        r2 = tree.commit('2nd commit', rev_id=u'\xc8'.encode('utf-8'))
2018.5.38 by Robert Collins
Implement RemoteBranch.revision_history().
733
        tree.unlock()
2018.5.83 by Andrew Bennetts
Fix some test failures caused by the switch from unicode to UTF-8-encoded strs for revision IDs.
734
        self.assertEqual(
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
735
            smart_req.SmartServerResponse(('ok', ), ('\x00'.join([r1, r2]))),
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
736
            request.execute(''))
737
738
739
class TestSmartServerBranchRequest(tests.TestCaseWithMemoryTransport):
2018.5.49 by Wouter van Heyst
Refactor SmartServerBranchRequest out from SmartServerRequestRevisionHistory to
740
741
    def test_no_branch(self):
742
        """When there is a bzrdir and no branch, NotBranchError is raised."""
743
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
744
        request = smart_branch.SmartServerBranchRequest(backing)
2018.5.49 by Wouter van Heyst
Refactor SmartServerBranchRequest out from SmartServerRequestRevisionHistory to
745
        self.make_bzrdir('.')
746
        self.assertRaises(errors.NotBranchError,
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
747
            request.execute, '')
2018.5.49 by Wouter van Heyst
Refactor SmartServerBranchRequest out from SmartServerRequestRevisionHistory to
748
2018.5.38 by Robert Collins
Implement RemoteBranch.revision_history().
749
    def test_branch_reference(self):
750
        """When there is a branch reference, NotBranchError is raised."""
751
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
752
        request = smart_branch.SmartServerBranchRequest(backing)
2018.5.38 by Robert Collins
Implement RemoteBranch.revision_history().
753
        branch = self.make_branch('branch')
754
        checkout = branch.create_checkout('reference',lightweight=True)
755
        self.assertRaises(errors.NotBranchError,
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
756
            request.execute, 'checkout')
757
758
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
759
class TestSmartServerBranchRequestLastRevisionInfo(
760
    tests.TestCaseWithMemoryTransport):
2018.5.50 by Wouter van Heyst
Add SmartServerBranchRequestLastRevisionInfo method.
761
762
    def test_empty(self):
2018.5.170 by Andrew Bennetts
Use 'null:' instead of '' to mean NULL_REVISION on the wire.
763
        """For an empty branch, the result is ('ok', '0', 'null:')."""
2018.5.50 by Wouter van Heyst
Add SmartServerBranchRequestLastRevisionInfo method.
764
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
765
        request = smart_branch.SmartServerBranchRequestLastRevisionInfo(backing)
2018.5.50 by Wouter van Heyst
Add SmartServerBranchRequestLastRevisionInfo method.
766
        self.make_branch('.')
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
767
        self.assertEqual(smart_req.SmartServerResponse(('ok', '0', 'null:')),
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
768
            request.execute(''))
2018.5.50 by Wouter van Heyst
Add SmartServerBranchRequestLastRevisionInfo method.
769
770
    def test_not_empty(self):
771
        """For a non-empty branch, the result is ('ok', 'revno', 'revid')."""
772
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
773
        request = smart_branch.SmartServerBranchRequestLastRevisionInfo(backing)
2018.5.50 by Wouter van Heyst
Add SmartServerBranchRequestLastRevisionInfo method.
774
        tree = self.make_branch_and_memory_tree('.')
775
        tree.lock_write()
776
        tree.add('')
2018.5.148 by Andrew Bennetts
Fix all the DeprecationWarnings in test_smart caused by unicode revision IDs.
777
        rev_id_utf8 = u'\xc8'.encode('utf-8')
2018.5.50 by Wouter van Heyst
Add SmartServerBranchRequestLastRevisionInfo method.
778
        r1 = tree.commit('1st commit')
2018.5.148 by Andrew Bennetts
Fix all the DeprecationWarnings in test_smart caused by unicode revision IDs.
779
        r2 = tree.commit('2nd commit', rev_id=rev_id_utf8)
2018.5.50 by Wouter van Heyst
Add SmartServerBranchRequestLastRevisionInfo method.
780
        tree.unlock()
781
        self.assertEqual(
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
782
            smart_req.SmartServerResponse(('ok', '2', rev_id_utf8)),
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
783
            request.execute(''))
784
785
6263.1.2 by Jelmer Vernooij
Add ``Branch.revision_id_to_revno`` smart verb.
786
class TestSmartServerBranchRequestRevisionIdToRevno(
787
    tests.TestCaseWithMemoryTransport):
788
789
    def test_null(self):
790
        backing = self.get_transport()
791
        request = smart_branch.SmartServerBranchRequestRevisionIdToRevno(
792
            backing)
793
        self.make_branch('.')
794
        self.assertEqual(smart_req.SmartServerResponse(('ok', '0')),
795
            request.execute('', 'null:'))
796
797
    def test_simple(self):
798
        backing = self.get_transport()
799
        request = smart_branch.SmartServerBranchRequestRevisionIdToRevno(
800
            backing)
801
        tree = self.make_branch_and_memory_tree('.')
802
        tree.lock_write()
803
        tree.add('')
804
        r1 = tree.commit('1st commit')
805
        tree.unlock()
806
        self.assertEqual(
807
            smart_req.SmartServerResponse(('ok', '1')),
808
            request.execute('', r1))
809
810
    def test_not_found(self):
811
        backing = self.get_transport()
812
        request = smart_branch.SmartServerBranchRequestRevisionIdToRevno(
813
            backing)
814
        branch = self.make_branch('.')
815
        self.assertEqual(
816
            smart_req.FailedSmartServerResponse(
817
                ('NoSuchRevision', 'idontexist')),
818
            request.execute('', 'idontexist'))
819
820
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
821
class TestSmartServerBranchRequestGetConfigFile(
822
    tests.TestCaseWithMemoryTransport):
2018.5.59 by Robert Collins
Get BranchConfig working somewhat on RemoteBranches (Robert Collins, Vincent Ladeuil).
823
824
    def test_default(self):
825
        """With no file, we get empty content."""
826
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
827
        request = smart_branch.SmartServerBranchGetConfigFile(backing)
2018.5.59 by Robert Collins
Get BranchConfig working somewhat on RemoteBranches (Robert Collins, Vincent Ladeuil).
828
        branch = self.make_branch('.')
829
        # there should be no file by default
830
        content = ''
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
831
        self.assertEqual(smart_req.SmartServerResponse(('ok', ), content),
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
832
            request.execute(''))
2018.5.59 by Robert Collins
Get BranchConfig working somewhat on RemoteBranches (Robert Collins, Vincent Ladeuil).
833
834
    def test_with_content(self):
835
        # SmartServerBranchGetConfigFile should return the content from
836
        # branch.control_files.get('branch.conf') for now - in the future it may
3943.8.1 by Marius Kruger
remove all trailing whitespace from bzr source
837
        # perform more complex processing.
2018.5.59 by Robert Collins
Get BranchConfig working somewhat on RemoteBranches (Robert Collins, Vincent Ladeuil).
838
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
839
        request = smart_branch.SmartServerBranchGetConfigFile(backing)
2018.5.59 by Robert Collins
Get BranchConfig working somewhat on RemoteBranches (Robert Collins, Vincent Ladeuil).
840
        branch = self.make_branch('.')
3407.2.5 by Martin Pool
Deprecate LockableFiles.put_utf8
841
        branch._transport.put_bytes('branch.conf', 'foo bar baz')
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
842
        self.assertEqual(smart_req.SmartServerResponse(('ok', ), 'foo bar baz'),
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
843
            request.execute(''))
844
845
4226.2.1 by Robert Collins
Set branch config options via a smart method.
846
class TestLockedBranch(tests.TestCaseWithMemoryTransport):
847
848
    def get_lock_tokens(self, branch):
5200.3.3 by Robert Collins
Lock methods on ``Tree``, ``Branch`` and ``Repository`` are now
849
        branch_token = branch.lock_write().branch_token
850
        repo_token = branch.repository.lock_write().repository_token
4226.2.1 by Robert Collins
Set branch config options via a smart method.
851
        branch.repository.unlock()
852
        return branch_token, repo_token
853
854
6270.1.17 by Jelmer Vernooij
s/set_config_file/put_config_file.
855
class TestSmartServerBranchRequestPutConfigFile(TestLockedBranch):
6270.1.9 by Jelmer Vernooij
add Branch.set_config_file.
856
857
    def test_with_content(self):
858
        backing = self.get_transport()
6270.1.17 by Jelmer Vernooij
s/set_config_file/put_config_file.
859
        request = smart_branch.SmartServerBranchPutConfigFile(backing)
6270.1.9 by Jelmer Vernooij
add Branch.set_config_file.
860
        branch = self.make_branch('.')
861
        branch_token, repo_token = self.get_lock_tokens(branch)
6270.1.10 by Jelmer Vernooij
Fix testing Branch.set_config_file.
862
        self.assertIs(None, request.execute('', branch_token, repo_token))
6270.1.9 by Jelmer Vernooij
add Branch.set_config_file.
863
        self.assertEqual(
864
            smart_req.SmartServerResponse(('ok', )),
865
            request.do_body('foo bar baz'))
866
        self.assertEquals(
867
            branch.control_transport.get_bytes('branch.conf'),
868
            'foo bar baz')
869
        branch.unlock()
870
871
4226.2.1 by Robert Collins
Set branch config options via a smart method.
872
class TestSmartServerBranchRequestSetConfigOption(TestLockedBranch):
873
874
    def test_value_name(self):
875
        branch = self.make_branch('.')
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
876
        request = smart_branch.SmartServerBranchRequestSetConfigOption(
4226.2.1 by Robert Collins
Set branch config options via a smart method.
877
            branch.bzrdir.root_transport)
878
        branch_token, repo_token = self.get_lock_tokens(branch)
879
        config = branch._get_config()
880
        result = request.execute('', branch_token, repo_token, 'bar', 'foo',
881
            '')
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
882
        self.assertEqual(smart_req.SuccessfulSmartServerResponse(()), result)
4226.2.1 by Robert Collins
Set branch config options via a smart method.
883
        self.assertEqual('bar', config.get_option('foo'))
4327.1.10 by Vincent Ladeuil
Fix 10 more lock-related test failures.
884
        # Cleanup
885
        branch.unlock()
4226.2.1 by Robert Collins
Set branch config options via a smart method.
886
887
    def test_value_name_section(self):
888
        branch = self.make_branch('.')
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
889
        request = smart_branch.SmartServerBranchRequestSetConfigOption(
4226.2.1 by Robert Collins
Set branch config options via a smart method.
890
            branch.bzrdir.root_transport)
891
        branch_token, repo_token = self.get_lock_tokens(branch)
892
        config = branch._get_config()
893
        result = request.execute('', branch_token, repo_token, 'bar', 'foo',
894
            'gam')
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
895
        self.assertEqual(smart_req.SuccessfulSmartServerResponse(()), result)
4226.2.1 by Robert Collins
Set branch config options via a smart method.
896
        self.assertEqual('bar', config.get_option('foo', 'gam'))
4327.1.10 by Vincent Ladeuil
Fix 10 more lock-related test failures.
897
        # Cleanup
898
        branch.unlock()
4226.2.1 by Robert Collins
Set branch config options via a smart method.
899
900
5227.1.2 by Andrew Bennetts
Add Branch.set_config_option_dict RPC (and VFS fallback), fixes #430382.
901
class TestSmartServerBranchRequestSetConfigOptionDict(TestLockedBranch):
902
903
    def setUp(self):
904
        TestLockedBranch.setUp(self)
905
        # A dict with non-ascii keys and values to exercise unicode
906
        # roundtripping.
907
        self.encoded_value_dict = (
908
            'd5:ascii1:a11:unicode \xe2\x8c\x9a3:\xe2\x80\xbde')
909
        self.value_dict = {
910
            'ascii': 'a', u'unicode \N{WATCH}': u'\N{INTERROBANG}'}
911
912
    def test_value_name(self):
913
        branch = self.make_branch('.')
914
        request = smart_branch.SmartServerBranchRequestSetConfigOptionDict(
915
            branch.bzrdir.root_transport)
916
        branch_token, repo_token = self.get_lock_tokens(branch)
917
        config = branch._get_config()
918
        result = request.execute('', branch_token, repo_token,
919
            self.encoded_value_dict, 'foo', '')
920
        self.assertEqual(smart_req.SuccessfulSmartServerResponse(()), result)
921
        self.assertEqual(self.value_dict, config.get_option('foo'))
922
        # Cleanup
923
        branch.unlock()
924
925
    def test_value_name_section(self):
926
        branch = self.make_branch('.')
927
        request = smart_branch.SmartServerBranchRequestSetConfigOptionDict(
928
            branch.bzrdir.root_transport)
929
        branch_token, repo_token = self.get_lock_tokens(branch)
930
        config = branch._get_config()
931
        result = request.execute('', branch_token, repo_token,
932
            self.encoded_value_dict, 'foo', 'gam')
933
        self.assertEqual(smart_req.SuccessfulSmartServerResponse(()), result)
934
        self.assertEqual(self.value_dict, config.get_option('foo', 'gam'))
935
        # Cleanup
936
        branch.unlock()
937
938
4556.2.2 by Andrew Bennetts
Handle failures more gracefully.
939
class TestSmartServerBranchRequestSetTagsBytes(TestLockedBranch):
940
    # Only called when the branch format and tags match [yay factory
941
    # methods] so only need to test straight forward cases.
942
943
    def test_set_bytes(self):
944
        base_branch = self.make_branch('base')
945
        tag_bytes = base_branch._get_tags_bytes()
946
        # get_lock_tokens takes out a lock.
947
        branch_token, repo_token = self.get_lock_tokens(base_branch)
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
948
        request = smart_branch.SmartServerBranchSetTagsBytes(
4556.2.2 by Andrew Bennetts
Handle failures more gracefully.
949
            self.get_transport())
950
        response = request.execute('base', branch_token, repo_token)
951
        self.assertEqual(None, response)
952
        response = request.do_chunk(tag_bytes)
953
        self.assertEqual(None, response)
954
        response = request.do_end()
955
        self.assertEquals(
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
956
            smart_req.SuccessfulSmartServerResponse(()), response)
4556.2.2 by Andrew Bennetts
Handle failures more gracefully.
957
        base_branch.unlock()
958
959
    def test_lock_failed(self):
960
        base_branch = self.make_branch('base')
961
        base_branch.lock_write()
962
        tag_bytes = base_branch._get_tags_bytes()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
963
        request = smart_branch.SmartServerBranchSetTagsBytes(
4556.2.2 by Andrew Bennetts
Handle failures more gracefully.
964
            self.get_transport())
965
        self.assertRaises(errors.TokenMismatch, request.execute,
966
            'base', 'wrong token', 'wrong token')
967
        # The request handler will keep processing the message parts, so even
968
        # if the request fails immediately do_chunk and do_end are still
969
        # called.
970
        request.do_chunk(tag_bytes)
971
        request.do_end()
972
        base_branch.unlock()
973
974
975
4226.2.1 by Robert Collins
Set branch config options via a smart method.
976
class SetLastRevisionTestBase(TestLockedBranch):
3441.5.30 by Andrew Bennetts
Improve tests for all Branch.set_last_revision* verbs.
977
    """Base test case for verbs that implement set_last_revision."""
978
979
    def setUp(self):
980
        tests.TestCaseWithMemoryTransport.setUp(self)
981
        backing_transport = self.get_transport()
982
        self.request = self.request_class(backing_transport)
983
        self.tree = self.make_branch_and_memory_tree('.')
984
985
    def lock_branch(self):
4226.2.1 by Robert Collins
Set branch config options via a smart method.
986
        return self.get_lock_tokens(self.tree.branch)
3441.5.30 by Andrew Bennetts
Improve tests for all Branch.set_last_revision* verbs.
987
988
    def unlock_branch(self):
989
        self.tree.branch.unlock()
3943.8.1 by Marius Kruger
remove all trailing whitespace from bzr source
990
3441.5.30 by Andrew Bennetts
Improve tests for all Branch.set_last_revision* verbs.
991
    def set_last_revision(self, revision_id, revno):
992
        branch_token, repo_token = self.lock_branch()
993
        response = self._set_last_revision(
994
            revision_id, revno, branch_token, repo_token)
995
        self.unlock_branch()
996
        return response
997
998
    def assertRequestSucceeds(self, revision_id, revno):
999
        response = self.set_last_revision(revision_id, revno)
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1000
        self.assertEqual(smart_req.SuccessfulSmartServerResponse(('ok',)),
1001
                         response)
3441.5.30 by Andrew Bennetts
Improve tests for all Branch.set_last_revision* verbs.
1002
3943.8.1 by Marius Kruger
remove all trailing whitespace from bzr source
1003
3441.5.30 by Andrew Bennetts
Improve tests for all Branch.set_last_revision* verbs.
1004
class TestSetLastRevisionVerbMixin(object):
1005
    """Mixin test case for verbs that implement set_last_revision."""
1006
1007
    def test_set_null_to_null(self):
1008
        """An empty branch can have its last revision set to 'null:'."""
1009
        self.assertRequestSucceeds('null:', 0)
1010
1011
    def test_NoSuchRevision(self):
1012
        """If the revision_id is not present, the verb returns NoSuchRevision.
1013
        """
1014
        revision_id = 'non-existent revision'
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1015
        self.assertEqual(smart_req.FailedSmartServerResponse(('NoSuchRevision',
1016
                                                              revision_id)),
1017
                         self.set_last_revision(revision_id, 1))
3441.5.30 by Andrew Bennetts
Improve tests for all Branch.set_last_revision* verbs.
1018
1019
    def make_tree_with_two_commits(self):
1020
        self.tree.lock_write()
1021
        self.tree.add('')
1022
        rev_id_utf8 = u'\xc8'.encode('utf-8')
1023
        r1 = self.tree.commit('1st commit', rev_id=rev_id_utf8)
1024
        r2 = self.tree.commit('2nd commit', rev_id='rev-2')
1025
        self.tree.unlock()
1026
1027
    def test_branch_last_revision_info_is_updated(self):
1028
        """A branch's tip can be set to a revision that is present in its
1029
        repository.
1030
        """
1031
        # Make a branch with an empty revision history, but two revisions in
1032
        # its repository.
1033
        self.make_tree_with_two_commits()
1034
        rev_id_utf8 = u'\xc8'.encode('utf-8')
5718.7.4 by Jelmer Vernooij
Branch.set_revision_history.
1035
        self.tree.branch.set_last_revision_info(0, 'null:')
3441.5.30 by Andrew Bennetts
Improve tests for all Branch.set_last_revision* verbs.
1036
        self.assertEqual(
1037
            (0, 'null:'), self.tree.branch.last_revision_info())
1038
        # We can update the branch to a revision that is present in the
1039
        # repository.
1040
        self.assertRequestSucceeds(rev_id_utf8, 1)
1041
        self.assertEqual(
1042
            (1, rev_id_utf8), self.tree.branch.last_revision_info())
1043
1044
    def test_branch_last_revision_info_rewind(self):
1045
        """A branch's tip can be set to a revision that is an ancestor of the
1046
        current tip.
1047
        """
1048
        self.make_tree_with_two_commits()
1049
        rev_id_utf8 = u'\xc8'.encode('utf-8')
1050
        self.assertEqual(
1051
            (2, 'rev-2'), self.tree.branch.last_revision_info())
1052
        self.assertRequestSucceeds(rev_id_utf8, 1)
1053
        self.assertEqual(
1054
            (1, rev_id_utf8), self.tree.branch.last_revision_info())
1055
3577.1.1 by Andrew Bennetts
Cherry-pick TipChangeRejected changes from pre-branch-tip-changed-hook loom.
1056
    def test_TipChangeRejected(self):
1057
        """If a pre_change_branch_tip hook raises TipChangeRejected, the verb
1058
        returns TipChangeRejected.
1059
        """
1060
        rejection_message = u'rejection message\N{INTERROBANG}'
1061
        def hook_that_rejects(params):
1062
            raise errors.TipChangeRejected(rejection_message)
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1063
        _mod_branch.Branch.hooks.install_named_hook(
3577.1.1 by Andrew Bennetts
Cherry-pick TipChangeRejected changes from pre-branch-tip-changed-hook loom.
1064
            'pre_change_branch_tip', hook_that_rejects, None)
1065
        self.assertEqual(
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1066
            smart_req.FailedSmartServerResponse(
3577.1.1 by Andrew Bennetts
Cherry-pick TipChangeRejected changes from pre-branch-tip-changed-hook loom.
1067
                ('TipChangeRejected', rejection_message.encode('utf-8'))),
1068
            self.set_last_revision('null:', 0))
1069
3441.5.30 by Andrew Bennetts
Improve tests for all Branch.set_last_revision* verbs.
1070
3441.5.6 by Andrew Bennetts
Greatly simplify RemoteBranch.update_revisions. Still needs more tests.
1071
class TestSmartServerBranchRequestSetLastRevision(
3441.5.30 by Andrew Bennetts
Improve tests for all Branch.set_last_revision* verbs.
1072
        SetLastRevisionTestBase, TestSetLastRevisionVerbMixin):
1073
    """Tests for Branch.set_last_revision verb."""
3441.5.6 by Andrew Bennetts
Greatly simplify RemoteBranch.update_revisions. Still needs more tests.
1074
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1075
    request_class = smart_branch.SmartServerBranchRequestSetLastRevision
3441.5.6 by Andrew Bennetts
Greatly simplify RemoteBranch.update_revisions. Still needs more tests.
1076
3441.5.30 by Andrew Bennetts
Improve tests for all Branch.set_last_revision* verbs.
1077
    def _set_last_revision(self, revision_id, revno, branch_token, repo_token):
1078
        return self.request.execute(
1079
            '', branch_token, repo_token, revision_id)
1080
1081
1082
class TestSmartServerBranchRequestSetLastRevisionInfo(
1083
        SetLastRevisionTestBase, TestSetLastRevisionVerbMixin):
1084
    """Tests for Branch.set_last_revision_info verb."""
1085
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1086
    request_class = smart_branch.SmartServerBranchRequestSetLastRevisionInfo
3441.5.30 by Andrew Bennetts
Improve tests for all Branch.set_last_revision* verbs.
1087
1088
    def _set_last_revision(self, revision_id, revno, branch_token, repo_token):
1089
        return self.request.execute(
1090
            '', branch_token, repo_token, revno, revision_id)
1091
1092
    def test_NoSuchRevision(self):
1093
        """Branch.set_last_revision_info does not have to return
1094
        NoSuchRevision if the revision_id is absent.
1095
        """
1096
        raise tests.TestNotApplicable()
3441.5.6 by Andrew Bennetts
Greatly simplify RemoteBranch.update_revisions. Still needs more tests.
1097
1098
3441.5.25 by Andrew Bennetts
Rename Branch.set_last_revision_descendant verb to Branch.set_last_revision_ex. It's a cop out, but at least it's not misleading.
1099
class TestSmartServerBranchRequestSetLastRevisionEx(
3441.5.30 by Andrew Bennetts
Improve tests for all Branch.set_last_revision* verbs.
1100
        SetLastRevisionTestBase, TestSetLastRevisionVerbMixin):
1101
    """Tests for Branch.set_last_revision_ex verb."""
3441.5.6 by Andrew Bennetts
Greatly simplify RemoteBranch.update_revisions. Still needs more tests.
1102
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1103
    request_class = smart_branch.SmartServerBranchRequestSetLastRevisionEx
3441.5.6 by Andrew Bennetts
Greatly simplify RemoteBranch.update_revisions. Still needs more tests.
1104
3441.5.30 by Andrew Bennetts
Improve tests for all Branch.set_last_revision* verbs.
1105
    def _set_last_revision(self, revision_id, revno, branch_token, repo_token):
1106
        return self.request.execute(
1107
            '', branch_token, repo_token, revision_id, 0, 0)
1108
1109
    def assertRequestSucceeds(self, revision_id, revno):
1110
        response = self.set_last_revision(revision_id, revno)
1111
        self.assertEqual(
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1112
            smart_req.SuccessfulSmartServerResponse(('ok', revno, revision_id)),
3441.5.30 by Andrew Bennetts
Improve tests for all Branch.set_last_revision* verbs.
1113
            response)
3943.8.1 by Marius Kruger
remove all trailing whitespace from bzr source
1114
3441.5.30 by Andrew Bennetts
Improve tests for all Branch.set_last_revision* verbs.
1115
    def test_branch_last_revision_info_rewind(self):
1116
        """A branch's tip can be set to a revision that is an ancestor of the
1117
        current tip, but only if allow_overwrite_descendant is passed.
1118
        """
1119
        self.make_tree_with_two_commits()
3441.5.6 by Andrew Bennetts
Greatly simplify RemoteBranch.update_revisions. Still needs more tests.
1120
        rev_id_utf8 = u'\xc8'.encode('utf-8')
3441.5.30 by Andrew Bennetts
Improve tests for all Branch.set_last_revision* verbs.
1121
        self.assertEqual(
1122
            (2, 'rev-2'), self.tree.branch.last_revision_info())
1123
        # If allow_overwrite_descendant flag is 0, then trying to set the tip
1124
        # to an older revision ID has no effect.
1125
        branch_token, repo_token = self.lock_branch()
1126
        response = self.request.execute(
1127
            '', branch_token, repo_token, rev_id_utf8, 0, 0)
1128
        self.assertEqual(
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1129
            smart_req.SuccessfulSmartServerResponse(('ok', 2, 'rev-2')),
3441.5.30 by Andrew Bennetts
Improve tests for all Branch.set_last_revision* verbs.
1130
            response)
1131
        self.assertEqual(
1132
            (2, 'rev-2'), self.tree.branch.last_revision_info())
1133
1134
        # If allow_overwrite_descendant flag is 1, then setting the tip to an
1135
        # ancestor works.
1136
        response = self.request.execute(
1137
            '', branch_token, repo_token, rev_id_utf8, 0, 1)
1138
        self.assertEqual(
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1139
            smart_req.SuccessfulSmartServerResponse(('ok', 1, rev_id_utf8)),
3441.5.30 by Andrew Bennetts
Improve tests for all Branch.set_last_revision* verbs.
1140
            response)
1141
        self.unlock_branch()
1142
        self.assertEqual(
1143
            (1, rev_id_utf8), self.tree.branch.last_revision_info())
1144
3441.5.31 by Andrew Bennetts
Add test for allow_diverged flag.
1145
    def make_branch_with_divergent_history(self):
1146
        """Make a branch with divergent history in its repo.
1147
1148
        The branch's tip will be 'child-2', and the repo will also contain
1149
        'child-1', which diverges from a common base revision.
3441.5.30 by Andrew Bennetts
Improve tests for all Branch.set_last_revision* verbs.
1150
        """
1151
        self.tree.lock_write()
1152
        self.tree.add('')
1153
        r1 = self.tree.commit('1st commit')
1154
        revno_1, revid_1 = self.tree.branch.last_revision_info()
1155
        r2 = self.tree.commit('2nd commit', rev_id='child-1')
3441.5.6 by Andrew Bennetts
Greatly simplify RemoteBranch.update_revisions. Still needs more tests.
1156
        # Undo the second commit
3441.5.30 by Andrew Bennetts
Improve tests for all Branch.set_last_revision* verbs.
1157
        self.tree.branch.set_last_revision_info(revno_1, revid_1)
1158
        self.tree.set_parent_ids([revid_1])
3441.5.6 by Andrew Bennetts
Greatly simplify RemoteBranch.update_revisions. Still needs more tests.
1159
        # Make a new second commit, child-2.  child-2 has diverged from
1160
        # child-1.
3441.5.30 by Andrew Bennetts
Improve tests for all Branch.set_last_revision* verbs.
1161
        new_r2 = self.tree.commit('2nd commit', rev_id='child-2')
1162
        self.tree.unlock()
3943.8.1 by Marius Kruger
remove all trailing whitespace from bzr source
1163
3441.5.31 by Andrew Bennetts
Add test for allow_diverged flag.
1164
    def test_not_allow_diverged(self):
1165
        """If allow_diverged is not passed, then setting a divergent history
1166
        returns a Diverged error.
1167
        """
1168
        self.make_branch_with_divergent_history()
3297.4.3 by Andrew Bennetts
Add more tests, handle NoSuchRevision in case the remote branch's format can raise it.
1169
        self.assertEqual(
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1170
            smart_req.FailedSmartServerResponse(('Diverged',)),
3441.5.30 by Andrew Bennetts
Improve tests for all Branch.set_last_revision* verbs.
1171
            self.set_last_revision('child-1', 2))
1172
        # The branch tip was not changed.
1173
        self.assertEqual('child-2', self.tree.branch.last_revision())
2892.2.1 by Andrew Bennetts
Add Branch.set_last_revision_info smart method, and make the RemoteBranch client use it.
1174
3441.5.31 by Andrew Bennetts
Add test for allow_diverged flag.
1175
    def test_allow_diverged(self):
1176
        """If allow_diverged is passed, then setting a divergent history
1177
        succeeds.
1178
        """
1179
        self.make_branch_with_divergent_history()
1180
        branch_token, repo_token = self.lock_branch()
1181
        response = self.request.execute(
1182
            '', branch_token, repo_token, 'child-1', 1, 0)
1183
        self.assertEqual(
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1184
            smart_req.SuccessfulSmartServerResponse(('ok', 2, 'child-1')),
3441.5.31 by Andrew Bennetts
Add test for allow_diverged flag.
1185
            response)
1186
        self.unlock_branch()
1187
        # The branch tip was changed.
1188
        self.assertEqual('child-1', self.tree.branch.last_revision())
1189
2892.2.1 by Andrew Bennetts
Add Branch.set_last_revision_info smart method, and make the RemoteBranch client use it.
1190
6280.4.4 by Jelmer Vernooij
Add Branch.break_lock.
1191
class TestSmartServerBranchBreakLock(tests.TestCaseWithMemoryTransport):
1192
1193
    def test_lock_to_break(self):
1194
        base_branch = self.make_branch('base')
1195
        request = smart_branch.SmartServerBranchBreakLock(
1196
            self.get_transport())
1197
        base_branch.lock_write()
1198
        self.assertEqual(
1199
            smart_req.SuccessfulSmartServerResponse(('ok', ), None),
1200
            request.execute('base'))
1201
1202
    def test_nothing_to_break(self):
1203
        base_branch = self.make_branch('base')
1204
        request = smart_branch.SmartServerBranchBreakLock(
1205
            self.get_transport())
1206
        self.assertEqual(
1207
            smart_req.SuccessfulSmartServerResponse(('ok', ), None),
1208
            request.execute('base'))
1209
1210
4078.2.1 by Robert Collins
Add a Branch.get_parent remote call for RemoteBranch.
1211
class TestSmartServerBranchRequestGetParent(tests.TestCaseWithMemoryTransport):
1212
1213
    def test_get_parent_none(self):
1214
        base_branch = self.make_branch('base')
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1215
        request = smart_branch.SmartServerBranchGetParent(self.get_transport())
4078.2.1 by Robert Collins
Add a Branch.get_parent remote call for RemoteBranch.
1216
        response = request.execute('base')
1217
        self.assertEquals(
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1218
            smart_req.SuccessfulSmartServerResponse(('',)), response)
4078.2.1 by Robert Collins
Add a Branch.get_parent remote call for RemoteBranch.
1219
1220
    def test_get_parent_something(self):
1221
        base_branch = self.make_branch('base')
1222
        base_branch.set_parent(self.get_url('foo'))
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1223
        request = smart_branch.SmartServerBranchGetParent(self.get_transport())
4078.2.1 by Robert Collins
Add a Branch.get_parent remote call for RemoteBranch.
1224
        response = request.execute('base')
1225
        self.assertEquals(
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1226
            smart_req.SuccessfulSmartServerResponse(("../foo",)),
4078.2.1 by Robert Collins
Add a Branch.get_parent remote call for RemoteBranch.
1227
            response)
1228
1229
5200.3.3 by Robert Collins
Lock methods on ``Tree``, ``Branch`` and ``Repository`` are now
1230
class TestSmartServerBranchRequestSetParent(TestLockedBranch):
4288.1.7 by Robert Collins
Add new remote server verb Branch.set_parent_location, dropping roundtrips further on push operations.
1231
1232
    def test_set_parent_none(self):
1233
        branch = self.make_branch('base', format="1.9")
4288.1.9 by Robert Collins
Fix up test usable of _set_parent_location on unlocked branches.
1234
        branch.lock_write()
4288.1.7 by Robert Collins
Add new remote server verb Branch.set_parent_location, dropping roundtrips further on push operations.
1235
        branch._set_parent_location('foo')
4288.1.9 by Robert Collins
Fix up test usable of _set_parent_location on unlocked branches.
1236
        branch.unlock()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1237
        request = smart_branch.SmartServerBranchRequestSetParentLocation(
4288.1.7 by Robert Collins
Add new remote server verb Branch.set_parent_location, dropping roundtrips further on push operations.
1238
            self.get_transport())
5200.3.3 by Robert Collins
Lock methods on ``Tree``, ``Branch`` and ``Repository`` are now
1239
        branch_token, repo_token = self.get_lock_tokens(branch)
4288.1.7 by Robert Collins
Add new remote server verb Branch.set_parent_location, dropping roundtrips further on push operations.
1240
        try:
1241
            response = request.execute('base', branch_token, repo_token, '')
1242
        finally:
1243
            branch.unlock()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1244
        self.assertEqual(smart_req.SuccessfulSmartServerResponse(()), response)
4288.1.7 by Robert Collins
Add new remote server verb Branch.set_parent_location, dropping roundtrips further on push operations.
1245
        self.assertEqual(None, branch.get_parent())
1246
1247
    def test_set_parent_something(self):
1248
        branch = self.make_branch('base', format="1.9")
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1249
        request = smart_branch.SmartServerBranchRequestSetParentLocation(
4288.1.7 by Robert Collins
Add new remote server verb Branch.set_parent_location, dropping roundtrips further on push operations.
1250
            self.get_transport())
5200.3.3 by Robert Collins
Lock methods on ``Tree``, ``Branch`` and ``Repository`` are now
1251
        branch_token, repo_token = self.get_lock_tokens(branch)
4288.1.7 by Robert Collins
Add new remote server verb Branch.set_parent_location, dropping roundtrips further on push operations.
1252
        try:
1253
            response = request.execute('base', branch_token, repo_token,
1254
            'http://bar/')
1255
        finally:
1256
            branch.unlock()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1257
        self.assertEqual(smart_req.SuccessfulSmartServerResponse(()), response)
4288.1.7 by Robert Collins
Add new remote server verb Branch.set_parent_location, dropping roundtrips further on push operations.
1258
        self.assertEqual('http://bar/', branch.get_parent())
1259
1260
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1261
class TestSmartServerBranchRequestGetTagsBytes(
1262
    tests.TestCaseWithMemoryTransport):
4556.2.2 by Andrew Bennetts
Handle failures more gracefully.
1263
    # Only called when the branch format and tags match [yay factory
1264
    # methods] so only need to test straight forward cases.
4084.2.1 by Robert Collins
Make accessing a branch.tags.get_tag_dict use a smart[er] method rather than VFS calls and real objects.
1265
1266
    def test_get_bytes(self):
1267
        base_branch = self.make_branch('base')
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1268
        request = smart_branch.SmartServerBranchGetTagsBytes(
4084.2.1 by Robert Collins
Make accessing a branch.tags.get_tag_dict use a smart[er] method rather than VFS calls and real objects.
1269
            self.get_transport())
1270
        response = request.execute('base')
1271
        self.assertEquals(
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1272
            smart_req.SuccessfulSmartServerResponse(('',)), response)
4084.2.1 by Robert Collins
Make accessing a branch.tags.get_tag_dict use a smart[er] method rather than VFS calls and real objects.
1273
1274
3691.2.5 by Martin Pool
Add Branch.get_stacked_on_url rpc and tests for same
1275
class TestSmartServerBranchRequestGetStackedOnURL(tests.TestCaseWithMemoryTransport):
1276
1277
    def test_get_stacked_on_url(self):
1278
        base_branch = self.make_branch('base', format='1.6')
1279
        stacked_branch = self.make_branch('stacked', format='1.6')
1280
        # typically should be relative
1281
        stacked_branch.set_stacked_on_url('../base')
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1282
        request = smart_branch.SmartServerBranchRequestGetStackedOnURL(
3691.2.5 by Martin Pool
Add Branch.get_stacked_on_url rpc and tests for same
1283
            self.get_transport())
1284
        response = request.execute('stacked')
1285
        self.assertEquals(
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1286
            smart_req.SmartServerResponse(('ok', '../base')),
3691.2.5 by Martin Pool
Add Branch.get_stacked_on_url rpc and tests for same
1287
            response)
1288
1289
5200.3.3 by Robert Collins
Lock methods on ``Tree``, ``Branch`` and ``Repository`` are now
1290
class TestSmartServerBranchRequestLockWrite(TestLockedBranch):
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
1291
1292
    def setUp(self):
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
1293
        tests.TestCaseWithMemoryTransport.setUp(self)
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
1294
1295
    def test_lock_write_on_unlocked_branch(self):
1296
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1297
        request = smart_branch.SmartServerBranchRequestLockWrite(backing)
3015.2.12 by Robert Collins
Make test_smart use specific formats as needed to exercise locked and unlocked repositories.
1298
        branch = self.make_branch('.', format='knit')
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
1299
        repository = branch.repository
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
1300
        response = request.execute('')
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
1301
        branch_nonce = branch.control_files._lock.peek().get('nonce')
1302
        repository_nonce = repository.control_files._lock.peek().get('nonce')
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1303
        self.assertEqual(smart_req.SmartServerResponse(
1304
                ('ok', branch_nonce, repository_nonce)),
1305
                         response)
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
1306
        # The branch (and associated repository) is now locked.  Verify that
1307
        # with a new branch object.
1308
        new_branch = repository.bzrdir.open_branch()
1309
        self.assertRaises(errors.LockContention, new_branch.lock_write)
4327.1.10 by Vincent Ladeuil
Fix 10 more lock-related test failures.
1310
        # Cleanup
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1311
        request = smart_branch.SmartServerBranchRequestUnlock(backing)
4327.1.10 by Vincent Ladeuil
Fix 10 more lock-related test failures.
1312
        response = request.execute('', branch_nonce, repository_nonce)
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
1313
1314
    def test_lock_write_on_locked_branch(self):
1315
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1316
        request = smart_branch.SmartServerBranchRequestLockWrite(backing)
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
1317
        branch = self.make_branch('.')
5200.3.3 by Robert Collins
Lock methods on ``Tree``, ``Branch`` and ``Repository`` are now
1318
        branch_token = branch.lock_write().branch_token
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
1319
        branch.leave_lock_in_place()
1320
        branch.unlock()
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
1321
        response = request.execute('')
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
1322
        self.assertEqual(
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1323
            smart_req.SmartServerResponse(('LockContention',)), response)
4327.1.10 by Vincent Ladeuil
Fix 10 more lock-related test failures.
1324
        # Cleanup
1325
        branch.lock_write(branch_token)
1326
        branch.dont_leave_lock_in_place()
1327
        branch.unlock()
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
1328
1329
    def test_lock_write_with_tokens_on_locked_branch(self):
1330
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1331
        request = smart_branch.SmartServerBranchRequestLockWrite(backing)
3015.2.12 by Robert Collins
Make test_smart use specific formats as needed to exercise locked and unlocked repositories.
1332
        branch = self.make_branch('.', format='knit')
5200.3.3 by Robert Collins
Lock methods on ``Tree``, ``Branch`` and ``Repository`` are now
1333
        branch_token, repo_token = self.get_lock_tokens(branch)
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
1334
        branch.leave_lock_in_place()
1335
        branch.repository.leave_lock_in_place()
1336
        branch.unlock()
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
1337
        response = request.execute('',
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
1338
                                   branch_token, repo_token)
1339
        self.assertEqual(
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1340
            smart_req.SmartServerResponse(('ok', branch_token, repo_token)),
1341
            response)
4327.1.10 by Vincent Ladeuil
Fix 10 more lock-related test failures.
1342
        # Cleanup
1343
        branch.repository.lock_write(repo_token)
1344
        branch.repository.dont_leave_lock_in_place()
1345
        branch.repository.unlock()
1346
        branch.lock_write(branch_token)
1347
        branch.dont_leave_lock_in_place()
1348
        branch.unlock()
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
1349
1350
    def test_lock_write_with_mismatched_tokens_on_locked_branch(self):
1351
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1352
        request = smart_branch.SmartServerBranchRequestLockWrite(backing)
3015.2.12 by Robert Collins
Make test_smart use specific formats as needed to exercise locked and unlocked repositories.
1353
        branch = self.make_branch('.', format='knit')
5200.3.3 by Robert Collins
Lock methods on ``Tree``, ``Branch`` and ``Repository`` are now
1354
        branch_token, repo_token = self.get_lock_tokens(branch)
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
1355
        branch.leave_lock_in_place()
1356
        branch.repository.leave_lock_in_place()
1357
        branch.unlock()
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
1358
        response = request.execute('',
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
1359
                                   branch_token+'xxx', repo_token)
1360
        self.assertEqual(
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1361
            smart_req.SmartServerResponse(('TokenMismatch',)), response)
4327.1.10 by Vincent Ladeuil
Fix 10 more lock-related test failures.
1362
        # Cleanup
1363
        branch.repository.lock_write(repo_token)
1364
        branch.repository.dont_leave_lock_in_place()
1365
        branch.repository.unlock()
1366
        branch.lock_write(branch_token)
1367
        branch.dont_leave_lock_in_place()
1368
        branch.unlock()
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
1369
1370
    def test_lock_write_on_locked_repo(self):
1371
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1372
        request = smart_branch.SmartServerBranchRequestLockWrite(backing)
3015.2.12 by Robert Collins
Make test_smart use specific formats as needed to exercise locked and unlocked repositories.
1373
        branch = self.make_branch('.', format='knit')
4327.1.10 by Vincent Ladeuil
Fix 10 more lock-related test failures.
1374
        repo = branch.repository
5200.3.3 by Robert Collins
Lock methods on ``Tree``, ``Branch`` and ``Repository`` are now
1375
        repo_token = repo.lock_write().repository_token
4327.1.10 by Vincent Ladeuil
Fix 10 more lock-related test failures.
1376
        repo.leave_lock_in_place()
1377
        repo.unlock()
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
1378
        response = request.execute('')
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
1379
        self.assertEqual(
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1380
            smart_req.SmartServerResponse(('LockContention',)), response)
4327.1.10 by Vincent Ladeuil
Fix 10 more lock-related test failures.
1381
        # Cleanup
1382
        repo.lock_write(repo_token)
1383
        repo.dont_leave_lock_in_place()
1384
        repo.unlock()
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
1385
2018.5.95 by Andrew Bennetts
Add a Transport.is_readonly remote call, let {Branch,Repository}.lock_write remote call return UnlockableTransport, and miscellaneous test fixes.
1386
    def test_lock_write_on_readonly_transport(self):
1387
        backing = self.get_readonly_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1388
        request = smart_branch.SmartServerBranchRequestLockWrite(backing)
2018.5.95 by Andrew Bennetts
Add a Transport.is_readonly remote call, let {Branch,Repository}.lock_write remote call return UnlockableTransport, and miscellaneous test fixes.
1389
        branch = self.make_branch('.')
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
1390
        root = self.get_transport().clone('/')
1391
        path = urlutils.relative_url(root.base, self.get_transport().base)
1392
        response = request.execute(path)
2872.5.3 by Martin Pool
Pass back LockFailed from smart server lock methods
1393
        error_name, lock_str, why_str = response.args
1394
        self.assertFalse(response.is_successful())
1395
        self.assertEqual('LockFailed', error_name)
2018.5.95 by Andrew Bennetts
Add a Transport.is_readonly remote call, let {Branch,Repository}.lock_write remote call return UnlockableTransport, and miscellaneous test fixes.
1396
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
1397
5200.3.3 by Robert Collins
Lock methods on ``Tree``, ``Branch`` and ``Repository`` are now
1398
class TestSmartServerBranchRequestUnlock(TestLockedBranch):
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
1399
1400
    def setUp(self):
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
1401
        tests.TestCaseWithMemoryTransport.setUp(self)
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
1402
1403
    def test_unlock_on_locked_branch_and_repo(self):
1404
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1405
        request = smart_branch.SmartServerBranchRequestUnlock(backing)
3015.2.12 by Robert Collins
Make test_smart use specific formats as needed to exercise locked and unlocked repositories.
1406
        branch = self.make_branch('.', format='knit')
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
1407
        # Lock the branch
5200.3.3 by Robert Collins
Lock methods on ``Tree``, ``Branch`` and ``Repository`` are now
1408
        branch_token, repo_token = self.get_lock_tokens(branch)
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
1409
        # Unlock the branch (and repo) object, leaving the physical locks
1410
        # in place.
1411
        branch.leave_lock_in_place()
1412
        branch.repository.leave_lock_in_place()
1413
        branch.unlock()
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
1414
        response = request.execute('',
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
1415
                                   branch_token, repo_token)
1416
        self.assertEqual(
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1417
            smart_req.SmartServerResponse(('ok',)), response)
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
1418
        # The branch is now unlocked.  Verify that with a new branch
1419
        # object.
1420
        new_branch = branch.bzrdir.open_branch()
1421
        new_branch.lock_write()
1422
        new_branch.unlock()
1423
1424
    def test_unlock_on_unlocked_branch_unlocked_repo(self):
1425
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1426
        request = smart_branch.SmartServerBranchRequestUnlock(backing)
3015.2.12 by Robert Collins
Make test_smart use specific formats as needed to exercise locked and unlocked repositories.
1427
        branch = self.make_branch('.', format='knit')
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
1428
        response = request.execute(
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
1429
            '', 'branch token', 'repo token')
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
1430
        self.assertEqual(
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1431
            smart_req.SmartServerResponse(('TokenMismatch',)), response)
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
1432
1433
    def test_unlock_on_unlocked_branch_locked_repo(self):
1434
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1435
        request = smart_branch.SmartServerBranchRequestUnlock(backing)
3015.2.12 by Robert Collins
Make test_smart use specific formats as needed to exercise locked and unlocked repositories.
1436
        branch = self.make_branch('.', format='knit')
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
1437
        # Lock the repository.
5200.3.3 by Robert Collins
Lock methods on ``Tree``, ``Branch`` and ``Repository`` are now
1438
        repo_token = branch.repository.lock_write().repository_token
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
1439
        branch.repository.leave_lock_in_place()
1440
        branch.repository.unlock()
1441
        # Issue branch lock_write request on the unlocked branch (with locked
1442
        # repo).
5200.3.3 by Robert Collins
Lock methods on ``Tree``, ``Branch`` and ``Repository`` are now
1443
        response = request.execute('', 'branch token', repo_token)
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
1444
        self.assertEqual(
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1445
            smart_req.SmartServerResponse(('TokenMismatch',)), response)
4327.1.10 by Vincent Ladeuil
Fix 10 more lock-related test failures.
1446
        # Cleanup
1447
        branch.repository.lock_write(repo_token)
1448
        branch.repository.dont_leave_lock_in_place()
1449
        branch.repository.unlock()
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
1450
1451
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
1452
class TestSmartServerRepositoryRequest(tests.TestCaseWithMemoryTransport):
2018.5.56 by Robert Collins
Factor out code we expect to be common in SmartServerRequestHasRevision to SmartServerRepositoryRequest (Robert Collins, Vincent Ladeuil).
1453
1454
    def test_no_repository(self):
1455
        """Raise NoRepositoryPresent when there is a bzrdir and no repo."""
1456
        # we test this using a shared repository above the named path,
1457
        # thus checking the right search logic is used - that is, that
1458
        # its the exact path being looked at and the server is not
1459
        # searching.
1460
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1461
        request = smart_repo.SmartServerRepositoryRequest(backing)
2018.5.56 by Robert Collins
Factor out code we expect to be common in SmartServerRequestHasRevision to SmartServerRepositoryRequest (Robert Collins, Vincent Ladeuil).
1462
        self.make_repository('.', shared=True)
1463
        self.make_bzrdir('subdir')
1464
        self.assertRaises(errors.NoRepositoryPresent,
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
1465
            request.execute, 'subdir')
1466
1467
6280.3.2 by Jelmer Vernooij
Add smart side of RemoteRepository.all_revision_ids().
1468
class TestSmartServerRepositoryAllRevisionIds(
1469
    tests.TestCaseWithMemoryTransport):
1470
1471
    def test_empty(self):
1472
        """An empty body should be returned for an empty repository."""
1473
        backing = self.get_transport()
1474
        request = smart_repo.SmartServerRepositoryAllRevisionIds(backing)
1475
        self.make_repository('.')
1476
        self.assertEquals(
1477
            smart_req.SuccessfulSmartServerResponse(("ok", ), ""),
1478
            request.execute(''))
1479
1480
    def test_some_revisions(self):
1481
        """An empty body should be returned for an empty repository."""
1482
        backing = self.get_transport()
1483
        request = smart_repo.SmartServerRepositoryAllRevisionIds(backing)
1484
        tree = self.make_branch_and_memory_tree('.')
1485
        tree.lock_write()
1486
        tree.add('')
1487
        tree.commit(rev_id='origineel', message="message")
1488
        tree.commit(rev_id='nog-een-revisie', message="message")
1489
        tree.unlock()
1490
        self.assertEquals(
1491
            smart_req.SuccessfulSmartServerResponse(("ok", ),
1492
                "origineel\nnog-een-revisie"),
1493
            request.execute(''))
1494
1495
6280.4.2 by Jelmer Vernooij
Provide server side of Repository.break_lock HPSS call.
1496
class TestSmartServerRepositoryBreakLock(tests.TestCaseWithMemoryTransport):
1497
1498
    def test_lock_to_break(self):
1499
        backing = self.get_transport()
1500
        request = smart_repo.SmartServerRepositoryBreakLock(backing)
1501
        tree = self.make_branch_and_memory_tree('.')
1502
        tree.branch.repository.lock_write()
1503
        self.assertEqual(
1504
            smart_req.SuccessfulSmartServerResponse(('ok', ), None),
1505
            request.execute(''))
1506
1507
    def test_nothing_to_break(self):
1508
        backing = self.get_transport()
1509
        request = smart_repo.SmartServerRepositoryBreakLock(backing)
1510
        tree = self.make_branch_and_memory_tree('.')
1511
        self.assertEqual(
1512
            smart_req.SuccessfulSmartServerResponse(('ok', ), None),
1513
            request.execute(''))
1514
1515
3441.5.4 by Andrew Bennetts
Fix test failures, and add some tests for the remote graph heads RPC.
1516
class TestSmartServerRepositoryGetParentMap(tests.TestCaseWithMemoryTransport):
3211.5.1 by Robert Collins
Change the smart server get_parents method to take a graph search to exclude already recieved parents from. This prevents history shortcuts causing huge numbers of duplicates.
1517
3211.5.3 by Robert Collins
Adjust size of batch and change gzip comments to bzip2.
1518
    def test_trivial_bzipped(self):
1519
        # This tests that the wire encoding is actually bzipped
3211.5.1 by Robert Collins
Change the smart server get_parents method to take a graph search to exclude already recieved parents from. This prevents history shortcuts causing huge numbers of duplicates.
1520
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1521
        request = smart_repo.SmartServerRepositoryGetParentMap(backing)
3211.5.1 by Robert Collins
Change the smart server get_parents method to take a graph search to exclude already recieved parents from. This prevents history shortcuts causing huge numbers of duplicates.
1522
        tree = self.make_branch_and_memory_tree('.')
1523
1524
        self.assertEqual(None,
2692.1.24 by Andrew Bennetts
Merge from bzr.dev.
1525
            request.execute('', 'missing-id'))
4190.1.3 by Robert Collins
Allow optional inclusion of ghost data in server get_parent_map calls.
1526
        # Note that it returns a body that is bzipped.
3211.5.1 by Robert Collins
Change the smart server get_parents method to take a graph search to exclude already recieved parents from. This prevents history shortcuts causing huge numbers of duplicates.
1527
        self.assertEqual(
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1528
            smart_req.SuccessfulSmartServerResponse(('ok', ), bz2.compress('')),
3211.5.1 by Robert Collins
Change the smart server get_parents method to take a graph search to exclude already recieved parents from. This prevents history shortcuts causing huge numbers of duplicates.
1529
            request.do_body('\n\n0\n'))
1530
4190.1.3 by Robert Collins
Allow optional inclusion of ghost data in server get_parent_map calls.
1531
    def test_trivial_include_missing(self):
1532
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1533
        request = smart_repo.SmartServerRepositoryGetParentMap(backing)
4190.1.3 by Robert Collins
Allow optional inclusion of ghost data in server get_parent_map calls.
1534
        tree = self.make_branch_and_memory_tree('.')
1535
1536
        self.assertEqual(None,
1537
            request.execute('', 'missing-id', 'include-missing:'))
1538
        self.assertEqual(
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1539
            smart_req.SuccessfulSmartServerResponse(('ok', ),
4190.1.3 by Robert Collins
Allow optional inclusion of ghost data in server get_parent_map calls.
1540
                bz2.compress('missing:missing-id')),
1541
            request.do_body('\n\n0\n'))
1542
3211.5.1 by Robert Collins
Change the smart server get_parents method to take a graph search to exclude already recieved parents from. This prevents history shortcuts causing huge numbers of duplicates.
1543
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1544
class TestSmartServerRepositoryGetRevisionGraph(
1545
    tests.TestCaseWithMemoryTransport):
2018.5.67 by Wouter van Heyst
Implement RemoteRepository.get_revision_graph (Wouter van Heyst, Robert Collins)
1546
1547
    def test_none_argument(self):
1548
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1549
        request = smart_repo.SmartServerRepositoryGetRevisionGraph(backing)
2018.5.67 by Wouter van Heyst
Implement RemoteRepository.get_revision_graph (Wouter van Heyst, Robert Collins)
1550
        tree = self.make_branch_and_memory_tree('.')
1551
        tree.lock_write()
1552
        tree.add('')
1553
        r1 = tree.commit('1st commit')
2018.5.148 by Andrew Bennetts
Fix all the DeprecationWarnings in test_smart caused by unicode revision IDs.
1554
        r2 = tree.commit('2nd commit', rev_id=u'\xc8'.encode('utf-8'))
2018.5.67 by Wouter van Heyst
Implement RemoteRepository.get_revision_graph (Wouter van Heyst, Robert Collins)
1555
        tree.unlock()
1556
1557
        # the lines of revision_id->revision_parent_list has no guaranteed
1558
        # order coming out of a dict, so sort both our test and response
1559
        lines = sorted([' '.join([r2, r1]), r1])
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
1560
        response = request.execute('', '')
2018.5.67 by Wouter van Heyst
Implement RemoteRepository.get_revision_graph (Wouter van Heyst, Robert Collins)
1561
        response.body = '\n'.join(sorted(response.body.split('\n')))
1562
2018.5.83 by Andrew Bennetts
Fix some test failures caused by the switch from unicode to UTF-8-encoded strs for revision IDs.
1563
        self.assertEqual(
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1564
            smart_req.SmartServerResponse(('ok', ), '\n'.join(lines)), response)
2018.5.67 by Wouter van Heyst
Implement RemoteRepository.get_revision_graph (Wouter van Heyst, Robert Collins)
1565
1566
    def test_specific_revision_argument(self):
1567
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1568
        request = smart_repo.SmartServerRepositoryGetRevisionGraph(backing)
2018.5.67 by Wouter van Heyst
Implement RemoteRepository.get_revision_graph (Wouter van Heyst, Robert Collins)
1569
        tree = self.make_branch_and_memory_tree('.')
1570
        tree.lock_write()
1571
        tree.add('')
2018.5.148 by Andrew Bennetts
Fix all the DeprecationWarnings in test_smart caused by unicode revision IDs.
1572
        rev_id_utf8 = u'\xc9'.encode('utf-8')
1573
        r1 = tree.commit('1st commit', rev_id=rev_id_utf8)
1574
        r2 = tree.commit('2nd commit', rev_id=u'\xc8'.encode('utf-8'))
2018.5.67 by Wouter van Heyst
Implement RemoteRepository.get_revision_graph (Wouter van Heyst, Robert Collins)
1575
        tree.unlock()
1576
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1577
        self.assertEqual(smart_req.SmartServerResponse(('ok', ), rev_id_utf8),
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
1578
            request.execute('', rev_id_utf8))
3943.8.1 by Marius Kruger
remove all trailing whitespace from bzr source
1579
2018.5.67 by Wouter van Heyst
Implement RemoteRepository.get_revision_graph (Wouter van Heyst, Robert Collins)
1580
    def test_no_such_revision(self):
1581
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1582
        request = smart_repo.SmartServerRepositoryGetRevisionGraph(backing)
2018.5.67 by Wouter van Heyst
Implement RemoteRepository.get_revision_graph (Wouter van Heyst, Robert Collins)
1583
        tree = self.make_branch_and_memory_tree('.')
1584
        tree.lock_write()
1585
        tree.add('')
1586
        r1 = tree.commit('1st commit')
1587
        tree.unlock()
1588
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
1589
        # Note that it still returns body (of zero bytes).
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1590
        self.assertEqual(smart_req.SmartServerResponse(
1591
                ('nosuchrevision', 'missingrevision', ), ''),
1592
                         request.execute('', 'missingrevision'))
1593
1594
1595
class TestSmartServerRepositoryGetRevIdForRevno(
1596
    tests.TestCaseWithMemoryTransport):
4419.2.6 by Andrew Bennetts
Add tests for server-side logic, and fix the bugs exposed by those tests.
1597
1598
    def test_revno_found(self):
1599
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1600
        request = smart_repo.SmartServerRepositoryGetRevIdForRevno(backing)
4419.2.6 by Andrew Bennetts
Add tests for server-side logic, and fix the bugs exposed by those tests.
1601
        tree = self.make_branch_and_memory_tree('.')
1602
        tree.lock_write()
1603
        tree.add('')
1604
        rev1_id_utf8 = u'\xc8'.encode('utf-8')
1605
        rev2_id_utf8 = u'\xc9'.encode('utf-8')
1606
        tree.commit('1st commit', rev_id=rev1_id_utf8)
1607
        tree.commit('2nd commit', rev_id=rev2_id_utf8)
1608
        tree.unlock()
1609
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1610
        self.assertEqual(smart_req.SmartServerResponse(('ok', rev1_id_utf8)),
4419.2.6 by Andrew Bennetts
Add tests for server-side logic, and fix the bugs exposed by those tests.
1611
            request.execute('', 1, (2, rev2_id_utf8)))
1612
1613
    def test_known_revid_missing(self):
1614
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1615
        request = smart_repo.SmartServerRepositoryGetRevIdForRevno(backing)
4419.2.6 by Andrew Bennetts
Add tests for server-side logic, and fix the bugs exposed by those tests.
1616
        repo = self.make_repository('.')
1617
        self.assertEqual(
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1618
            smart_req.FailedSmartServerResponse(('nosuchrevision', 'ghost')),
4419.2.6 by Andrew Bennetts
Add tests for server-side logic, and fix the bugs exposed by those tests.
1619
            request.execute('', 1, (2, 'ghost')))
1620
1621
    def test_history_incomplete(self):
1622
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1623
        request = smart_repo.SmartServerRepositoryGetRevIdForRevno(backing)
4419.2.6 by Andrew Bennetts
Add tests for server-side logic, and fix the bugs exposed by those tests.
1624
        parent = self.make_branch_and_memory_tree('parent', format='1.9')
4526.9.21 by Robert Collins
Fix test_smart's test_history_incomplete to generate a good tree before committing.
1625
        parent.lock_write()
1626
        parent.add([''], ['TREE_ROOT'])
4419.2.6 by Andrew Bennetts
Add tests for server-side logic, and fix the bugs exposed by those tests.
1627
        r1 = parent.commit(message='first commit')
1628
        r2 = parent.commit(message='second commit')
4526.9.21 by Robert Collins
Fix test_smart's test_history_incomplete to generate a good tree before committing.
1629
        parent.unlock()
4419.2.6 by Andrew Bennetts
Add tests for server-side logic, and fix the bugs exposed by those tests.
1630
        local = self.make_branch_and_memory_tree('local', format='1.9')
1631
        local.branch.pull(parent.branch)
1632
        local.set_parent_ids([r2])
1633
        r3 = local.commit(message='local commit')
1634
        local.branch.create_clone_on_transport(
1635
            self.get_transport('stacked'), stacked_on=self.get_url('parent'))
1636
        self.assertEqual(
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1637
            smart_req.SmartServerResponse(('history-incomplete', 2, r2)),
4419.2.6 by Andrew Bennetts
Add tests for server-side logic, and fix the bugs exposed by those tests.
1638
            request.execute('stacked', 1, (3, r3)))
1639
4476.3.68 by Andrew Bennetts
Review comments from John.
1640
5539.2.4 by Andrew Bennetts
Add some basic tests for the new verb, fix some shallow bugs.
1641
class GetStreamTestBase(tests.TestCaseWithMemoryTransport):
4070.9.14 by Andrew Bennetts
Tweaks requested by Robert's review.
1642
1643
    def make_two_commit_repo(self):
1644
        tree = self.make_branch_and_memory_tree('.')
1645
        tree.lock_write()
1646
        tree.add('')
1647
        r1 = tree.commit('1st commit')
1648
        r2 = tree.commit('2nd commit', rev_id=u'\xc8'.encode('utf-8'))
1649
        tree.unlock()
1650
        repo = tree.branch.repository
1651
        return repo, r1, r2
1652
5539.2.4 by Andrew Bennetts
Add some basic tests for the new verb, fix some shallow bugs.
1653
1654
class TestSmartServerRepositoryGetStream(GetStreamTestBase):
1655
4070.9.14 by Andrew Bennetts
Tweaks requested by Robert's review.
1656
    def test_ancestry_of(self):
1657
        """The search argument may be a 'ancestry-of' some heads'."""
1658
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1659
        request = smart_repo.SmartServerRepositoryGetStream(backing)
4070.9.14 by Andrew Bennetts
Tweaks requested by Robert's review.
1660
        repo, r1, r2 = self.make_two_commit_repo()
1661
        fetch_spec = ['ancestry-of', r2]
1662
        lines = '\n'.join(fetch_spec)
1663
        request.execute('', repo._format.network_name())
1664
        response = request.do_body(lines)
1665
        self.assertEqual(('ok',), response.args)
1666
        stream_bytes = ''.join(response.body_stream)
1667
        self.assertStartsWith(stream_bytes, 'Bazaar pack format 1')
1668
1669
    def test_search(self):
1670
        """The search argument may be a 'search' of some explicit keys."""
1671
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1672
        request = smart_repo.SmartServerRepositoryGetStream(backing)
4070.9.14 by Andrew Bennetts
Tweaks requested by Robert's review.
1673
        repo, r1, r2 = self.make_two_commit_repo()
1674
        fetch_spec = ['search', '%s %s' % (r1, r2), 'null:', '2']
1675
        lines = '\n'.join(fetch_spec)
1676
        request.execute('', repo._format.network_name())
1677
        response = request.do_body(lines)
1678
        self.assertEqual(('ok',), response.args)
1679
        stream_bytes = ''.join(response.body_stream)
1680
        self.assertStartsWith(stream_bytes, 'Bazaar pack format 1')
1681
5539.2.4 by Andrew Bennetts
Add some basic tests for the new verb, fix some shallow bugs.
1682
    def test_search_everything(self):
1683
        """A search of 'everything' returns a stream."""
1684
        backing = self.get_transport()
5539.2.14 by Andrew Bennetts
Don't add a new verb; instead just teach the client to fallback if it gets a BadSearch error.
1685
        request = smart_repo.SmartServerRepositoryGetStream_1_19(backing)
5539.2.4 by Andrew Bennetts
Add some basic tests for the new verb, fix some shallow bugs.
1686
        repo, r1, r2 = self.make_two_commit_repo()
1687
        serialised_fetch_spec = 'everything'
1688
        request.execute('', repo._format.network_name())
1689
        response = request.do_body(serialised_fetch_spec)
1690
        self.assertEqual(('ok',), response.args)
1691
        stream_bytes = ''.join(response.body_stream)
1692
        self.assertStartsWith(stream_bytes, 'Bazaar pack format 1')
1693
4070.9.14 by Andrew Bennetts
Tweaks requested by Robert's review.
1694
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
1695
class TestSmartServerRequestHasRevision(tests.TestCaseWithMemoryTransport):
2018.5.56 by Robert Collins
Factor out code we expect to be common in SmartServerRequestHasRevision to SmartServerRepositoryRequest (Robert Collins, Vincent Ladeuil).
1696
1697
    def test_missing_revision(self):
1698
        """For a missing revision, ('no', ) is returned."""
1699
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1700
        request = smart_repo.SmartServerRequestHasRevision(backing)
2018.5.56 by Robert Collins
Factor out code we expect to be common in SmartServerRequestHasRevision to SmartServerRepositoryRequest (Robert Collins, Vincent Ladeuil).
1701
        self.make_repository('.')
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1702
        self.assertEqual(smart_req.SmartServerResponse(('no', )),
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
1703
            request.execute('', 'revid'))
2018.5.56 by Robert Collins
Factor out code we expect to be common in SmartServerRequestHasRevision to SmartServerRepositoryRequest (Robert Collins, Vincent Ladeuil).
1704
1705
    def test_present_revision(self):
2018.5.158 by Andrew Bennetts
Return 'yes'/'no' rather than 'ok'/'no' from the Repository.has_revision smart command.
1706
        """For a present revision, ('yes', ) is returned."""
2018.5.56 by Robert Collins
Factor out code we expect to be common in SmartServerRequestHasRevision to SmartServerRepositoryRequest (Robert Collins, Vincent Ladeuil).
1707
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1708
        request = smart_repo.SmartServerRequestHasRevision(backing)
2018.5.56 by Robert Collins
Factor out code we expect to be common in SmartServerRequestHasRevision to SmartServerRepositoryRequest (Robert Collins, Vincent Ladeuil).
1709
        tree = self.make_branch_and_memory_tree('.')
1710
        tree.lock_write()
1711
        tree.add('')
2018.5.148 by Andrew Bennetts
Fix all the DeprecationWarnings in test_smart caused by unicode revision IDs.
1712
        rev_id_utf8 = u'\xc8abc'.encode('utf-8')
1713
        r1 = tree.commit('a commit', rev_id=rev_id_utf8)
2018.5.56 by Robert Collins
Factor out code we expect to be common in SmartServerRequestHasRevision to SmartServerRepositoryRequest (Robert Collins, Vincent Ladeuil).
1714
        tree.unlock()
2018.5.148 by Andrew Bennetts
Fix all the DeprecationWarnings in test_smart caused by unicode revision IDs.
1715
        self.assertTrue(tree.branch.repository.has_revision(rev_id_utf8))
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1716
        self.assertEqual(smart_req.SmartServerResponse(('yes', )),
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
1717
            request.execute('', rev_id_utf8))
1718
1719
6265.1.1 by Jelmer Vernooij
Add new HPSS call ``Repository.has_signature_for_revision_id``.
1720
class TestSmartServerRequestHasSignatureForRevisionId(
1721
        tests.TestCaseWithMemoryTransport):
1722
1723
    def test_missing_revision(self):
1724
        """For a missing revision, NoSuchRevision is returned."""
1725
        backing = self.get_transport()
1726
        request = smart_repo.SmartServerRequestHasSignatureForRevisionId(
1727
            backing)
1728
        self.make_repository('.')
1729
        self.assertEqual(
1730
            smart_req.FailedSmartServerResponse(
6265.1.5 by Jelmer Vernooij
Fix capitalization - NoSuchRevision is for branches.
1731
                ('nosuchrevision', 'revid'), None),
6265.1.1 by Jelmer Vernooij
Add new HPSS call ``Repository.has_signature_for_revision_id``.
1732
            request.execute('', 'revid'))
1733
1734
    def test_missing_signature(self):
1735
        """For a missing signature, ('no', ) is returned."""
1736
        backing = self.get_transport()
1737
        request = smart_repo.SmartServerRequestHasSignatureForRevisionId(
1738
            backing)
1739
        tree = self.make_branch_and_memory_tree('.')
1740
        tree.lock_write()
1741
        tree.add('')
1742
        r1 = tree.commit('a commit', rev_id='A')
1743
        tree.unlock()
1744
        self.assertTrue(tree.branch.repository.has_revision('A'))
1745
        self.assertEqual(smart_req.SmartServerResponse(('no', )),
1746
            request.execute('', 'A'))
1747
1748
    def test_present_signature(self):
1749
        """For a present signature, ('yes', ) is returned."""
1750
        backing = self.get_transport()
1751
        request = smart_repo.SmartServerRequestHasSignatureForRevisionId(
1752
            backing)
1753
        strategy = gpg.LoopbackGPGStrategy(None)
1754
        tree = self.make_branch_and_memory_tree('.')
1755
        tree.lock_write()
1756
        tree.add('')
1757
        r1 = tree.commit('a commit', rev_id='A')
1758
        tree.branch.repository.start_write_group()
1759
        tree.branch.repository.sign_revision('A', strategy)
1760
        tree.branch.repository.commit_write_group()
1761
        tree.unlock()
1762
        self.assertTrue(tree.branch.repository.has_revision('A'))
1763
        self.assertEqual(smart_req.SmartServerResponse(('yes', )),
1764
            request.execute('', 'A'))
1765
1766
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
1767
class TestSmartServerRepositoryGatherStats(tests.TestCaseWithMemoryTransport):
2018.10.2 by v.ladeuil+lp at free
gather_stats server side and request registration
1768
1769
    def test_empty_revid(self):
1770
        """With an empty revid, we get only size an number and revisions"""
1771
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1772
        request = smart_repo.SmartServerRepositoryGatherStats(backing)
2018.10.2 by v.ladeuil+lp at free
gather_stats server side and request registration
1773
        repository = self.make_repository('.')
1774
        stats = repository.gather_stats()
3350.6.4 by Robert Collins
First cut at pluralised VersionedFiles. Some rather massive API incompatabilities, primarily because of the difficulty of coherence among competing stores.
1775
        expected_body = 'revisions: 0\n'
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1776
        self.assertEqual(smart_req.SmartServerResponse(('ok', ), expected_body),
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
1777
                         request.execute('', '', 'no'))
2018.10.2 by v.ladeuil+lp at free
gather_stats server side and request registration
1778
1779
    def test_revid_with_committers(self):
1780
        """For a revid we get more infos."""
1781
        backing = self.get_transport()
2018.5.148 by Andrew Bennetts
Fix all the DeprecationWarnings in test_smart caused by unicode revision IDs.
1782
        rev_id_utf8 = u'\xc8abc'.encode('utf-8')
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1783
        request = smart_repo.SmartServerRepositoryGatherStats(backing)
2018.10.2 by v.ladeuil+lp at free
gather_stats server side and request registration
1784
        tree = self.make_branch_and_memory_tree('.')
1785
        tree.lock_write()
1786
        tree.add('')
1787
        # Let's build a predictable result
1788
        tree.commit('a commit', timestamp=123456.2, timezone=3600)
2018.5.148 by Andrew Bennetts
Fix all the DeprecationWarnings in test_smart caused by unicode revision IDs.
1789
        tree.commit('a commit', timestamp=654321.4, timezone=0,
1790
                    rev_id=rev_id_utf8)
2018.10.2 by v.ladeuil+lp at free
gather_stats server side and request registration
1791
        tree.unlock()
1792
1793
        stats = tree.branch.repository.gather_stats()
1794
        expected_body = ('firstrev: 123456.200 3600\n'
1795
                         'latestrev: 654321.400 0\n'
3350.6.4 by Robert Collins
First cut at pluralised VersionedFiles. Some rather massive API incompatabilities, primarily because of the difficulty of coherence among competing stores.
1796
                         'revisions: 2\n')
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1797
        self.assertEqual(smart_req.SmartServerResponse(('ok', ), expected_body),
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
1798
                         request.execute('',
2018.5.148 by Andrew Bennetts
Fix all the DeprecationWarnings in test_smart caused by unicode revision IDs.
1799
                                         rev_id_utf8, 'no'))
2018.10.2 by v.ladeuil+lp at free
gather_stats server side and request registration
1800
1801
    def test_not_empty_repository_with_committers(self):
1802
        """For a revid and requesting committers we get the whole thing."""
1803
        backing = self.get_transport()
2018.5.148 by Andrew Bennetts
Fix all the DeprecationWarnings in test_smart caused by unicode revision IDs.
1804
        rev_id_utf8 = u'\xc8abc'.encode('utf-8')
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1805
        request = smart_repo.SmartServerRepositoryGatherStats(backing)
2018.10.2 by v.ladeuil+lp at free
gather_stats server side and request registration
1806
        tree = self.make_branch_and_memory_tree('.')
1807
        tree.lock_write()
1808
        tree.add('')
1809
        # Let's build a predictable result
1810
        tree.commit('a commit', timestamp=123456.2, timezone=3600,
1811
                    committer='foo')
1812
        tree.commit('a commit', timestamp=654321.4, timezone=0,
2018.5.148 by Andrew Bennetts
Fix all the DeprecationWarnings in test_smart caused by unicode revision IDs.
1813
                    committer='bar', rev_id=rev_id_utf8)
2018.10.2 by v.ladeuil+lp at free
gather_stats server side and request registration
1814
        tree.unlock()
1815
        stats = tree.branch.repository.gather_stats()
1816
1817
        expected_body = ('committers: 2\n'
1818
                         'firstrev: 123456.200 3600\n'
1819
                         'latestrev: 654321.400 0\n'
3350.6.4 by Robert Collins
First cut at pluralised VersionedFiles. Some rather massive API incompatabilities, primarily because of the difficulty of coherence among competing stores.
1820
                         'revisions: 2\n')
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1821
        self.assertEqual(smart_req.SmartServerResponse(('ok', ), expected_body),
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
1822
                         request.execute('',
2018.5.148 by Andrew Bennetts
Fix all the DeprecationWarnings in test_smart caused by unicode revision IDs.
1823
                                         rev_id_utf8, 'yes'))
2018.10.2 by v.ladeuil+lp at free
gather_stats server side and request registration
1824
6291.1.1 by Jelmer Vernooij
Cope with missing revision ids being specified to
1825
    def test_unknown_revid(self):
1826
        """An unknown revision id causes a 'nosuchrevision' error."""
1827
        backing = self.get_transport()
1828
        request = smart_repo.SmartServerRepositoryGatherStats(backing)
1829
        repository = self.make_repository('.')
1830
        expected_body = 'revisions: 0\n'
1831
        self.assertEqual(
1832
            smart_req.FailedSmartServerResponse(
1833
                ('nosuchrevision', 'mia'), None),
1834
            request.execute('', 'mia', 'yes'))
1835
2018.10.2 by v.ladeuil+lp at free
gather_stats server side and request registration
1836
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
1837
class TestSmartServerRepositoryIsShared(tests.TestCaseWithMemoryTransport):
2018.5.57 by Robert Collins
Implement RemoteRepository.is_shared (Robert Collins, Vincent Ladeuil).
1838
1839
    def test_is_shared(self):
1840
        """For a shared repository, ('yes', ) is returned."""
1841
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1842
        request = smart_repo.SmartServerRepositoryIsShared(backing)
2018.5.57 by Robert Collins
Implement RemoteRepository.is_shared (Robert Collins, Vincent Ladeuil).
1843
        self.make_repository('.', shared=True)
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1844
        self.assertEqual(smart_req.SmartServerResponse(('yes', )),
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
1845
            request.execute('', ))
2018.5.57 by Robert Collins
Implement RemoteRepository.is_shared (Robert Collins, Vincent Ladeuil).
1846
1847
    def test_is_not_shared(self):
2018.5.58 by Wouter van Heyst
Small test fixes to reflect naming and documentation
1848
        """For a shared repository, ('no', ) is returned."""
2018.5.57 by Robert Collins
Implement RemoteRepository.is_shared (Robert Collins, Vincent Ladeuil).
1849
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1850
        request = smart_repo.SmartServerRepositoryIsShared(backing)
2018.5.57 by Robert Collins
Implement RemoteRepository.is_shared (Robert Collins, Vincent Ladeuil).
1851
        self.make_repository('.', shared=False)
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1852
        self.assertEqual(smart_req.SmartServerResponse(('no', )),
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
1853
            request.execute('', ))
1854
1855
6263.2.1 by Jelmer Vernooij
Add hpss call ``Repository.make_working_trees``
1856
class TestSmartServerRepositoryMakeWorkingTrees(
1857
        tests.TestCaseWithMemoryTransport):
1858
1859
    def test_make_working_trees(self):
1860
        """For a repository with working trees, ('yes', ) is returned."""
1861
        backing = self.get_transport()
1862
        request = smart_repo.SmartServerRepositoryMakeWorkingTrees(backing)
1863
        r = self.make_repository('.')
1864
        r.set_make_working_trees(True)
1865
        self.assertEqual(smart_req.SmartServerResponse(('yes', )),
1866
            request.execute('', ))
1867
1868
    def test_is_not_shared(self):
1869
        """For a repository with working trees, ('no', ) is returned."""
1870
        backing = self.get_transport()
1871
        request = smart_repo.SmartServerRepositoryMakeWorkingTrees(backing)
1872
        r = self.make_repository('.')
1873
        r.set_make_working_trees(False)
1874
        self.assertEqual(smart_req.SmartServerResponse(('no', )),
1875
            request.execute('', ))
1876
1877
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
1878
class TestSmartServerRepositoryLockWrite(tests.TestCaseWithMemoryTransport):
2018.5.78 by Andrew Bennetts
Implement RemoteRepository.lock_write/unlock to expect and send tokens over the
1879
1880
    def test_lock_write_on_unlocked_repo(self):
1881
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1882
        request = smart_repo.SmartServerRepositoryLockWrite(backing)
3015.2.12 by Robert Collins
Make test_smart use specific formats as needed to exercise locked and unlocked repositories.
1883
        repository = self.make_repository('.', format='knit')
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
1884
        response = request.execute('')
2018.5.78 by Andrew Bennetts
Implement RemoteRepository.lock_write/unlock to expect and send tokens over the
1885
        nonce = repository.control_files._lock.peek().get('nonce')
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1886
        self.assertEqual(smart_req.SmartServerResponse(('ok', nonce)), response)
2018.5.78 by Andrew Bennetts
Implement RemoteRepository.lock_write/unlock to expect and send tokens over the
1887
        # The repository is now locked.  Verify that with a new repository
1888
        # object.
1889
        new_repo = repository.bzrdir.open_repository()
1890
        self.assertRaises(errors.LockContention, new_repo.lock_write)
4327.1.10 by Vincent Ladeuil
Fix 10 more lock-related test failures.
1891
        # Cleanup
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1892
        request = smart_repo.SmartServerRepositoryUnlock(backing)
4327.1.10 by Vincent Ladeuil
Fix 10 more lock-related test failures.
1893
        response = request.execute('', nonce)
2018.5.78 by Andrew Bennetts
Implement RemoteRepository.lock_write/unlock to expect and send tokens over the
1894
1895
    def test_lock_write_on_locked_repo(self):
1896
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1897
        request = smart_repo.SmartServerRepositoryLockWrite(backing)
3015.2.12 by Robert Collins
Make test_smart use specific formats as needed to exercise locked and unlocked repositories.
1898
        repository = self.make_repository('.', format='knit')
5200.3.3 by Robert Collins
Lock methods on ``Tree``, ``Branch`` and ``Repository`` are now
1899
        repo_token = repository.lock_write().repository_token
2018.5.78 by Andrew Bennetts
Implement RemoteRepository.lock_write/unlock to expect and send tokens over the
1900
        repository.leave_lock_in_place()
1901
        repository.unlock()
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
1902
        response = request.execute('')
2018.5.78 by Andrew Bennetts
Implement RemoteRepository.lock_write/unlock to expect and send tokens over the
1903
        self.assertEqual(
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1904
            smart_req.SmartServerResponse(('LockContention',)), response)
4327.1.10 by Vincent Ladeuil
Fix 10 more lock-related test failures.
1905
        # Cleanup
1906
        repository.lock_write(repo_token)
1907
        repository.dont_leave_lock_in_place()
1908
        repository.unlock()
2018.5.78 by Andrew Bennetts
Implement RemoteRepository.lock_write/unlock to expect and send tokens over the
1909
2018.5.95 by Andrew Bennetts
Add a Transport.is_readonly remote call, let {Branch,Repository}.lock_write remote call return UnlockableTransport, and miscellaneous test fixes.
1910
    def test_lock_write_on_readonly_transport(self):
1911
        backing = self.get_readonly_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1912
        request = smart_repo.SmartServerRepositoryLockWrite(backing)
3015.2.12 by Robert Collins
Make test_smart use specific formats as needed to exercise locked and unlocked repositories.
1913
        repository = self.make_repository('.', format='knit')
2018.5.95 by Andrew Bennetts
Add a Transport.is_readonly remote call, let {Branch,Repository}.lock_write remote call return UnlockableTransport, and miscellaneous test fixes.
1914
        response = request.execute('')
2872.5.3 by Martin Pool
Pass back LockFailed from smart server lock methods
1915
        self.assertFalse(response.is_successful())
1916
        self.assertEqual('LockFailed', response.args[0])
2018.5.95 by Andrew Bennetts
Add a Transport.is_readonly remote call, let {Branch,Repository}.lock_write remote call return UnlockableTransport, and miscellaneous test fixes.
1917
2018.5.78 by Andrew Bennetts
Implement RemoteRepository.lock_write/unlock to expect and send tokens over the
1918
4144.3.1 by Andrew Bennetts
Add Repository.insert_stream_locked server-side implementation, plus tests for server-side _translate_error.
1919
class TestInsertStreamBase(tests.TestCaseWithMemoryTransport):
1920
1921
    def make_empty_byte_stream(self, repo):
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1922
        byte_stream = smart_repo._stream_to_byte_stream([], repo._format)
4144.3.1 by Andrew Bennetts
Add Repository.insert_stream_locked server-side implementation, plus tests for server-side _translate_error.
1923
        return ''.join(byte_stream)
1924
1925
1926
class TestSmartServerRepositoryInsertStream(TestInsertStreamBase):
1927
1928
    def test_insert_stream_empty(self):
1929
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1930
        request = smart_repo.SmartServerRepositoryInsertStream(backing)
4144.3.1 by Andrew Bennetts
Add Repository.insert_stream_locked server-side implementation, plus tests for server-side _translate_error.
1931
        repository = self.make_repository('.')
1932
        response = request.execute('', '')
1933
        self.assertEqual(None, response)
1934
        response = request.do_chunk(self.make_empty_byte_stream(repository))
1935
        self.assertEqual(None, response)
1936
        response = request.do_end()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1937
        self.assertEqual(smart_req.SmartServerResponse(('ok', )), response)
1938
4144.3.1 by Andrew Bennetts
Add Repository.insert_stream_locked server-side implementation, plus tests for server-side _translate_error.
1939
1940
class TestSmartServerRepositoryInsertStreamLocked(TestInsertStreamBase):
1941
1942
    def test_insert_stream_empty(self):
1943
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1944
        request = smart_repo.SmartServerRepositoryInsertStreamLocked(
4144.3.1 by Andrew Bennetts
Add Repository.insert_stream_locked server-side implementation, plus tests for server-side _translate_error.
1945
            backing)
1946
        repository = self.make_repository('.', format='knit')
5200.3.3 by Robert Collins
Lock methods on ``Tree``, ``Branch`` and ``Repository`` are now
1947
        lock_token = repository.lock_write().repository_token
4144.3.1 by Andrew Bennetts
Add Repository.insert_stream_locked server-side implementation, plus tests for server-side _translate_error.
1948
        response = request.execute('', '', lock_token)
1949
        self.assertEqual(None, response)
1950
        response = request.do_chunk(self.make_empty_byte_stream(repository))
1951
        self.assertEqual(None, response)
1952
        response = request.do_end()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1953
        self.assertEqual(smart_req.SmartServerResponse(('ok', )), response)
4144.3.1 by Andrew Bennetts
Add Repository.insert_stream_locked server-side implementation, plus tests for server-side _translate_error.
1954
        repository.unlock()
1955
1956
    def test_insert_stream_with_wrong_lock_token(self):
1957
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1958
        request = smart_repo.SmartServerRepositoryInsertStreamLocked(
4144.3.1 by Andrew Bennetts
Add Repository.insert_stream_locked server-side implementation, plus tests for server-side _translate_error.
1959
            backing)
1960
        repository = self.make_repository('.', format='knit')
5200.3.3 by Robert Collins
Lock methods on ``Tree``, ``Branch`` and ``Repository`` are now
1961
        lock_token = repository.lock_write().repository_token
4144.3.1 by Andrew Bennetts
Add Repository.insert_stream_locked server-side implementation, plus tests for server-side _translate_error.
1962
        self.assertRaises(
1963
            errors.TokenMismatch, request.execute, '', '', 'wrong-token')
1964
        repository.unlock()
1965
1966
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
1967
class TestSmartServerRepositoryUnlock(tests.TestCaseWithMemoryTransport):
2018.5.78 by Andrew Bennetts
Implement RemoteRepository.lock_write/unlock to expect and send tokens over the
1968
1969
    def setUp(self):
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
1970
        tests.TestCaseWithMemoryTransport.setUp(self)
2018.5.78 by Andrew Bennetts
Implement RemoteRepository.lock_write/unlock to expect and send tokens over the
1971
1972
    def test_unlock_on_locked_repo(self):
1973
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1974
        request = smart_repo.SmartServerRepositoryUnlock(backing)
3015.2.12 by Robert Collins
Make test_smart use specific formats as needed to exercise locked and unlocked repositories.
1975
        repository = self.make_repository('.', format='knit')
5200.3.3 by Robert Collins
Lock methods on ``Tree``, ``Branch`` and ``Repository`` are now
1976
        token = repository.lock_write().repository_token
2018.5.78 by Andrew Bennetts
Implement RemoteRepository.lock_write/unlock to expect and send tokens over the
1977
        repository.leave_lock_in_place()
1978
        repository.unlock()
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
1979
        response = request.execute('', token)
2018.5.78 by Andrew Bennetts
Implement RemoteRepository.lock_write/unlock to expect and send tokens over the
1980
        self.assertEqual(
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1981
            smart_req.SmartServerResponse(('ok',)), response)
2018.5.78 by Andrew Bennetts
Implement RemoteRepository.lock_write/unlock to expect and send tokens over the
1982
        # The repository is now unlocked.  Verify that with a new repository
1983
        # object.
1984
        new_repo = repository.bzrdir.open_repository()
1985
        new_repo.lock_write()
1986
        new_repo.unlock()
1987
1988
    def test_unlock_on_unlocked_repo(self):
1989
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1990
        request = smart_repo.SmartServerRepositoryUnlock(backing)
3015.2.12 by Robert Collins
Make test_smart use specific formats as needed to exercise locked and unlocked repositories.
1991
        repository = self.make_repository('.', format='knit')
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
1992
        response = request.execute('', 'some token')
2018.5.78 by Andrew Bennetts
Implement RemoteRepository.lock_write/unlock to expect and send tokens over the
1993
        self.assertEqual(
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
1994
            smart_req.SmartServerResponse(('TokenMismatch',)), response)
2018.5.78 by Andrew Bennetts
Implement RemoteRepository.lock_write/unlock to expect and send tokens over the
1995
1996
2692.1.1 by Andrew Bennetts
Add translate_client_path method to SmartServerRequest.
1997
class TestSmartServerIsReadonly(tests.TestCaseWithMemoryTransport):
2018.5.95 by Andrew Bennetts
Add a Transport.is_readonly remote call, let {Branch,Repository}.lock_write remote call return UnlockableTransport, and miscellaneous test fixes.
1998
1999
    def test_is_readonly_no(self):
2000
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2001
        request = smart_req.SmartServerIsReadonly(backing)
2018.5.95 by Andrew Bennetts
Add a Transport.is_readonly remote call, let {Branch,Repository}.lock_write remote call return UnlockableTransport, and miscellaneous test fixes.
2002
        response = request.execute()
2003
        self.assertEqual(
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2004
            smart_req.SmartServerResponse(('no',)), response)
2018.5.95 by Andrew Bennetts
Add a Transport.is_readonly remote call, let {Branch,Repository}.lock_write remote call return UnlockableTransport, and miscellaneous test fixes.
2005
2006
    def test_is_readonly_yes(self):
2007
        backing = self.get_readonly_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2008
        request = smart_req.SmartServerIsReadonly(backing)
2018.5.95 by Andrew Bennetts
Add a Transport.is_readonly remote call, let {Branch,Repository}.lock_write remote call return UnlockableTransport, and miscellaneous test fixes.
2009
        response = request.execute()
2010
        self.assertEqual(
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2011
            smart_req.SmartServerResponse(('yes',)), response)
2012
2013
2014
class TestSmartServerRepositorySetMakeWorkingTrees(
2015
    tests.TestCaseWithMemoryTransport):
4017.3.4 by Robert Collins
Create a verb for Repository.set_make_working_trees.
2016
2017
    def test_set_false(self):
2018
        backing = self.get_transport()
2019
        repo = self.make_repository('.', shared=True)
2020
        repo.set_make_working_trees(True)
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2021
        request_class = smart_repo.SmartServerRepositorySetMakeWorkingTrees
4017.3.4 by Robert Collins
Create a verb for Repository.set_make_working_trees.
2022
        request = request_class(backing)
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2023
        self.assertEqual(smart_req.SuccessfulSmartServerResponse(('ok',)),
4017.3.4 by Robert Collins
Create a verb for Repository.set_make_working_trees.
2024
            request.execute('', 'False'))
2025
        repo = repo.bzrdir.open_repository()
2026
        self.assertFalse(repo.make_working_trees())
2027
2028
    def test_set_true(self):
2029
        backing = self.get_transport()
2030
        repo = self.make_repository('.', shared=True)
2031
        repo.set_make_working_trees(False)
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2032
        request_class = smart_repo.SmartServerRepositorySetMakeWorkingTrees
4017.3.4 by Robert Collins
Create a verb for Repository.set_make_working_trees.
2033
        request = request_class(backing)
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2034
        self.assertEqual(smart_req.SuccessfulSmartServerResponse(('ok',)),
4017.3.4 by Robert Collins
Create a verb for Repository.set_make_working_trees.
2035
            request.execute('', 'True'))
2036
        repo = repo.bzrdir.open_repository()
2037
        self.assertTrue(repo.make_working_trees())
2038
2039
6280.5.2 by Jelmer Vernooij
New HPSS call VersionedFileRepository.get_serializer_format.
2040
class TestSmartServerRepositoryGetSerializerFormat(
2041
    tests.TestCaseWithMemoryTransport):
2042
6280.5.4 by Jelmer Vernooij
Fix test name.
2043
    def test_get_serializer_format(self):
6280.5.2 by Jelmer Vernooij
New HPSS call VersionedFileRepository.get_serializer_format.
2044
        backing = self.get_transport()
2045
        repo = self.make_repository('.', format='2a')
2046
        request_class = smart_repo.SmartServerRepositoryGetSerializerFormat
2047
        request = request_class(backing)
2048
        self.assertEqual(
2049
            smart_req.SuccessfulSmartServerResponse(('ok', '10')),
2050
            request.execute(''))
2051
2052
3801.1.4 by Andrew Bennetts
Add tests for autopack RPC.
2053
class TestSmartServerPackRepositoryAutopack(tests.TestCaseWithTransport):
2054
2055
    def make_repo_needing_autopacking(self, path='.'):
2056
        # Make a repo in need of autopacking.
2057
        tree = self.make_branch_and_tree('.', format='pack-0.92')
2058
        repo = tree.branch.repository
2059
        # monkey-patch the pack collection to disable autopacking
2060
        repo._pack_collection._max_pack_count = lambda count: count
2061
        for x in range(10):
2062
            tree.commit('commit %s' % x)
2063
        self.assertEqual(10, len(repo._pack_collection.names()))
2064
        del repo._pack_collection._max_pack_count
2065
        return repo
2066
2067
    def test_autopack_needed(self):
2068
        repo = self.make_repo_needing_autopacking()
4145.1.6 by Robert Collins
More test fallout, but all caught now.
2069
        repo.lock_write()
2070
        self.addCleanup(repo.unlock)
3801.1.4 by Andrew Bennetts
Add tests for autopack RPC.
2071
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2072
        request = smart_packrepo.SmartServerPackRepositoryAutopack(
3801.1.4 by Andrew Bennetts
Add tests for autopack RPC.
2073
            backing)
2074
        response = request.execute('')
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2075
        self.assertEqual(smart_req.SmartServerResponse(('ok',)), response)
3801.1.4 by Andrew Bennetts
Add tests for autopack RPC.
2076
        repo._pack_collection.reload_pack_names()
2077
        self.assertEqual(1, len(repo._pack_collection.names()))
3943.8.1 by Marius Kruger
remove all trailing whitespace from bzr source
2078
3801.1.4 by Andrew Bennetts
Add tests for autopack RPC.
2079
    def test_autopack_not_needed(self):
2080
        tree = self.make_branch_and_tree('.', format='pack-0.92')
2081
        repo = tree.branch.repository
4145.1.6 by Robert Collins
More test fallout, but all caught now.
2082
        repo.lock_write()
2083
        self.addCleanup(repo.unlock)
3801.1.4 by Andrew Bennetts
Add tests for autopack RPC.
2084
        for x in range(9):
2085
            tree.commit('commit %s' % x)
2086
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2087
        request = smart_packrepo.SmartServerPackRepositoryAutopack(
3801.1.4 by Andrew Bennetts
Add tests for autopack RPC.
2088
            backing)
2089
        response = request.execute('')
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2090
        self.assertEqual(smart_req.SmartServerResponse(('ok',)), response)
3801.1.4 by Andrew Bennetts
Add tests for autopack RPC.
2091
        repo._pack_collection.reload_pack_names()
2092
        self.assertEqual(9, len(repo._pack_collection.names()))
3943.8.1 by Marius Kruger
remove all trailing whitespace from bzr source
2093
3801.1.4 by Andrew Bennetts
Add tests for autopack RPC.
2094
    def test_autopack_on_nonpack_format(self):
3801.1.20 by Andrew Bennetts
Return ('ok',) rather than an error the autopack RPC is used on a non-pack repo.
2095
        """A request to autopack a non-pack repo is a no-op."""
3801.1.4 by Andrew Bennetts
Add tests for autopack RPC.
2096
        repo = self.make_repository('.', format='knit')
2097
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2098
        request = smart_packrepo.SmartServerPackRepositoryAutopack(
3801.1.4 by Andrew Bennetts
Add tests for autopack RPC.
2099
            backing)
2100
        response = request.execute('')
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2101
        self.assertEqual(smart_req.SmartServerResponse(('ok',)), response)
3943.8.1 by Marius Kruger
remove all trailing whitespace from bzr source
2102
3801.1.4 by Andrew Bennetts
Add tests for autopack RPC.
2103
4760.2.5 by Andrew Bennetts
Add some more tests.
2104
class TestSmartServerVfsGet(tests.TestCaseWithMemoryTransport):
2105
2106
    def test_unicode_path(self):
2107
        """VFS requests expect unicode paths to be escaped."""
2108
        filename = u'foo\N{INTERROBANG}'
2109
        filename_escaped = urlutils.escape(filename)
2110
        backing = self.get_transport()
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2111
        request = vfs.GetRequest(backing)
4760.2.5 by Andrew Bennetts
Add some more tests.
2112
        backing.put_bytes_non_atomic(filename_escaped, 'contents')
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2113
        self.assertEqual(smart_req.SmartServerResponse(('ok', ), 'contents'),
4760.2.5 by Andrew Bennetts
Add some more tests.
2114
            request.execute(filename_escaped))
2115
2116
2018.6.1 by Robert Collins
Implement a BzrDir.open_branch smart server method for opening a branch without VFS.
2117
class TestHandlers(tests.TestCase):
2118
    """Tests for the request.request_handlers object."""
2119
3526.3.1 by Andrew Bennetts
Remove registrations of defunct HPSS verbs.
2120
    def test_all_registrations_exist(self):
2121
        """All registered request_handlers can be found."""
2122
        # If there's a typo in a register_lazy call, this loop will fail with
2123
        # an AttributeError.
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2124
        for key, item in smart_req.request_handlers.iteritems():
3526.3.1 by Andrew Bennetts
Remove registrations of defunct HPSS verbs.
2125
            pass
2126
4288.1.2 by Robert Collins
Create a server verb for doing BzrDir.get_config()
2127
    def assertHandlerEqual(self, verb, handler):
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2128
        self.assertEqual(smart_req.request_handlers.get(verb), handler)
4288.1.2 by Robert Collins
Create a server verb for doing BzrDir.get_config()
2129
2018.6.1 by Robert Collins
Implement a BzrDir.open_branch smart server method for opening a branch without VFS.
2130
    def test_registered_methods(self):
2131
        """Test that known methods are registered to the correct object."""
6280.4.4 by Jelmer Vernooij
Add Branch.break_lock.
2132
        self.assertHandlerEqual('Branch.break_lock',
2133
            smart_branch.SmartServerBranchBreakLock)
4288.1.2 by Robert Collins
Create a server verb for doing BzrDir.get_config()
2134
        self.assertHandlerEqual('Branch.get_config_file',
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2135
            smart_branch.SmartServerBranchGetConfigFile)
6270.1.17 by Jelmer Vernooij
s/set_config_file/put_config_file.
2136
        self.assertHandlerEqual('Branch.put_config_file',
2137
            smart_branch.SmartServerBranchPutConfigFile)
4288.1.2 by Robert Collins
Create a server verb for doing BzrDir.get_config()
2138
        self.assertHandlerEqual('Branch.get_parent',
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2139
            smart_branch.SmartServerBranchGetParent)
4288.1.2 by Robert Collins
Create a server verb for doing BzrDir.get_config()
2140
        self.assertHandlerEqual('Branch.get_tags_bytes',
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2141
            smart_branch.SmartServerBranchGetTagsBytes)
4288.1.2 by Robert Collins
Create a server verb for doing BzrDir.get_config()
2142
        self.assertHandlerEqual('Branch.lock_write',
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2143
            smart_branch.SmartServerBranchRequestLockWrite)
4288.1.2 by Robert Collins
Create a server verb for doing BzrDir.get_config()
2144
        self.assertHandlerEqual('Branch.last_revision_info',
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2145
            smart_branch.SmartServerBranchRequestLastRevisionInfo)
4288.1.2 by Robert Collins
Create a server verb for doing BzrDir.get_config()
2146
        self.assertHandlerEqual('Branch.revision_history',
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2147
            smart_branch.SmartServerRequestRevisionHistory)
6263.1.5 by Jelmer Vernooij
Test for presence of Branch.revision_id_to_revno verb.
2148
        self.assertHandlerEqual('Branch.revision_id_to_revno',
2149
            smart_branch.SmartServerBranchRequestRevisionIdToRevno)
4288.1.2 by Robert Collins
Create a server verb for doing BzrDir.get_config()
2150
        self.assertHandlerEqual('Branch.set_config_option',
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2151
            smart_branch.SmartServerBranchRequestSetConfigOption)
4288.1.2 by Robert Collins
Create a server verb for doing BzrDir.get_config()
2152
        self.assertHandlerEqual('Branch.set_last_revision',
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2153
            smart_branch.SmartServerBranchRequestSetLastRevision)
4288.1.2 by Robert Collins
Create a server verb for doing BzrDir.get_config()
2154
        self.assertHandlerEqual('Branch.set_last_revision_info',
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2155
            smart_branch.SmartServerBranchRequestSetLastRevisionInfo)
4288.1.7 by Robert Collins
Add new remote server verb Branch.set_parent_location, dropping roundtrips further on push operations.
2156
        self.assertHandlerEqual('Branch.set_last_revision_ex',
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2157
            smart_branch.SmartServerBranchRequestSetLastRevisionEx)
4288.1.7 by Robert Collins
Add new remote server verb Branch.set_parent_location, dropping roundtrips further on push operations.
2158
        self.assertHandlerEqual('Branch.set_parent_location',
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2159
            smart_branch.SmartServerBranchRequestSetParentLocation)
4288.1.2 by Robert Collins
Create a server verb for doing BzrDir.get_config()
2160
        self.assertHandlerEqual('Branch.unlock',
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2161
            smart_branch.SmartServerBranchRequestUnlock)
4288.1.2 by Robert Collins
Create a server verb for doing BzrDir.get_config()
2162
        self.assertHandlerEqual('BzrDir.find_repository',
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2163
            smart_dir.SmartServerRequestFindRepositoryV1)
4288.1.2 by Robert Collins
Create a server verb for doing BzrDir.get_config()
2164
        self.assertHandlerEqual('BzrDir.find_repositoryV2',
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2165
            smart_dir.SmartServerRequestFindRepositoryV2)
4288.1.2 by Robert Collins
Create a server verb for doing BzrDir.get_config()
2166
        self.assertHandlerEqual('BzrDirFormat.initialize',
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2167
            smart_dir.SmartServerRequestInitializeBzrDir)
4436.1.1 by Andrew Bennetts
Rename BzrDirFormat.initialize_ex verb to BzrDirFormat.initialize_ex_1.16.
2168
        self.assertHandlerEqual('BzrDirFormat.initialize_ex_1.16',
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2169
            smart_dir.SmartServerRequestBzrDirInitializeEx)
4288.1.2 by Robert Collins
Create a server verb for doing BzrDir.get_config()
2170
        self.assertHandlerEqual('BzrDir.cloning_metadir',
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2171
            smart_dir.SmartServerBzrDirRequestCloningMetaDir)
4288.1.2 by Robert Collins
Create a server verb for doing BzrDir.get_config()
2172
        self.assertHandlerEqual('BzrDir.get_config_file',
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2173
            smart_dir.SmartServerBzrDirRequestConfigFile)
4288.1.2 by Robert Collins
Create a server verb for doing BzrDir.get_config()
2174
        self.assertHandlerEqual('BzrDir.open_branch',
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2175
            smart_dir.SmartServerRequestOpenBranch)
4288.1.2 by Robert Collins
Create a server verb for doing BzrDir.get_config()
2176
        self.assertHandlerEqual('BzrDir.open_branchV2',
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2177
            smart_dir.SmartServerRequestOpenBranchV2)
4734.4.8 by Andrew Bennetts
Fix HPSS tests; pass 'location is a repository' message via smart server when possible (adds BzrDir.open_branchV3 verb).
2178
        self.assertHandlerEqual('BzrDir.open_branchV3',
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2179
            smart_dir.SmartServerRequestOpenBranchV3)
4288.1.2 by Robert Collins
Create a server verb for doing BzrDir.get_config()
2180
        self.assertHandlerEqual('PackRepository.autopack',
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2181
            smart_packrepo.SmartServerPackRepositoryAutopack)
6280.3.2 by Jelmer Vernooij
Add smart side of RemoteRepository.all_revision_ids().
2182
        self.assertHandlerEqual('Repository.all_revision_ids',
2183
            smart_repo.SmartServerRepositoryAllRevisionIds)
6280.4.2 by Jelmer Vernooij
Provide server side of Repository.break_lock HPSS call.
2184
        self.assertHandlerEqual('Repository.break_lock',
2185
            smart_repo.SmartServerRepositoryBreakLock)
4288.1.2 by Robert Collins
Create a server verb for doing BzrDir.get_config()
2186
        self.assertHandlerEqual('Repository.gather_stats',
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2187
            smart_repo.SmartServerRepositoryGatherStats)
4288.1.2 by Robert Collins
Create a server verb for doing BzrDir.get_config()
2188
        self.assertHandlerEqual('Repository.get_parent_map',
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2189
            smart_repo.SmartServerRepositoryGetParentMap)
4419.2.6 by Andrew Bennetts
Add tests for server-side logic, and fix the bugs exposed by those tests.
2190
        self.assertHandlerEqual('Repository.get_rev_id_for_revno',
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2191
            smart_repo.SmartServerRepositoryGetRevIdForRevno)
4288.1.2 by Robert Collins
Create a server verb for doing BzrDir.get_config()
2192
        self.assertHandlerEqual('Repository.get_revision_graph',
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2193
            smart_repo.SmartServerRepositoryGetRevisionGraph)
4288.1.2 by Robert Collins
Create a server verb for doing BzrDir.get_config()
2194
        self.assertHandlerEqual('Repository.get_stream',
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2195
            smart_repo.SmartServerRepositoryGetStream)
5539.2.4 by Andrew Bennetts
Add some basic tests for the new verb, fix some shallow bugs.
2196
        self.assertHandlerEqual('Repository.get_stream_1.19',
2197
            smart_repo.SmartServerRepositoryGetStream_1_19)
4288.1.2 by Robert Collins
Create a server verb for doing BzrDir.get_config()
2198
        self.assertHandlerEqual('Repository.has_revision',
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2199
            smart_repo.SmartServerRequestHasRevision)
4288.1.2 by Robert Collins
Create a server verb for doing BzrDir.get_config()
2200
        self.assertHandlerEqual('Repository.insert_stream',
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2201
            smart_repo.SmartServerRepositoryInsertStream)
4288.1.2 by Robert Collins
Create a server verb for doing BzrDir.get_config()
2202
        self.assertHandlerEqual('Repository.insert_stream_locked',
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2203
            smart_repo.SmartServerRepositoryInsertStreamLocked)
4288.1.2 by Robert Collins
Create a server verb for doing BzrDir.get_config()
2204
        self.assertHandlerEqual('Repository.is_shared',
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2205
            smart_repo.SmartServerRepositoryIsShared)
4288.1.2 by Robert Collins
Create a server verb for doing BzrDir.get_config()
2206
        self.assertHandlerEqual('Repository.lock_write',
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2207
            smart_repo.SmartServerRepositoryLockWrite)
6263.2.1 by Jelmer Vernooij
Add hpss call ``Repository.make_working_trees``
2208
        self.assertHandlerEqual('Repository.make_working_trees',
2209
            smart_repo.SmartServerRepositoryMakeWorkingTrees)
4288.1.2 by Robert Collins
Create a server verb for doing BzrDir.get_config()
2210
        self.assertHandlerEqual('Repository.tarball',
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2211
            smart_repo.SmartServerRepositoryTarball)
4288.1.2 by Robert Collins
Create a server verb for doing BzrDir.get_config()
2212
        self.assertHandlerEqual('Repository.unlock',
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2213
            smart_repo.SmartServerRepositoryUnlock)
6280.5.2 by Jelmer Vernooij
New HPSS call VersionedFileRepository.get_serializer_format.
2214
        self.assertHandlerEqual('VersionedFileRepository.get_serializer_format',
2215
            smart_repo.SmartServerRepositoryGetSerializerFormat)
4288.1.2 by Robert Collins
Create a server verb for doing BzrDir.get_config()
2216
        self.assertHandlerEqual('Transport.is_readonly',
5010.2.8 by Vincent Ladeuil
Fix test_smart.py imports.
2217
            smart_req.SmartServerIsReadonly)
5611.1.2 by Jelmer Vernooij
Add some tests for the hooks.
2218
2219
2220
class SmartTCPServerHookTests(tests.TestCaseWithMemoryTransport):
2221
    """Tests for SmartTCPServer hooks."""
2222
2223
    def setUp(self):
2224
        super(SmartTCPServerHookTests, self).setUp()
2225
        self.server = server.SmartTCPServer(self.get_transport())
2226
2227
    def test_run_server_started_hooks(self):
2228
        """Test the server started hooks get fired properly."""
2229
        started_calls = []
2230
        server.SmartTCPServer.hooks.install_named_hook('server_started',
2231
            lambda backing_urls, url: started_calls.append((backing_urls, url)),
2232
            None)
2233
        started_ex_calls = []
2234
        server.SmartTCPServer.hooks.install_named_hook('server_started_ex',
2235
            lambda backing_urls, url: started_ex_calls.append((backing_urls, url)),
2236
            None)
5611.1.3 by Jelmer Vernooij
review comments from Vincent.
2237
        self.server._sockname = ('example.com', 42)
5611.1.2 by Jelmer Vernooij
Add some tests for the hooks.
2238
        self.server.run_server_started_hooks()
2239
        self.assertEquals(started_calls,
5611.1.3 by Jelmer Vernooij
review comments from Vincent.
2240
            [([self.get_transport().base], 'bzr://example.com:42/')])
5611.1.2 by Jelmer Vernooij
Add some tests for the hooks.
2241
        self.assertEquals(started_ex_calls,
2242
            [([self.get_transport().base], self.server)])
2243
2244
    def test_run_server_started_hooks_ipv6(self):
2245
        """Test that socknames can contain 4-tuples."""
2246
        self.server._sockname = ('::', 42, 0, 0)
2247
        started_calls = []
2248
        server.SmartTCPServer.hooks.install_named_hook('server_started',
2249
            lambda backing_urls, url: started_calls.append((backing_urls, url)),
2250
            None)
2251
        self.server.run_server_started_hooks()
2252
        self.assertEquals(started_calls,
2253
                [([self.get_transport().base], 'bzr://:::42/')])
2254
2255
    def test_run_server_stopped_hooks(self):
2256
        """Test the server stopped hooks."""
5611.1.3 by Jelmer Vernooij
review comments from Vincent.
2257
        self.server._sockname = ('example.com', 42)
5611.1.2 by Jelmer Vernooij
Add some tests for the hooks.
2258
        stopped_calls = []
2259
        server.SmartTCPServer.hooks.install_named_hook('server_stopped',
2260
            lambda backing_urls, url: stopped_calls.append((backing_urls, url)),
2261
            None)
2262
        self.server.run_server_stopped_hooks()
2263
        self.assertEquals(stopped_calls,
5611.1.3 by Jelmer Vernooij
review comments from Vincent.
2264
            [([self.get_transport().base], 'bzr://example.com:42/')])