/brz/remove-bazaar

To get this branch, use:
bzr branch http://gegoxaren.bato24.eu/bzr/brz/remove-bazaar
6404.6.1 by Vincent Ladeuil
Tests passing for a first rough version of a cached branch config store. The changes here are too invasive and several parallel proposals have been made.
1
# Copyright (C) 2006-2012 Canonical Ltd
1752.2.30 by Martin Pool
Start adding a RemoteBzrDir, etc
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
1752.2.30 by Martin Pool
Start adding a RemoteBzrDir, etc
16
6379.6.1 by Jelmer Vernooij
Import absolute_import in a few places.
17
from __future__ import absolute_import
18
3211.5.2 by Robert Collins
Change RemoteRepository.get_parent_map to use bz2 not gzip for compression.
19
import bz2
6280.9.4 by Jelmer Vernooij
use zlib instead.
20
import zlib
1752.2.30 by Martin Pool
Start adding a RemoteBzrDir, etc
21
6624 by Jelmer Vernooij
Merge Python3 porting work ('py3 pokes')
22
from . import (
2694.5.4 by Jelmer Vernooij
Move bzrlib.util.bencode to bzrlib._bencode_py.
23
    bencode,
2490.2.5 by Aaron Bentley
Use GraphWalker.unique_ancestor to determine merge base
24
    branch,
6362.6.3 by Jelmer Vernooij
Fix compatibility after config stack changes.
25
    config as _mod_config,
5363.2.10 by Jelmer Vernooij
base ControlDir on ControlComponent.
26
    controldir,
3192.1.1 by Andrew Bennetts
Add some -Dhpss debugging to get_parent_map.
27
    debug,
2490.2.5 by Aaron Bentley
Use GraphWalker.unique_ancestor to determine merge base
28
    errors,
6280.8.1 by Jelmer Vernooij
Avoid _ensure_real in RemoteRepository.verify_revision_signature and RemoteRepository.sign_revision.
29
    gpg,
3172.5.1 by Robert Collins
Create a RemoteRepository get_graph implementation and delegate get_parents_map to the real repository.
30
    graph,
4509.3.28 by Martin Pool
Add missing import
31
    lock,
2490.2.5 by Aaron Bentley
Use GraphWalker.unique_ancestor to determine merge base
32
    lockdir,
6280.10.18 by Jelmer Vernooij
Ensure file ids are always utf8.
33
    osutils,
6284.1.1 by Jelmer Vernooij
Allow registering custom error handlers in the HPSS client.
34
    registry,
5158.4.1 by Andrew Bennetts
Don't allow RemoteRepository to stack on incompatible formats.
35
    repository as _mod_repository,
4307.2.3 by Robert Collins
Change RemoteRepository.has_revision to use get_parent_map to leverage the caching.
36
    revision as _mod_revision,
4913.4.2 by Jelmer Vernooij
Add Repository.get_known_graph_ancestry.
37
    static_tuple,
6280.8.1 by Jelmer Vernooij
Avoid _ensure_real in RemoteRepository.verify_revision_signature and RemoteRepository.sign_revision.
38
    testament as _mod_testament,
5535.3.7 by Andrew Bennetts
Allow for trailing-slash differences between local url path vs. remote url path for remote branch's repository.
39
    urlutils,
6670.4.1 by Jelmer Vernooij
Update imports.
40
    )
41
from .bzr import (
42
    branch as bzrbranch,
43
    bzrdir as _mod_bzrdir,
44
    inventory_delta,
5815.4.1 by Jelmer Vernooij
Split versionedfile-specific stuff out into VersionedFileRepository.
45
    vf_repository,
6341.1.4 by Jelmer Vernooij
Move more functionality to vf_search.
46
    vf_search,
5815.4.1 by Jelmer Vernooij
Split versionedfile-specific stuff out into VersionedFileRepository.
47
    )
6670.4.1 by Jelmer Vernooij
Update imports.
48
from .bzr.branch import BranchReferenceFormat
6653.1.1 by Jelmer Vernooij
Split bzr branch code out into breezy.bzrbranch.
49
from .branch import BranchWriteLockResult
6624 by Jelmer Vernooij
Merge Python3 porting work ('py3 pokes')
50
from .decorators import needs_read_lock, needs_write_lock, only_raises
51
from .errors import (
3376.2.4 by Martin Pool
Remove every assert statement from bzrlib!
52
    NoSuchRevision,
53
    SmartProtocolError,
54
    )
6624 by Jelmer Vernooij
Merge Python3 porting work ('py3 pokes')
55
from .i18n import gettext
6670.4.1 by Jelmer Vernooij
Update imports.
56
from .bzr.inventory import Inventory
6624 by Jelmer Vernooij
Merge Python3 porting work ('py3 pokes')
57
from .lockable_files import LockableFiles
6656.1.1 by Martin
Apply 2to3 dict fixer and clean up resulting mess using view helpers
58
from .sixish import (
59
    viewitems,
60
    viewvalues,
61
    )
6624 by Jelmer Vernooij
Merge Python3 porting work ('py3 pokes')
62
from .smart import client, vfs, repository as smart_repo
63
from .smart.client import _SmartClient
64
from .revision import NULL_REVISION
65
from .revisiontree import InventoryRevisionTree
66
from .repository import RepositoryWriteLockResult, _LazyListJoin
67
from .serializer import format_registry as serializer_format_registry
68
from .trace import mutter, note, warning, log_exception_quietly
6670.4.1 by Jelmer Vernooij
Update imports.
69
from .bzr.versionedfile import FulltextContentFactory
1752.2.30 by Martin Pool
Start adding a RemoteBzrDir, etc
70
3445.1.5 by John Arbash Meinel
allow passing a 'graph' object into Branch.update_revisions.
71
6015.23.12 by John Arbash Meinel
Going with 100 to be friendlier to bandwith/latency constrained environs.
72
_DEFAULT_SEARCH_DEPTH = 100
6015.23.11 by John Arbash Meinel
allow a bit more flexibilty in how we walk the searches.
73
74
3786.2.3 by Andrew Bennetts
Remove duplicated 'call & translate errors' code in bzrlib.remote.
75
class _RpcHelper(object):
76
    """Mixin class that helps with issuing RPCs."""
77
78
    def _call(self, method, *args, **err_context):
79
        try:
80
            return self._client.call(method, *args)
6619.3.2 by Jelmer Vernooij
Apply 2to3 except fix.
81
        except errors.ErrorFromSmartServer as err:
3786.2.3 by Andrew Bennetts
Remove duplicated 'call & translate errors' code in bzrlib.remote.
82
            self._translate_error(err, **err_context)
3943.8.1 by Marius Kruger
remove all trailing whitespace from bzr source
83
3786.2.3 by Andrew Bennetts
Remove duplicated 'call & translate errors' code in bzrlib.remote.
84
    def _call_expecting_body(self, method, *args, **err_context):
85
        try:
86
            return self._client.call_expecting_body(method, *args)
6619.3.2 by Jelmer Vernooij
Apply 2to3 except fix.
87
        except errors.ErrorFromSmartServer as err:
3786.2.3 by Andrew Bennetts
Remove duplicated 'call & translate errors' code in bzrlib.remote.
88
            self._translate_error(err, **err_context)
3943.8.1 by Marius Kruger
remove all trailing whitespace from bzr source
89
4556.2.1 by Andrew Bennetts
Add Branch.set_tags_bytes RPC, with HPSS call count acceptance test. Also fixes serialisation of LockDir, and uses external_url() in LockDir's repr and contention message.
90
    def _call_with_body_bytes(self, method, args, body_bytes, **err_context):
91
        try:
92
            return self._client.call_with_body_bytes(method, args, body_bytes)
6619.3.2 by Jelmer Vernooij
Apply 2to3 except fix.
93
        except errors.ErrorFromSmartServer as err:
4556.2.1 by Andrew Bennetts
Add Branch.set_tags_bytes RPC, with HPSS call count acceptance test. Also fixes serialisation of LockDir, and uses external_url() in LockDir's repr and contention message.
94
            self._translate_error(err, **err_context)
95
3786.2.3 by Andrew Bennetts
Remove duplicated 'call & translate errors' code in bzrlib.remote.
96
    def _call_with_body_bytes_expecting_body(self, method, args, body_bytes,
97
                                             **err_context):
98
        try:
99
            return self._client.call_with_body_bytes_expecting_body(
100
                method, args, body_bytes)
6619.3.2 by Jelmer Vernooij
Apply 2to3 except fix.
101
        except errors.ErrorFromSmartServer as err:
3786.2.3 by Andrew Bennetts
Remove duplicated 'call & translate errors' code in bzrlib.remote.
102
            self._translate_error(err, **err_context)
3943.8.1 by Marius Kruger
remove all trailing whitespace from bzr source
103
4032.3.2 by Robert Collins
Create and use a RPC call to create branches on bzr servers rather than using VFS calls.
104
105
def response_tuple_to_repo_format(response):
106
    """Convert a response tuple describing a repository format to a format."""
107
    format = RemoteRepositoryFormat()
4118.1.1 by Andrew Bennetts
Fix performance regression (many small round-trips) when pushing to a remote pack, and tidy the tests.
108
    format._rich_root_data = (response[0] == 'yes')
109
    format._supports_tree_reference = (response[1] == 'yes')
110
    format._supports_external_lookups = (response[2] == 'yes')
4032.3.2 by Robert Collins
Create and use a RPC call to create branches on bzr servers rather than using VFS calls.
111
    format._network_name = response[3]
112
    return format
113
114
6622.1.34 by Jelmer Vernooij
Rename brzlib => breezy.
115
# Note that RemoteBzrDirProber lives in breezy.bzrdir so breezy.remote
5712.3.13 by Jelmer Vernooij
Add Prober.known_formats().
116
# does not have to be imported unless a remote format is involved.
117
118
class RemoteBzrDirFormat(_mod_bzrdir.BzrDirMetaFormat1):
119
    """Format representing bzrdirs accessed via a smart server"""
120
121
    supports_workingtrees = False
122
6437.21.7 by Jelmer Vernooij
Fix remaining tests.
123
    colocated_branches = False
124
5712.3.13 by Jelmer Vernooij
Add Prober.known_formats().
125
    def __init__(self):
5712.3.17 by Jelmer Vernooij
more fixes.
126
        _mod_bzrdir.BzrDirMetaFormat1.__init__(self)
5712.3.13 by Jelmer Vernooij
Add Prober.known_formats().
127
        # XXX: It's a bit ugly that the network name is here, because we'd
128
        # like to believe that format objects are stateless or at least
129
        # immutable,  However, we do at least avoid mutating the name after
130
        # it's returned.  See <https://bugs.launchpad.net/bzr/+bug/504102>
131
        self._network_name = None
132
133
    def __repr__(self):
134
        return "%s(_network_name=%r)" % (self.__class__.__name__,
135
            self._network_name)
136
137
    def get_format_description(self):
138
        if self._network_name:
6305.4.1 by Jelmer Vernooij
Print sensible error message when remote format is unknown.
139
            try:
140
                real_format = controldir.network_format_registry.get(
141
                        self._network_name)
142
            except KeyError:
143
                pass
144
            else:
145
                return 'Remote: ' + real_format.get_format_description()
5712.3.13 by Jelmer Vernooij
Add Prober.known_formats().
146
        return 'bzr remote bzrdir'
147
148
    def get_format_string(self):
149
        raise NotImplementedError(self.get_format_string)
150
151
    def network_name(self):
152
        if self._network_name:
153
            return self._network_name
154
        else:
155
            raise AssertionError("No network name set.")
156
157
    def initialize_on_transport(self, transport):
158
        try:
159
            # hand off the request to the smart server
160
            client_medium = transport.get_smart_medium()
161
        except errors.NoSmartMedium:
162
            # TODO: lookup the local format from a server hint.
163
            local_dir_format = _mod_bzrdir.BzrDirMetaFormat1()
164
            return local_dir_format.initialize_on_transport(transport)
165
        client = _SmartClient(client_medium)
166
        path = client.remote_path_from_transport(transport)
167
        try:
168
            response = client.call('BzrDirFormat.initialize', path)
6619.3.2 by Jelmer Vernooij
Apply 2to3 except fix.
169
        except errors.ErrorFromSmartServer as err:
5712.3.13 by Jelmer Vernooij
Add Prober.known_formats().
170
            _translate_error(err, path=path)
171
        if response[0] != 'ok':
172
            raise errors.SmartProtocolError('unexpected response code %s' % (response,))
173
        format = RemoteBzrDirFormat()
174
        self._supply_sub_formats_to(format)
175
        return RemoteBzrDir(transport, format)
176
177
    def parse_NoneTrueFalse(self, arg):
178
        if not arg:
179
            return None
180
        if arg == 'False':
181
            return False
182
        if arg == 'True':
183
            return True
184
        raise AssertionError("invalid arg %r" % arg)
185
186
    def _serialize_NoneTrueFalse(self, arg):
187
        if arg is False:
188
            return 'False'
189
        if arg:
190
            return 'True'
191
        return ''
192
193
    def _serialize_NoneString(self, arg):
194
        return arg or ''
195
196
    def initialize_on_transport_ex(self, transport, use_existing_dir=False,
197
        create_prefix=False, force_new_repo=False, stacked_on=None,
198
        stack_on_pwd=None, repo_format_name=None, make_working_trees=None,
199
        shared_repo=False):
200
        try:
201
            # hand off the request to the smart server
202
            client_medium = transport.get_smart_medium()
203
        except errors.NoSmartMedium:
204
            do_vfs = True
205
        else:
206
            # Decline to open it if the server doesn't support our required
207
            # version (3) so that the VFS-based transport will do it.
208
            if client_medium.should_probe():
209
                try:
210
                    server_version = client_medium.protocol_version()
211
                    if server_version != '2':
212
                        do_vfs = True
213
                    else:
214
                        do_vfs = False
215
                except errors.SmartProtocolError:
216
                    # Apparently there's no usable smart server there, even though
217
                    # the medium supports the smart protocol.
218
                    do_vfs = True
219
            else:
220
                do_vfs = False
221
        if not do_vfs:
222
            client = _SmartClient(client_medium)
223
            path = client.remote_path_from_transport(transport)
224
            if client_medium._is_remote_before((1, 16)):
225
                do_vfs = True
226
        if do_vfs:
227
            # TODO: lookup the local format from a server hint.
228
            local_dir_format = _mod_bzrdir.BzrDirMetaFormat1()
229
            self._supply_sub_formats_to(local_dir_format)
230
            return local_dir_format.initialize_on_transport_ex(transport,
231
                use_existing_dir=use_existing_dir, create_prefix=create_prefix,
232
                force_new_repo=force_new_repo, stacked_on=stacked_on,
233
                stack_on_pwd=stack_on_pwd, repo_format_name=repo_format_name,
234
                make_working_trees=make_working_trees, shared_repo=shared_repo,
235
                vfs_only=True)
236
        return self._initialize_on_transport_ex_rpc(client, path, transport,
237
            use_existing_dir, create_prefix, force_new_repo, stacked_on,
238
            stack_on_pwd, repo_format_name, make_working_trees, shared_repo)
239
240
    def _initialize_on_transport_ex_rpc(self, client, path, transport,
241
        use_existing_dir, create_prefix, force_new_repo, stacked_on,
242
        stack_on_pwd, repo_format_name, make_working_trees, shared_repo):
243
        args = []
244
        args.append(self._serialize_NoneTrueFalse(use_existing_dir))
245
        args.append(self._serialize_NoneTrueFalse(create_prefix))
246
        args.append(self._serialize_NoneTrueFalse(force_new_repo))
247
        args.append(self._serialize_NoneString(stacked_on))
248
        # stack_on_pwd is often/usually our transport
249
        if stack_on_pwd:
250
            try:
251
                stack_on_pwd = transport.relpath(stack_on_pwd)
252
                if not stack_on_pwd:
253
                    stack_on_pwd = '.'
254
            except errors.PathNotChild:
255
                pass
256
        args.append(self._serialize_NoneString(stack_on_pwd))
257
        args.append(self._serialize_NoneString(repo_format_name))
258
        args.append(self._serialize_NoneTrueFalse(make_working_trees))
259
        args.append(self._serialize_NoneTrueFalse(shared_repo))
260
        request_network_name = self._network_name or \
261
            _mod_bzrdir.BzrDirFormat.get_default_format().network_name()
262
        try:
263
            response = client.call('BzrDirFormat.initialize_ex_1.16',
264
                request_network_name, path, *args)
265
        except errors.UnknownSmartMethod:
266
            client._medium._remember_remote_is_before((1,16))
267
            local_dir_format = _mod_bzrdir.BzrDirMetaFormat1()
268
            self._supply_sub_formats_to(local_dir_format)
269
            return local_dir_format.initialize_on_transport_ex(transport,
270
                use_existing_dir=use_existing_dir, create_prefix=create_prefix,
271
                force_new_repo=force_new_repo, stacked_on=stacked_on,
272
                stack_on_pwd=stack_on_pwd, repo_format_name=repo_format_name,
273
                make_working_trees=make_working_trees, shared_repo=shared_repo,
274
                vfs_only=True)
6619.3.2 by Jelmer Vernooij
Apply 2to3 except fix.
275
        except errors.ErrorFromSmartServer as err:
5712.3.13 by Jelmer Vernooij
Add Prober.known_formats().
276
            _translate_error(err, path=path)
277
        repo_path = response[0]
278
        bzrdir_name = response[6]
279
        require_stacking = response[7]
280
        require_stacking = self.parse_NoneTrueFalse(require_stacking)
281
        format = RemoteBzrDirFormat()
282
        format._network_name = bzrdir_name
283
        self._supply_sub_formats_to(format)
284
        bzrdir = RemoteBzrDir(transport, format, _client=client)
285
        if repo_path:
286
            repo_format = response_tuple_to_repo_format(response[1:])
287
            if repo_path == '.':
288
                repo_path = ''
289
            if repo_path:
290
                repo_bzrdir_format = RemoteBzrDirFormat()
291
                repo_bzrdir_format._network_name = response[5]
292
                repo_bzr = RemoteBzrDir(transport.clone(repo_path),
293
                    repo_bzrdir_format)
294
            else:
295
                repo_bzr = bzrdir
296
            final_stack = response[8] or None
297
            final_stack_pwd = response[9] or None
298
            if final_stack_pwd:
299
                final_stack_pwd = urlutils.join(
300
                    transport.base, final_stack_pwd)
301
            remote_repo = RemoteRepository(repo_bzr, repo_format)
302
            if len(response) > 10:
303
                # Updated server verb that locks remotely.
304
                repo_lock_token = response[10] or None
305
                remote_repo.lock_write(repo_lock_token, _skip_rpc=True)
306
                if repo_lock_token:
307
                    remote_repo.dont_leave_lock_in_place()
308
            else:
309
                remote_repo.lock_write()
5712.3.17 by Jelmer Vernooij
more fixes.
310
            policy = _mod_bzrdir.UseExistingRepository(remote_repo, final_stack,
5712.3.13 by Jelmer Vernooij
Add Prober.known_formats().
311
                final_stack_pwd, require_stacking)
312
            policy.acquire_repository()
313
        else:
314
            remote_repo = None
315
            policy = None
316
        bzrdir._format.set_branch_format(self.get_branch_format())
317
        if require_stacking:
318
            # The repo has already been created, but we need to make sure that
319
            # we'll make a stackable branch.
320
            bzrdir._format.require_stacking(_skip_repo=True)
321
        return remote_repo, bzrdir, require_stacking, policy
322
323
    def _open(self, transport):
324
        return RemoteBzrDir(transport, self)
325
326
    def __eq__(self, other):
327
        if not isinstance(other, RemoteBzrDirFormat):
328
            return False
329
        return self.get_format_description() == other.get_format_description()
330
331
    def __return_repository_format(self):
332
        # Always return a RemoteRepositoryFormat object, but if a specific bzr
333
        # repository format has been asked for, tell the RemoteRepositoryFormat
334
        # that it should use that for init() etc.
335
        result = RemoteRepositoryFormat()
336
        custom_format = getattr(self, '_repository_format', None)
337
        if custom_format:
338
            if isinstance(custom_format, RemoteRepositoryFormat):
339
                return custom_format
340
            else:
341
                # We will use the custom format to create repositories over the
342
                # wire; expose its details like rich_root_data for code to
343
                # query
344
                result._custom_format = custom_format
345
        return result
346
347
    def get_branch_format(self):
348
        result = _mod_bzrdir.BzrDirMetaFormat1.get_branch_format(self)
349
        if not isinstance(result, RemoteBranchFormat):
350
            new_result = RemoteBranchFormat()
351
            new_result._custom_format = result
352
            # cache the result
353
            self.set_branch_format(new_result)
354
            result = new_result
355
        return result
356
357
    repository_format = property(__return_repository_format,
358
        _mod_bzrdir.BzrDirMetaFormat1._set_repository_format) #.im_func)
359
360
6362.6.3 by Jelmer Vernooij
Fix compatibility after config stack changes.
361
class RemoteControlStore(_mod_config.IniFileStore):
6270.1.6 by Jelmer Vernooij
Provide RemoteControlStore and RemoteBranchStore.
362
    """Control store which attempts to use HPSS calls to retrieve control store.
363
364
    Note that this is specific to bzr-based formats.
365
    """
366
367
    def __init__(self, bzrdir):
368
        super(RemoteControlStore, self).__init__()
369
        self.bzrdir = bzrdir
6270.1.7 by Jelmer Vernooij
Use _ensure_real.
370
        self._real_store = None
6270.1.6 by Jelmer Vernooij
Provide RemoteControlStore and RemoteBranchStore.
371
6270.1.8 by Jelmer Vernooij
Fix RemoteControlStore.
372
    def lock_write(self, token=None):
373
        self._ensure_real()
374
        return self._real_store.lock_write(token)
375
376
    def unlock(self):
377
        self._ensure_real()
378
        return self._real_store.unlock()
379
380
    @needs_write_lock
381
    def save(self):
382
        # We need to be able to override the undecorated implementation
383
        self.save_without_locking()
384
385
    def save_without_locking(self):
386
        super(RemoteControlStore, self).save()
387
6270.1.7 by Jelmer Vernooij
Use _ensure_real.
388
    def _ensure_real(self):
389
        self.bzrdir._ensure_real()
6270.1.8 by Jelmer Vernooij
Fix RemoteControlStore.
390
        if self._real_store is None:
6362.6.3 by Jelmer Vernooij
Fix compatibility after config stack changes.
391
            self._real_store = _mod_config.ControlStore(self.bzrdir)
6270.1.6 by Jelmer Vernooij
Provide RemoteControlStore and RemoteBranchStore.
392
393
    def external_url(self):
6499.3.2 by Vincent Ladeuil
Use a proper unique url for remote config files.
394
        return urlutils.join(self.branch.user_url, 'control.conf')
6270.1.6 by Jelmer Vernooij
Provide RemoteControlStore and RemoteBranchStore.
395
396
    def _load_content(self):
397
        medium = self.bzrdir._client._medium
398
        path = self.bzrdir._path_for_remote_call(self.bzrdir._client)
399
        try:
400
            response, handler = self.bzrdir._call_expecting_body(
401
                'BzrDir.get_config_file', path)
402
        except errors.UnknownSmartMethod:
6270.1.7 by Jelmer Vernooij
Use _ensure_real.
403
            self._ensure_real()
404
            return self._real_store._load_content()
6270.1.6 by Jelmer Vernooij
Provide RemoteControlStore and RemoteBranchStore.
405
        if len(response) and response[0] != 'ok':
406
            raise errors.UnexpectedSmartServerResponse(response)
407
        return handler.read_body_bytes()
408
409
    def _save_content(self, content):
6270.1.12 by Jelmer Vernooij
Note HPSS usage.
410
        # FIXME JRV 2011-11-22: Ideally this should use a
411
        # HPSS call too, but at the moment it is not possible
412
        # to write lock control directories.
413
        self._ensure_real()
414
        return self._real_store._save_content(content)
6270.1.6 by Jelmer Vernooij
Provide RemoteControlStore and RemoteBranchStore.
415
416
5712.3.13 by Jelmer Vernooij
Add Prober.known_formats().
417
class RemoteBzrDir(_mod_bzrdir.BzrDir, _RpcHelper):
2018.5.163 by Andrew Bennetts
Deal with various review comments from Robert.
418
    """Control directory on a remote server, accessed via bzr:// or similar."""
1752.2.30 by Martin Pool
Start adding a RemoteBzrDir, etc
419
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.
420
    def __init__(self, transport, format, _client=None, _force_probe=False):
2018.5.51 by Wouter van Heyst
Test and implement RemoteBranch.last_revision_info()
421
        """Construct a RemoteBzrDir.
422
423
        :param _client: Private parameter for testing. Disables probing and the
424
            use of a real bzrdir.
425
        """
5712.3.13 by Jelmer Vernooij
Add Prober.known_formats().
426
        _mod_bzrdir.BzrDir.__init__(self, transport, format)
1752.2.31 by Martin Pool
[broken] some support for write operations over hpss
427
        # this object holds a delegated bzrdir that uses file-level operations
428
        # to talk to the other side
2018.5.70 by Robert Collins
Only try to get real repositories when an operation requires them.
429
        self._real_bzrdir = None
4634.47.3 by Andrew Bennetts
Add a BzrDir.open_2.1 verb that indicates if there is a workingtree present. Removes the last 2 VFS calls from incremental pushes.
430
        self._has_working_tree = None
4044.1.3 by Robert Collins
Create a one-shot cache of the result of RemoteBzrDir.create_branch, eliminating 3 round trips for nonstacked branches and 5 for stacked.
431
        # 1-shot cache for the call pattern 'create_branch; open_branch' - see
432
        # create_branch for details.
433
        self._next_open_branch_result = None
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
434
435
        if _client is None:
3313.2.3 by Andrew Bennetts
Deprecate Transport.get_shared_medium.
436
            medium = transport.get_smart_medium()
3431.3.2 by Andrew Bennetts
Remove 'base' from _SmartClient entirely, now that the medium has it.
437
            self._client = client._SmartClient(medium)
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
438
        else:
439
            self._client = _client
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.
440
            if not _force_probe:
441
                return
442
443
        self._probe_bzrdir()
444
4964.2.1 by Martin Pool
Add RemoteBzrDir repr
445
    def __repr__(self):
446
        return '%s(%r)' % (self.__class__.__name__, self._client)
447
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.
448
    def _probe_bzrdir(self):
449
        medium = self._client._medium
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
450
        path = self._path_for_remote_call(self._client)
4634.47.3 by Andrew Bennetts
Add a BzrDir.open_2.1 verb that indicates if there is a workingtree present. Removes the last 2 VFS calls from incremental pushes.
451
        if medium._is_remote_before((2, 1)):
452
            self._rpc_open(path)
453
            return
454
        try:
455
            self._rpc_open_2_1(path)
456
            return
457
        except errors.UnknownSmartMethod:
458
            medium._remember_remote_is_before((2, 1))
459
            self._rpc_open(path)
460
461
    def _rpc_open_2_1(self, path):
462
        response = self._call('BzrDir.open_2.1', path)
463
        if response == ('no',):
464
            raise errors.NotBranchError(path=self.root_transport.base)
465
        elif response[0] == 'yes':
466
            if response[1] == 'yes':
467
                self._has_working_tree = True
468
            elif response[1] == 'no':
469
                self._has_working_tree = False
470
            else:
471
                raise errors.UnexpectedSmartServerResponse(response)
472
        else:
473
            raise errors.UnexpectedSmartServerResponse(response)
474
475
    def _rpc_open(self, path):
3786.2.3 by Andrew Bennetts
Remove duplicated 'call & translate errors' code in bzrlib.remote.
476
        response = self._call('BzrDir.open', path)
2018.5.163 by Andrew Bennetts
Deal with various review comments from Robert.
477
        if response not in [('yes',), ('no',)]:
478
            raise errors.UnexpectedSmartServerResponse(response)
2018.5.26 by Andrew Bennetts
Extract a simple SmartClient class from RemoteTransport, and a hack to avoid VFS operations when probing for a bzrdir over a smart transport.
479
        if response == ('no',):
4634.47.3 by Andrew Bennetts
Add a BzrDir.open_2.1 verb that indicates if there is a workingtree present. Removes the last 2 VFS calls from incremental pushes.
480
            raise errors.NotBranchError(path=self.root_transport.base)
1752.2.31 by Martin Pool
[broken] some support for write operations over hpss
481
2018.5.70 by Robert Collins
Only try to get real repositories when an operation requires them.
482
    def _ensure_real(self):
483
        """Ensure that there is a _real_bzrdir set.
484
2018.5.163 by Andrew Bennetts
Deal with various review comments from Robert.
485
        Used before calls to self._real_bzrdir.
2018.5.70 by Robert Collins
Only try to get real repositories when an operation requires them.
486
        """
487
        if not self._real_bzrdir:
4789.2.1 by Robert Collins
Trigger hpssvfs backtrace dumps with RemoteBzrDir._ensure_real.
488
            if 'hpssvfs' in debug.debug_flags:
489
                import traceback
490
                warning('VFS BzrDir access triggered\n%s',
491
                    ''.join(traceback.format_stack()))
5712.3.13 by Jelmer Vernooij
Add Prober.known_formats().
492
            self._real_bzrdir = _mod_bzrdir.BzrDir.open_from_transport(
6402.3.3 by Jelmer Vernooij
Simplify safe open a bit more.
493
                self.root_transport, probers=[_mod_bzrdir.BzrProber])
4070.2.1 by Robert Collins
Add a BzrDirFormat.network_name.
494
            self._format._network_name = \
495
                self._real_bzrdir._format.network_name()
2018.5.70 by Robert Collins
Only try to get real repositories when an operation requires them.
496
3786.2.3 by Andrew Bennetts
Remove duplicated 'call & translate errors' code in bzrlib.remote.
497
    def _translate_error(self, err, **context):
498
        _translate_error(err, bzrdir=self, **context)
499
4044.1.3 by Robert Collins
Create a one-shot cache of the result of RemoteBzrDir.create_branch, eliminating 3 round trips for nonstacked branches and 5 for stacked.
500
    def break_lock(self):
501
        # Prevent aliasing problems in the next_open_branch_result cache.
502
        # See create_branch for rationale.
503
        self._next_open_branch_result = None
5712.3.13 by Jelmer Vernooij
Add Prober.known_formats().
504
        return _mod_bzrdir.BzrDir.break_lock(self)
4044.1.3 by Robert Collins
Create a one-shot cache of the result of RemoteBzrDir.create_branch, eliminating 3 round trips for nonstacked branches and 5 for stacked.
505
6305.5.10 by Jelmer Vernooij
Move to BzrDir.checkout_metadir.
506
    def _vfs_checkout_metadir(self):
507
        self._ensure_real()
508
        return self._real_bzrdir.checkout_metadir()
509
510
    def checkout_metadir(self):
6305.5.14 by Jelmer Vernooij
Client-side documentation.
511
        """Retrieve the controldir format to use for checkouts of this one.
512
        """
6305.5.10 by Jelmer Vernooij
Move to BzrDir.checkout_metadir.
513
        medium = self._client._medium
514
        if medium._is_remote_before((2, 5)):
515
            return self._vfs_checkout_metadir()
516
        path = self._path_for_remote_call(self._client)
517
        try:
518
            response = self._client.call('BzrDir.checkout_metadir',
519
                path)
520
        except errors.UnknownSmartMethod:
521
            medium._remember_remote_is_before((2, 5))
522
            return self._vfs_checkout_metadir()
523
        if len(response) != 3:
524
            raise errors.UnexpectedSmartServerResponse(response)
525
        control_name, repo_name, branch_name = response
526
        try:
527
            format = controldir.network_format_registry.get(control_name)
528
        except KeyError:
6305.5.14 by Jelmer Vernooij
Client-side documentation.
529
            raise errors.UnknownFormatError(kind='control',
530
                format=control_name)
6305.5.10 by Jelmer Vernooij
Move to BzrDir.checkout_metadir.
531
        if repo_name:
532
            try:
533
                repo_format = _mod_repository.network_format_registry.get(
534
                    repo_name)
535
            except KeyError:
536
                raise errors.UnknownFormatError(kind='repository',
537
                    format=repo_name)
538
            format.repository_format = repo_format
539
        if branch_name:
540
            try:
541
                format.set_branch_format(
542
                    branch.network_format_registry.get(branch_name))
543
            except KeyError:
544
                raise errors.UnknownFormatError(kind='branch',
545
                    format=branch_name)
546
        return format
547
4070.2.3 by Robert Collins
Get BzrDir.cloning_metadir working.
548
    def _vfs_cloning_metadir(self, require_stacking=False):
3242.3.28 by Aaron Bentley
Use repository acquisition policy for sprouting
549
        self._ensure_real()
4070.2.3 by Robert Collins
Get BzrDir.cloning_metadir working.
550
        return self._real_bzrdir.cloning_metadir(
551
            require_stacking=require_stacking)
552
553
    def cloning_metadir(self, require_stacking=False):
554
        medium = self._client._medium
555
        if medium._is_remote_before((1, 13)):
556
            return self._vfs_cloning_metadir(require_stacking=require_stacking)
557
        verb = 'BzrDir.cloning_metadir'
558
        if require_stacking:
559
            stacking = 'True'
560
        else:
561
            stacking = 'False'
562
        path = self._path_for_remote_call(self._client)
563
        try:
564
            response = self._call(verb, path, stacking)
565
        except errors.UnknownSmartMethod:
4094.1.1 by Andrew Bennetts
Add some medium._remember_is_before((1, 13)) calls.
566
            medium._remember_remote_is_before((1, 13))
4070.2.3 by Robert Collins
Get BzrDir.cloning_metadir working.
567
            return self._vfs_cloning_metadir(require_stacking=require_stacking)
6619.3.2 by Jelmer Vernooij
Apply 2to3 except fix.
568
        except errors.UnknownErrorFromSmartServer as err:
4160.2.9 by Andrew Bennetts
Fix BzrDir.cloning_metadir RPC to fail on branch references, and make
569
            if err.error_tuple != ('BranchReference',):
570
                raise
571
            # We need to resolve the branch reference to determine the
572
            # cloning_metadir.  This causes unnecessary RPCs to open the
573
            # referenced branch (and bzrdir, etc) but only when the caller
574
            # didn't already resolve the branch reference.
575
            referenced_branch = self.open_branch()
576
            return referenced_branch.bzrdir.cloning_metadir()
4070.2.3 by Robert Collins
Get BzrDir.cloning_metadir working.
577
        if len(response) != 3:
578
            raise errors.UnexpectedSmartServerResponse(response)
4070.7.4 by Andrew Bennetts
Deal with branch references better in BzrDir.cloning_metadir RPC (changes protocol).
579
        control_name, repo_name, branch_info = response
580
        if len(branch_info) != 2:
581
            raise errors.UnexpectedSmartServerResponse(response)
582
        branch_ref, branch_name = branch_info
6305.4.1 by Jelmer Vernooij
Print sensible error message when remote format is unknown.
583
        try:
584
            format = controldir.network_format_registry.get(control_name)
585
        except KeyError:
586
            raise errors.UnknownFormatError(kind='control', format=control_name)
587
4070.2.3 by Robert Collins
Get BzrDir.cloning_metadir working.
588
        if repo_name:
6305.4.1 by Jelmer Vernooij
Print sensible error message when remote format is unknown.
589
            try:
590
                format.repository_format = _mod_repository.network_format_registry.get(
591
                    repo_name)
592
            except KeyError:
593
                raise errors.UnknownFormatError(kind='repository',
594
                    format=repo_name)
4084.2.2 by Robert Collins
Review feedback.
595
        if branch_ref == 'ref':
4070.7.4 by Andrew Bennetts
Deal with branch references better in BzrDir.cloning_metadir RPC (changes protocol).
596
            # XXX: we need possible_transports here to avoid reopening the
4070.7.5 by Andrew Bennetts
Tweak comment.
597
            # connection to the referenced location
5712.3.13 by Jelmer Vernooij
Add Prober.known_formats().
598
            ref_bzrdir = _mod_bzrdir.BzrDir.open(branch_name)
4070.7.4 by Andrew Bennetts
Deal with branch references better in BzrDir.cloning_metadir RPC (changes protocol).
599
            branch_format = ref_bzrdir.cloning_metadir().get_branch_format()
600
            format.set_branch_format(branch_format)
4084.2.2 by Robert Collins
Review feedback.
601
        elif branch_ref == 'branch':
4070.7.4 by Andrew Bennetts
Deal with branch references better in BzrDir.cloning_metadir RPC (changes protocol).
602
            if branch_name:
6305.4.1 by Jelmer Vernooij
Print sensible error message when remote format is unknown.
603
                try:
604
                    branch_format = branch.network_format_registry.get(
605
                        branch_name)
606
                except KeyError:
607
                    raise errors.UnknownFormatError(kind='branch',
608
                        format=branch_name)
609
                format.set_branch_format(branch_format)
4070.7.4 by Andrew Bennetts
Deal with branch references better in BzrDir.cloning_metadir RPC (changes protocol).
610
        else:
611
            raise errors.UnexpectedSmartServerResponse(response)
4070.2.3 by Robert Collins
Get BzrDir.cloning_metadir working.
612
        return format
3242.3.28 by Aaron Bentley
Use repository acquisition policy for sprouting
613
1752.2.39 by Martin Pool
[broken] implement upgrade apis on remote bzrdirs
614
    def create_repository(self, shared=False):
4005.2.1 by Robert Collins
Fix RemoteBranch to be used correctly in tests using bzr+ssh, to fire off Branch hooks correctly, and improve the branch_implementations tests to check that making a branch gets the right format under test.
615
        # as per meta1 formats - just delegate to the format object which may
616
        # be parameterised.
617
        result = self._format.repository_format.initialize(self, shared)
618
        if not isinstance(result, RemoteRepository):
619
            return self.open_repository()
620
        else:
621
            return result
1752.2.50 by Andrew Bennetts
Implement RemoteBzrDir.create_{branch,workingtree}
622
2796.2.19 by Aaron Bentley
Support reconfigure --lightweight-checkout
623
    def destroy_repository(self):
624
        """See BzrDir.destroy_repository"""
6266.2.1 by Jelmer Vernooij
New HPSS call BzrDir.destroy_repository.
625
        path = self._path_for_remote_call(self._client)
626
        try:
627
            response = self._call('BzrDir.destroy_repository', path)
628
        except errors.UnknownSmartMethod:
629
            self._ensure_real()
630
            self._real_bzrdir.destroy_repository()
631
            return
632
        if response[0] != 'ok':
633
            raise SmartProtocolError('unexpected response code %s' % (response,))
2796.2.19 by Aaron Bentley
Support reconfigure --lightweight-checkout
634
6123.9.12 by Jelmer Vernooij
Add append_revisions_only argument to BranchFormat.initialize.
635
    def create_branch(self, name=None, repository=None,
636
                      append_revisions_only=None):
6436.1.2 by Jelmer Vernooij
Fix some tests.
637
        if name is None:
638
            name = self._get_selected_branch()
6437.21.9 by Jelmer Vernooij
Some fixes.
639
        if name != "":
640
            raise errors.NoColocatedBranchSupport(self)
4005.2.1 by Robert Collins
Fix RemoteBranch to be used correctly in tests using bzr+ssh, to fire off Branch hooks correctly, and improve the branch_implementations tests to check that making a branch gets the right format under test.
641
        # as per meta1 formats - just delegate to the format object which may
642
        # be parameterised.
5051.3.10 by Jelmer Vernooij
Pass colocated branch name around in more places.
643
        real_branch = self._format.get_branch_format().initialize(self,
6123.9.12 by Jelmer Vernooij
Add append_revisions_only argument to BranchFormat.initialize.
644
            name=name, repository=repository,
645
            append_revisions_only=append_revisions_only)
4005.2.1 by Robert Collins
Fix RemoteBranch to be used correctly in tests using bzr+ssh, to fire off Branch hooks correctly, and improve the branch_implementations tests to check that making a branch gets the right format under test.
646
        if not isinstance(real_branch, RemoteBranch):
5536.1.1 by Andrew Bennetts
Avoid reopening (and relocking) the same branches/repositories in ControlDir.sprout. Still a few rough edges, but the tests I've run are passing.
647
            if not isinstance(repository, RemoteRepository):
5536.1.10 by Andrew Bennetts
Give more helpful message in AssertionErrors, just in case.
648
                raise AssertionError(
649
                    'need a RemoteRepository to use with RemoteBranch, got %r'
650
                    % (repository,))
5536.1.1 by Andrew Bennetts
Avoid reopening (and relocking) the same branches/repositories in ControlDir.sprout. Still a few rough edges, but the tests I've run are passing.
651
            result = RemoteBranch(self, repository, real_branch, name=name)
4005.2.1 by Robert Collins
Fix RemoteBranch to be used correctly in tests using bzr+ssh, to fire off Branch hooks correctly, and improve the branch_implementations tests to check that making a branch gets the right format under test.
652
        else:
4044.1.3 by Robert Collins
Create a one-shot cache of the result of RemoteBzrDir.create_branch, eliminating 3 round trips for nonstacked branches and 5 for stacked.
653
            result = real_branch
654
        # BzrDir.clone_on_transport() uses the result of create_branch but does
655
        # not return it to its callers; we save approximately 8% of our round
656
        # trips by handing the branch we created back to the first caller to
657
        # open_branch rather than probing anew. Long term we need a API in
658
        # bzrdir that doesn't discard result objects (like result_branch).
659
        # RBC 20090225
660
        self._next_open_branch_result = result
661
        return result
1752.2.50 by Andrew Bennetts
Implement RemoteBzrDir.create_{branch,workingtree}
662
5051.3.3 by Jelmer Vernooij
Add tests for colo branches.
663
    def destroy_branch(self, name=None):
2796.2.16 by Aaron Bentley
Documentation updates from review
664
        """See BzrDir.destroy_branch"""
6437.21.9 by Jelmer Vernooij
Some fixes.
665
        if name is None:
666
            name = self._get_selected_branch()
667
        if name != "":
668
            raise errors.NoColocatedBranchSupport(self)
6266.4.1 by Jelmer Vernooij
HPSS call 'BzrDir.destroy_branch'.
669
        path = self._path_for_remote_call(self._client)
670
        try:
6437.21.9 by Jelmer Vernooij
Some fixes.
671
            if name != "":
6266.4.3 by Jelmer Vernooij
fix tests.
672
                args = (name, )
673
            else:
674
                args = ()
675
            response = self._call('BzrDir.destroy_branch', path, *args)
6266.4.1 by Jelmer Vernooij
HPSS call 'BzrDir.destroy_branch'.
676
        except errors.UnknownSmartMethod:
677
            self._ensure_real()
678
            self._real_bzrdir.destroy_branch(name=name)
679
            self._next_open_branch_result = None
680
            return
6266.4.3 by Jelmer Vernooij
fix tests.
681
        self._next_open_branch_result = None
6266.4.1 by Jelmer Vernooij
HPSS call 'BzrDir.destroy_branch'.
682
        if response[0] != 'ok':
683
            raise SmartProtocolError('unexpected response code %s' % (response,))
2796.2.6 by Aaron Bentley
Implement destroy_branch
684
5042.1.1 by Neil Martinsen-Burrell
Fix signature of RemoteBzrDir.create_workingtree
685
    def create_workingtree(self, revision_id=None, from_branch=None,
686
        accelerator_tree=None, hardlink=False):
2018.5.174 by Andrew Bennetts
Various nits discovered by pyflakes.
687
        raise errors.NotLocalUrl(self.transport.base)
1752.2.39 by Martin Pool
[broken] implement upgrade apis on remote bzrdirs
688
5147.4.1 by Jelmer Vernooij
Pass branch names in more places.
689
    def find_branch_format(self, name=None):
2018.5.124 by Robert Collins
Fix test_format_initialize_find_open by delegating Branch formt lookup to the BzrDir, where it should have stayed from the start.
690
        """Find the branch 'format' for this bzrdir.
691
692
        This might be a synthetic object for e.g. RemoteBranch and SVN.
693
        """
5147.4.3 by Jelmer Vernooij
Support branch name argument to BzrDir.get_branch_reference.
694
        b = self.open_branch(name=name)
2018.5.124 by Robert Collins
Fix test_format_initialize_find_open by delegating Branch formt lookup to the BzrDir, where it should have stayed from the start.
695
        return b._format
696
6436.3.1 by Jelmer Vernooij
Add remote get_branches call.
697
    def get_branches(self, possible_transports=None, ignore_fallbacks=False):
698
        path = self._path_for_remote_call(self._client)
699
        try:
700
            response, handler = self._call_expecting_body(
701
                'BzrDir.get_branches', path)
702
        except errors.UnknownSmartMethod:
703
            self._ensure_real()
704
            return self._real_bzrdir.get_branches()
705
        if response[0] != "success":
706
            raise errors.UnexpectedSmartServerResponse(response)
707
        body = bencode.bdecode(handler.read_body_bytes())
708
        ret = {}
6656.1.1 by Martin
Apply 2to3 dict fixer and clean up resulting mess using view helpers
709
        for name, value in viewitems(body):
6436.3.1 by Jelmer Vernooij
Add remote get_branches call.
710
            ret[name] = self._open_branch(name, value[0], value[1],
711
                possible_transports=possible_transports,
712
                ignore_fallbacks=ignore_fallbacks)
713
        return ret
714
6437.7.1 by Jelmer Vernooij
Add ControlDir.set_branch_reference.
715
    def set_branch_reference(self, target_branch, name=None):
716
        """See BzrDir.set_branch_reference()."""
6437.21.9 by Jelmer Vernooij
Some fixes.
717
        if name is None:
718
            name = self._get_selected_branch()
719
        if name != "":
720
            raise errors.NoColocatedBranchSupport(self)
6437.7.1 by Jelmer Vernooij
Add ControlDir.set_branch_reference.
721
        self._ensure_real()
722
        return self._real_bzrdir.set_branch_reference(target_branch, name=name)
723
5147.4.3 by Jelmer Vernooij
Support branch name argument to BzrDir.get_branch_reference.
724
    def get_branch_reference(self, name=None):
2018.5.132 by Robert Collins
Make all BzrDir implementation tests pass on RemoteBzrDir - fix some things, and remove the incomplete_with_basis tests as cruft.
725
        """See BzrDir.get_branch_reference()."""
6437.21.9 by Jelmer Vernooij
Some fixes.
726
        if name is None:
727
            name = self._get_selected_branch()
728
        if name != "":
5147.4.3 by Jelmer Vernooij
Support branch name argument to BzrDir.get_branch_reference.
729
            raise errors.NoColocatedBranchSupport(self)
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.
730
        response = self._get_branch_reference()
731
        if response[0] == 'ref':
732
            return response[1]
733
        else:
734
            return None
735
736
    def _get_branch_reference(self):
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
737
        path = self._path_for_remote_call(self._client)
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.
738
        medium = self._client._medium
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).
739
        candidate_calls = [
740
            ('BzrDir.open_branchV3', (2, 1)),
741
            ('BzrDir.open_branchV2', (1, 13)),
742
            ('BzrDir.open_branch', None),
743
            ]
744
        for verb, required_version in candidate_calls:
745
            if required_version and medium._is_remote_before(required_version):
746
                continue
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.
747
            try:
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).
748
                response = self._call(verb, path)
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.
749
            except errors.UnknownSmartMethod:
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).
750
                if required_version is None:
751
                    raise
752
                medium._remember_remote_is_before(required_version)
753
            else:
754
                break
755
        if verb == 'BzrDir.open_branch':
756
            if response[0] != 'ok':
757
                raise errors.UnexpectedSmartServerResponse(response)
758
            if response[1] != '':
759
                return ('ref', response[1])
760
            else:
761
                return ('branch', '')
762
        if response[0] not in ('ref', 'branch'):
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.
763
            raise errors.UnexpectedSmartServerResponse(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).
764
        return response
2018.5.132 by Robert Collins
Make all BzrDir implementation tests pass on RemoteBzrDir - fix some things, and remove the incomplete_with_basis tests as cruft.
765
5147.4.1 by Jelmer Vernooij
Pass branch names in more places.
766
    def _get_tree_branch(self, name=None):
3211.4.1 by Robert Collins
* ``RemoteBzrDir._get_tree_branch`` no longer triggers ``_ensure_real``,
767
        """See BzrDir._get_tree_branch()."""
5147.4.1 by Jelmer Vernooij
Pass branch names in more places.
768
        return None, self.open_branch(name=name)
3211.4.1 by Robert Collins
* ``RemoteBzrDir._get_tree_branch`` no longer triggers ``_ensure_real``,
769
6436.3.1 by Jelmer Vernooij
Add remote get_branches call.
770
    def _open_branch(self, name, kind, location_or_format,
771
                     ignore_fallbacks=False, possible_transports=None):
772
        if kind == 'ref':
2018.5.132 by Robert Collins
Make all BzrDir implementation tests pass on RemoteBzrDir - fix some things, and remove the incomplete_with_basis tests as cruft.
773
            # a branch reference, use the existing BranchReference logic.
774
            format = BranchReferenceFormat()
5051.3.10 by Jelmer Vernooij
Pass colocated branch name around in more places.
775
            return format.open(self, name=name, _found=True,
6436.3.1 by Jelmer Vernooij
Add remote get_branches call.
776
                location=location_or_format, ignore_fallbacks=ignore_fallbacks,
6305.3.2 by Jelmer Vernooij
Only make a single connection.
777
                possible_transports=possible_transports)
6436.3.1 by Jelmer Vernooij
Add remote get_branches call.
778
        branch_format_name = location_or_format
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.
779
        if not branch_format_name:
780
            branch_format_name = None
781
        format = RemoteBranchFormat(network_name=branch_format_name)
4160.2.6 by Andrew Bennetts
Add ignore_fallbacks flag.
782
        return RemoteBranch(self, self.find_repository(), format=format,
6305.3.6 by Jelmer Vernooij
Pass possible_transports along for remote branches.
783
            setup_stacking=not ignore_fallbacks, name=name,
784
            possible_transports=possible_transports)
3943.8.1 by Marius Kruger
remove all trailing whitespace from bzr source
785
6436.3.1 by Jelmer Vernooij
Add remote get_branches call.
786
    def open_branch(self, name=None, unsupported=False,
787
                    ignore_fallbacks=False, possible_transports=None):
6437.21.11 by Jelmer Vernooij
actually run per_controldir_colo tests against RemoteBzrDir.
788
        if name is None:
789
            name = self._get_selected_branch()
790
        if name != "":
791
            raise errors.NoColocatedBranchSupport(self)
6436.3.1 by Jelmer Vernooij
Add remote get_branches call.
792
        if unsupported:
793
            raise NotImplementedError('unsupported flag support not implemented yet.')
794
        if self._next_open_branch_result is not None:
795
            # See create_branch for details.
796
            result = self._next_open_branch_result
797
            self._next_open_branch_result = None
798
            return result
799
        response = self._get_branch_reference()
800
        return self._open_branch(name, response[0], response[1],
801
            possible_transports=possible_transports,
802
            ignore_fallbacks=ignore_fallbacks)
803
4053.1.1 by Robert Collins
New version of the BzrDir.find_repository verb supporting _network_name to support removing more _ensure_real calls.
804
    def _open_repo_v1(self, path):
805
        verb = 'BzrDir.find_repository'
806
        response = self._call(verb, path)
807
        if response[0] != 'ok':
808
            raise errors.UnexpectedSmartServerResponse(response)
809
        # servers that only support the v1 method don't support external
810
        # references either.
811
        self._ensure_real()
812
        repo = self._real_bzrdir.open_repository()
813
        response = response + ('no', repo._format.network_name())
814
        return response, repo
815
816
    def _open_repo_v2(self, path):
817
        verb = 'BzrDir.find_repositoryV2'
818
        response = self._call(verb, path)
819
        if response[0] != 'ok':
820
            raise errors.UnexpectedSmartServerResponse(response)
821
        self._ensure_real()
822
        repo = self._real_bzrdir.open_repository()
823
        response = response + (repo._format.network_name(),)
824
        return response, repo
825
826
    def _open_repo_v3(self, path):
827
        verb = 'BzrDir.find_repositoryV3'
4053.1.2 by Robert Collins
Actually make this branch work.
828
        medium = self._client._medium
829
        if medium._is_remote_before((1, 13)):
830
            raise errors.UnknownSmartMethod(verb)
4094.1.1 by Andrew Bennetts
Add some medium._remember_is_before((1, 13)) calls.
831
        try:
832
            response = self._call(verb, path)
833
        except errors.UnknownSmartMethod:
834
            medium._remember_remote_is_before((1, 13))
835
            raise
4053.1.1 by Robert Collins
New version of the BzrDir.find_repository verb supporting _network_name to support removing more _ensure_real calls.
836
        if response[0] != 'ok':
837
            raise errors.UnexpectedSmartServerResponse(response)
838
        return response, None
839
1752.2.31 by Martin Pool
[broken] some support for write operations over hpss
840
    def open_repository(self):
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
841
        path = self._path_for_remote_call(self._client)
4053.1.1 by Robert Collins
New version of the BzrDir.find_repository verb supporting _network_name to support removing more _ensure_real calls.
842
        response = None
843
        for probe in [self._open_repo_v3, self._open_repo_v2,
844
            self._open_repo_v1]:
845
            try:
846
                response, real_repo = probe(path)
847
                break
848
            except errors.UnknownSmartMethod:
849
                pass
850
        if response is None:
851
            raise errors.UnknownSmartMethod('BzrDir.find_repository{3,2,}')
3245.4.24 by Andrew Bennetts
Consistently raise errors from the server as ErrorFromSmartServer exceptions.
852
        if response[0] != 'ok':
853
            raise errors.UnexpectedSmartServerResponse(response)
4053.1.1 by Robert Collins
New version of the BzrDir.find_repository verb supporting _network_name to support removing more _ensure_real calls.
854
        if len(response) != 6:
3376.2.4 by Martin Pool
Remove every assert statement from bzrlib!
855
            raise SmartProtocolError('incorrect response length %s' % (response,))
2018.5.34 by Robert Collins
Get test_remote.BasicRemoteObjectTests.test_open_remote_branch passing by implementing a remote method BzrDir.find_repository.
856
        if response[1] == '':
4053.1.1 by Robert Collins
New version of the BzrDir.find_repository verb supporting _network_name to support removing more _ensure_real calls.
857
            # repo is at this dir.
858
            format = response_tuple_to_repo_format(response[2:])
3221.15.10 by Robert Collins
Add test that we can stack on a smart server from Jonathan Lange.
859
            # Used to support creating a real format instance when needed.
860
            format._creating_bzrdir = self
3990.5.1 by Andrew Bennetts
Add network_name() to RepositoryFormat.
861
            remote_repo = RemoteRepository(self, format)
862
            format._creating_repo = remote_repo
4053.1.1 by Robert Collins
New version of the BzrDir.find_repository verb supporting _network_name to support removing more _ensure_real calls.
863
            if real_repo is not None:
864
                remote_repo._set_real_repository(real_repo)
3990.5.1 by Andrew Bennetts
Add network_name() to RepositoryFormat.
865
            return remote_repo
2018.5.34 by Robert Collins
Get test_remote.BasicRemoteObjectTests.test_open_remote_branch passing by implementing a remote method BzrDir.find_repository.
866
        else:
867
            raise errors.NoRepositoryPresent(self)
1752.2.30 by Martin Pool
Start adding a RemoteBzrDir, etc
868
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.
869
    def has_workingtree(self):
4634.47.3 by Andrew Bennetts
Add a BzrDir.open_2.1 verb that indicates if there is a workingtree present. Removes the last 2 VFS calls from incremental pushes.
870
        if self._has_working_tree is None:
6266.3.1 by Jelmer Vernooij
Add HPSS call for BzrDir.has_workingtree.
871
            path = self._path_for_remote_call(self._client)
872
            try:
873
                response = self._call('BzrDir.has_workingtree', path)
874
            except errors.UnknownSmartMethod:
875
                self._ensure_real()
876
                self._has_working_tree = self._real_bzrdir.has_workingtree()
877
            else:
878
                if response[0] not in ('yes', 'no'):
879
                    raise SmartProtocolError('unexpected response code %s' % (response,))
880
                self._has_working_tree = (response[0] == '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.
881
        return self._has_working_tree
882
883
    def open_workingtree(self, recommend_upgrade=True):
884
        if self.has_workingtree():
2445.1.1 by Andrew Bennetts
Make RemoteBzrDir.open_workingtree raise NoWorkingTree rather than NotLocalUrl
885
            raise errors.NotLocalUrl(self.root_transport)
886
        else:
887
            raise errors.NoWorkingTree(self.root_transport.base)
1752.2.50 by Andrew Bennetts
Implement RemoteBzrDir.create_{branch,workingtree}
888
2018.5.42 by Robert Collins
Various hopefully improvements, but wsgi is broken, handing over to spiv :).
889
    def _path_for_remote_call(self, client):
2018.6.1 by Robert Collins
Implement a BzrDir.open_branch smart server method for opening a branch without VFS.
890
        """Return the path to be used for this bzrdir in a remote call."""
5268.7.29 by Jelmer Vernooij
Fix remote tests.
891
        return urlutils.split_segment_parameters_raw(
892
            client.remote_path_from_transport(self.root_transport))[0]
2018.6.1 by Robert Collins
Implement a BzrDir.open_branch smart server method for opening a branch without VFS.
893
5051.3.10 by Jelmer Vernooij
Pass colocated branch name around in more places.
894
    def get_branch_transport(self, branch_format, name=None):
2018.5.162 by Andrew Bennetts
Add some missing _ensure_real calls, and a missing import.
895
        self._ensure_real()
5051.3.10 by Jelmer Vernooij
Pass colocated branch name around in more places.
896
        return self._real_bzrdir.get_branch_transport(branch_format, name=name)
1752.2.31 by Martin Pool
[broken] some support for write operations over hpss
897
1752.2.43 by Andrew Bennetts
Fix get_{branch,repository,workingtree}_transport.
898
    def get_repository_transport(self, repository_format):
2018.5.162 by Andrew Bennetts
Add some missing _ensure_real calls, and a missing import.
899
        self._ensure_real()
1752.2.43 by Andrew Bennetts
Fix get_{branch,repository,workingtree}_transport.
900
        return self._real_bzrdir.get_repository_transport(repository_format)
901
902
    def get_workingtree_transport(self, workingtree_format):
2018.5.162 by Andrew Bennetts
Add some missing _ensure_real calls, and a missing import.
903
        self._ensure_real()
1752.2.43 by Andrew Bennetts
Fix get_{branch,repository,workingtree}_transport.
904
        return self._real_bzrdir.get_workingtree_transport(workingtree_format)
905
1752.2.39 by Martin Pool
[broken] implement upgrade apis on remote bzrdirs
906
    def can_convert_format(self):
907
        """Upgrading of remote bzrdirs is not supported yet."""
908
        return False
909
5670.1.1 by Jelmer Vernooij
Remove all methods and arguments that were deprecated before bzr 2.0.0.
910
    def needs_format_conversion(self, format):
1752.2.39 by Martin Pool
[broken] implement upgrade apis on remote bzrdirs
911
        """Upgrading of remote bzrdirs is not supported yet."""
912
        return False
913
4288.1.1 by Robert Collins
Add support for a RemoteBzrDirConfig to support optimising push operations which need to look for default stacking locations.
914
    def _get_config(self):
915
        return RemoteBzrDirConfig(self)
3567.1.3 by Michael Hudson
fix problem
916
6270.1.19 by Jelmer Vernooij
Some changes discussed with vila on IRC.
917
    def _get_config_store(self):
918
        return RemoteControlStore(self)
6270.1.4 by Jelmer Vernooij
Add Branch.get_config_stack / BzrDir.get_config_stack.
919
1752.2.31 by Martin Pool
[broken] some support for write operations over hpss
920
5815.4.5 by Jelmer Vernooij
Use MetaDirVersionedFileRepositoryFormat (a Soyuz worthy name).
921
class RemoteRepositoryFormat(vf_repository.VersionedFileRepositoryFormat):
2018.5.159 by Andrew Bennetts
Rename SmartClient to _SmartClient.
922
    """Format for repositories accessed over a _SmartClient.
1752.2.31 by Martin Pool
[broken] some support for write operations over hpss
923
1752.2.50 by Andrew Bennetts
Implement RemoteBzrDir.create_{branch,workingtree}
924
    Instances of this repository are represented by RemoteRepository
1752.2.31 by Martin Pool
[broken] some support for write operations over hpss
925
    instances.
2018.5.118 by Robert Collins
Fix RemoteRepositoryFormat to have appropriate rich_root_data and support_tree_reference.
926
3128.1.3 by Vincent Ladeuil
Since we are there s/parameteris.*/parameteriz&/.
927
    The RemoteRepositoryFormat is parameterized during construction
2018.5.118 by Robert Collins
Fix RemoteRepositoryFormat to have appropriate rich_root_data and support_tree_reference.
928
    to reflect the capabilities of the real, remote format. Specifically
2018.5.138 by Robert Collins
Merge bzr.dev.
929
    the attributes rich_root_data and supports_tree_reference are set
2018.5.118 by Robert Collins
Fix RemoteRepositoryFormat to have appropriate rich_root_data and support_tree_reference.
930
    on a per instance basis, and are not set (and should not be) at
931
    the class level.
3990.5.3 by Robert Collins
Docs and polish on RepositoryFormat.network_name.
932
4032.1.1 by John Arbash Meinel
Merge the removal of all trailing whitespace, and resolve conflicts.
933
    :ivar _custom_format: If set, a specific concrete repository format that
3990.5.3 by Robert Collins
Docs and polish on RepositoryFormat.network_name.
934
        will be used when initializing a repository with this
935
        RemoteRepositoryFormat.
936
    :ivar _creating_repo: If set, the repository object that this
937
        RemoteRepositoryFormat was created for: it can be called into
3990.5.4 by Robert Collins
Review feedback.
938
        to obtain data like the network name.
1752.2.31 by Martin Pool
[broken] some support for write operations over hpss
939
    """
940
3543.1.2 by Michael Hudson
the two character fix
941
    _matchingbzrdir = RemoteBzrDirFormat()
5684.2.1 by Jelmer Vernooij
Add bzrlib.tests.per_repository_vf.
942
    supports_full_versioned_files = True
5684.2.6 by Jelmer Vernooij
Implement .supports_funky_characters and .supports_leaving_lock.
943
    supports_leaving_lock = True
1752.2.31 by Martin Pool
[broken] some support for write operations over hpss
944
4005.2.1 by Robert Collins
Fix RemoteBranch to be used correctly in tests using bzr+ssh, to fire off Branch hooks correctly, and improve the branch_implementations tests to check that making a branch gets the right format under test.
945
    def __init__(self):
5712.3.17 by Jelmer Vernooij
more fixes.
946
        _mod_repository.RepositoryFormat.__init__(self)
4005.2.1 by Robert Collins
Fix RemoteBranch to be used correctly in tests using bzr+ssh, to fire off Branch hooks correctly, and improve the branch_implementations tests to check that making a branch gets the right format under test.
947
        self._custom_format = None
4017.3.2 by Robert Collins
Reduce the number of round trips required to create a repository over the network.
948
        self._network_name = None
4017.3.3 by Robert Collins
Review feedback - make RemoteRepository.initialize use helpers, and version-lock the new method to not attempt the method on older servers.
949
        self._creating_bzrdir = None
5766.1.1 by Jelmer Vernooij
Make revision-graph-can-have-wrong-parents a repository format attribute rather than a repository method.
950
        self._revision_graph_can_have_wrong_parents = None
4476.3.15 by Andrew Bennetts
Partially working fallback for pre-1.17 servers.
951
        self._supports_chks = None
4118.1.1 by Andrew Bennetts
Fix performance regression (many small round-trips) when pushing to a remote pack, and tidy the tests.
952
        self._supports_external_lookups = None
953
        self._supports_tree_reference = None
5684.2.6 by Jelmer Vernooij
Implement .supports_funky_characters and .supports_leaving_lock.
954
        self._supports_funky_characters = None
6145.2.2 by Jelmer Vernooij
Set supports_nesting_repositories.
955
        self._supports_nesting_repositories = None
4118.1.1 by Andrew Bennetts
Fix performance regression (many small round-trips) when pushing to a remote pack, and tidy the tests.
956
        self._rich_root_data = None
957
4608.1.2 by Martin Pool
Add RemoteRepositoryFormat repr
958
    def __repr__(self):
959
        return "%s(_network_name=%r)" % (self.__class__.__name__,
960
            self._network_name)
961
4118.1.1 by Andrew Bennetts
Fix performance regression (many small round-trips) when pushing to a remote pack, and tidy the tests.
962
    @property
4183.5.1 by Robert Collins
Add RepositoryFormat.fast_deltas to signal fast delta creation.
963
    def fast_deltas(self):
964
        self._ensure_real()
965
        return self._custom_format.fast_deltas
966
967
    @property
4118.1.1 by Andrew Bennetts
Fix performance regression (many small round-trips) when pushing to a remote pack, and tidy the tests.
968
    def rich_root_data(self):
969
        if self._rich_root_data is None:
970
            self._ensure_real()
971
            self._rich_root_data = self._custom_format.rich_root_data
972
        return self._rich_root_data
973
974
    @property
4476.3.15 by Andrew Bennetts
Partially working fallback for pre-1.17 servers.
975
    def supports_chks(self):
976
        if self._supports_chks is None:
977
            self._ensure_real()
978
            self._supports_chks = self._custom_format.supports_chks
979
        return self._supports_chks
980
981
    @property
4118.1.1 by Andrew Bennetts
Fix performance regression (many small round-trips) when pushing to a remote pack, and tidy the tests.
982
    def supports_external_lookups(self):
983
        if self._supports_external_lookups is None:
984
            self._ensure_real()
985
            self._supports_external_lookups = \
4104.4.2 by Robert Collins
Fix test_source for 1.13 landing.
986
                self._custom_format.supports_external_lookups
4118.1.1 by Andrew Bennetts
Fix performance regression (many small round-trips) when pushing to a remote pack, and tidy the tests.
987
        return self._supports_external_lookups
988
989
    @property
5684.2.6 by Jelmer Vernooij
Implement .supports_funky_characters and .supports_leaving_lock.
990
    def supports_funky_characters(self):
991
        if self._supports_funky_characters is None:
992
            self._ensure_real()
993
            self._supports_funky_characters = \
994
                self._custom_format.supports_funky_characters
995
        return self._supports_funky_characters
996
997
    @property
6145.2.2 by Jelmer Vernooij
Set supports_nesting_repositories.
998
    def supports_nesting_repositories(self):
999
        if self._supports_nesting_repositories is None:
1000
            self._ensure_real()
1001
            self._supports_nesting_repositories = \
1002
                self._custom_format.supports_nesting_repositories
1003
        return self._supports_nesting_repositories
1004
1005
    @property
4118.1.1 by Andrew Bennetts
Fix performance regression (many small round-trips) when pushing to a remote pack, and tidy the tests.
1006
    def supports_tree_reference(self):
1007
        if self._supports_tree_reference is None:
1008
            self._ensure_real()
1009
            self._supports_tree_reference = \
1010
                self._custom_format.supports_tree_reference
1011
        return self._supports_tree_reference
4017.3.3 by Robert Collins
Review feedback - make RemoteRepository.initialize use helpers, and version-lock the new method to not attempt the method on older servers.
1012
5766.1.1 by Jelmer Vernooij
Make revision-graph-can-have-wrong-parents a repository format attribute rather than a repository method.
1013
    @property
1014
    def revision_graph_can_have_wrong_parents(self):
1015
        if self._revision_graph_can_have_wrong_parents is None:
1016
            self._ensure_real()
1017
            self._revision_graph_can_have_wrong_parents = \
1018
                self._custom_format.revision_graph_can_have_wrong_parents
1019
        return self._revision_graph_can_have_wrong_parents
1020
4017.3.3 by Robert Collins
Review feedback - make RemoteRepository.initialize use helpers, and version-lock the new method to not attempt the method on older servers.
1021
    def _vfs_initialize(self, a_bzrdir, shared):
1022
        """Helper for common code in initialize."""
1023
        if self._custom_format:
1024
            # Custom format requested
1025
            result = self._custom_format.initialize(a_bzrdir, shared=shared)
1026
        elif self._creating_bzrdir is not None:
1027
            # Use the format that the repository we were created to back
1028
            # has.
1029
            prior_repo = self._creating_bzrdir.open_repository()
1030
            prior_repo._ensure_real()
1031
            result = prior_repo._real_repository._format.initialize(
1032
                a_bzrdir, shared=shared)
1033
        else:
1034
            # assume that a_bzr is a RemoteBzrDir but the smart server didn't
1035
            # support remote initialization.
1036
            # We delegate to a real object at this point (as RemoteBzrDir
1037
            # delegate to the repository format which would lead to infinite
1038
            # recursion if we just called a_bzrdir.create_repository.
1039
            a_bzrdir._ensure_real()
1040
            result = a_bzrdir._real_bzrdir.create_repository(shared=shared)
1041
        if not isinstance(result, RemoteRepository):
1042
            return self.open(a_bzrdir)
1043
        else:
1044
            return result
4005.2.1 by Robert Collins
Fix RemoteBranch to be used correctly in tests using bzr+ssh, to fire off Branch hooks correctly, and improve the branch_implementations tests to check that making a branch gets the right format under test.
1045
1752.2.52 by Andrew Bennetts
Flesh out more Remote* methods needed to open and initialise remote branches/trees/repositories.
1046
    def initialize(self, a_bzrdir, shared=False):
4017.3.2 by Robert Collins
Reduce the number of round trips required to create a repository over the network.
1047
        # Being asked to create on a non RemoteBzrDir:
1048
        if not isinstance(a_bzrdir, RemoteBzrDir):
4017.3.3 by Robert Collins
Review feedback - make RemoteRepository.initialize use helpers, and version-lock the new method to not attempt the method on older servers.
1049
            return self._vfs_initialize(a_bzrdir, shared)
1050
        medium = a_bzrdir._client._medium
1051
        if medium._is_remote_before((1, 13)):
1052
            return self._vfs_initialize(a_bzrdir, shared)
4017.3.2 by Robert Collins
Reduce the number of round trips required to create a repository over the network.
1053
        # Creating on a remote bzr dir.
1054
        # 1) get the network name to use.
4005.2.1 by Robert Collins
Fix RemoteBranch to be used correctly in tests using bzr+ssh, to fire off Branch hooks correctly, and improve the branch_implementations tests to check that making a branch gets the right format under test.
1055
        if self._custom_format:
4017.3.2 by Robert Collins
Reduce the number of round trips required to create a repository over the network.
1056
            network_name = self._custom_format.network_name()
4294.2.5 by Robert Collins
Reasonable unit test coverage for initialize_on_transport_ex.
1057
        elif self._network_name:
1058
            network_name = self._network_name
4017.3.2 by Robert Collins
Reduce the number of round trips required to create a repository over the network.
1059
        else:
6622.1.34 by Jelmer Vernooij
Rename brzlib => breezy.
1060
            # Select the current breezy default and ask for that.
6472.2.1 by Jelmer Vernooij
Use bzrdir.controldir for generic access to control directories.
1061
            reference_bzrdir_format = controldir.format_registry.get('default')()
4017.3.2 by Robert Collins
Reduce the number of round trips required to create a repository over the network.
1062
            reference_format = reference_bzrdir_format.repository_format
1063
            network_name = reference_format.network_name()
1064
        # 2) try direct creation via RPC
1065
        path = a_bzrdir._path_for_remote_call(a_bzrdir._client)
1066
        verb = 'BzrDir.create_repository'
1067
        if shared:
1068
            shared_str = 'True'
1069
        else:
1070
            shared_str = 'False'
1071
        try:
1072
            response = a_bzrdir._call(verb, path, network_name, shared_str)
1073
        except errors.UnknownSmartMethod:
4017.3.3 by Robert Collins
Review feedback - make RemoteRepository.initialize use helpers, and version-lock the new method to not attempt the method on older servers.
1074
            # Fallback - use vfs methods
4094.1.1 by Andrew Bennetts
Add some medium._remember_is_before((1, 13)) calls.
1075
            medium._remember_remote_is_before((1, 13))
4017.3.3 by Robert Collins
Review feedback - make RemoteRepository.initialize use helpers, and version-lock the new method to not attempt the method on older servers.
1076
            return self._vfs_initialize(a_bzrdir, shared)
4017.3.2 by Robert Collins
Reduce the number of round trips required to create a repository over the network.
1077
        else:
1078
            # Turn the response into a RemoteRepository object.
4032.3.2 by Robert Collins
Create and use a RPC call to create branches on bzr servers rather than using VFS calls.
1079
            format = response_tuple_to_repo_format(response[1:])
4017.3.2 by Robert Collins
Reduce the number of round trips required to create a repository over the network.
1080
            # Used to support creating a real format instance when needed.
1081
            format._creating_bzrdir = a_bzrdir
1082
            remote_repo = RemoteRepository(a_bzrdir, format)
1083
            format._creating_repo = remote_repo
1084
            return remote_repo
3943.8.1 by Marius Kruger
remove all trailing whitespace from bzr source
1085
1752.2.52 by Andrew Bennetts
Flesh out more Remote* methods needed to open and initialise remote branches/trees/repositories.
1086
    def open(self, a_bzrdir):
3376.2.4 by Martin Pool
Remove every assert statement from bzrlib!
1087
        if not isinstance(a_bzrdir, RemoteBzrDir):
1088
            raise AssertionError('%r is not a RemoteBzrDir' % (a_bzrdir,))
1752.2.72 by Andrew Bennetts
Make Remote* classes in remote.py more consistent and remove some dead code.
1089
        return a_bzrdir.open_repository()
1752.2.52 by Andrew Bennetts
Flesh out more Remote* methods needed to open and initialise remote branches/trees/repositories.
1090
4053.1.4 by Robert Collins
Move the fetch control attributes from Repository to RepositoryFormat.
1091
    def _ensure_real(self):
1092
        if self._custom_format is None:
6305.4.1 by Jelmer Vernooij
Print sensible error message when remote format is unknown.
1093
            try:
1094
                self._custom_format = _mod_repository.network_format_registry.get(
1095
                    self._network_name)
1096
            except KeyError:
1097
                raise errors.UnknownFormatError(kind='repository',
1098
                    format=self._network_name)
4053.1.4 by Robert Collins
Move the fetch control attributes from Repository to RepositoryFormat.
1099
1100
    @property
1101
    def _fetch_order(self):
1102
        self._ensure_real()
1103
        return self._custom_format._fetch_order
1104
1105
    @property
1106
    def _fetch_uses_deltas(self):
1107
        self._ensure_real()
1108
        return self._custom_format._fetch_uses_deltas
1109
1110
    @property
1111
    def _fetch_reconcile(self):
1112
        self._ensure_real()
1113
        return self._custom_format._fetch_reconcile
1114
1752.2.52 by Andrew Bennetts
Flesh out more Remote* methods needed to open and initialise remote branches/trees/repositories.
1115
    def get_format_description(self):
4792.1.1 by Andrew Bennetts
Show real branch/repo format description in 'info -v' over HPSS.
1116
        self._ensure_real()
1117
        return 'Remote: ' + self._custom_format.get_format_description()
1752.2.52 by Andrew Bennetts
Flesh out more Remote* methods needed to open and initialise remote branches/trees/repositories.
1118
1119
    def __eq__(self, other):
4088.3.1 by Benjamin Peterson
compare types with 'is' not ==
1120
        return self.__class__ is other.__class__
1752.2.87 by Andrew Bennetts
Make tests pass.
1121
3990.5.1 by Andrew Bennetts
Add network_name() to RepositoryFormat.
1122
    def network_name(self):
4017.3.2 by Robert Collins
Reduce the number of round trips required to create a repository over the network.
1123
        if self._network_name:
1124
            return self._network_name
3990.5.1 by Andrew Bennetts
Add network_name() to RepositoryFormat.
1125
        self._creating_repo._ensure_real()
1126
        return self._creating_repo._real_repository._format.network_name()
1127
4022.1.1 by Robert Collins
Refactoring of fetch to have a sender and sink component enabling splitting the logic over a network stream. (Robert Collins, Andrew Bennetts)
1128
    @property
4431.3.7 by Jonathan Lange
Cherrypick bzr.dev 4470, resolving conflicts.
1129
    def pack_compresses(self):
1130
        self._ensure_real()
1131
        return self._custom_format.pack_compresses
1132
1133
    @property
4022.1.1 by Robert Collins
Refactoring of fetch to have a sender and sink component enabling splitting the logic over a network stream. (Robert Collins, Andrew Bennetts)
1134
    def _serializer(self):
4053.1.4 by Robert Collins
Move the fetch control attributes from Repository to RepositoryFormat.
1135
        self._ensure_real()
1136
        return self._custom_format._serializer
4022.1.1 by Robert Collins
Refactoring of fetch to have a sender and sink component enabling splitting the logic over a network stream. (Robert Collins, Andrew Bennetts)
1137
1752.2.31 by Martin Pool
[broken] some support for write operations over hpss
1138
6289.1.1 by Jelmer Vernooij
Make Repository a base class of RemoteRepository
1139
class RemoteRepository(_mod_repository.Repository, _RpcHelper,
1140
        lock._RelockDebugMixin):
1752.2.31 by Martin Pool
[broken] some support for write operations over hpss
1141
    """Repository accessed over rpc.
1142
2018.5.163 by Andrew Bennetts
Deal with various review comments from Robert.
1143
    For the moment most operations are performed using local transport-backed
1144
    Repository objects.
1752.2.31 by Martin Pool
[broken] some support for write operations over hpss
1145
    """
1146
2018.5.118 by Robert Collins
Fix RemoteRepositoryFormat to have appropriate rich_root_data and support_tree_reference.
1147
    def __init__(self, remote_bzrdir, format, real_repository=None, _client=None):
2018.5.34 by Robert Collins
Get test_remote.BasicRemoteObjectTests.test_open_remote_branch passing by implementing a remote method BzrDir.find_repository.
1148
        """Create a RemoteRepository instance.
3943.8.1 by Marius Kruger
remove all trailing whitespace from bzr source
1149
2018.5.34 by Robert Collins
Get test_remote.BasicRemoteObjectTests.test_open_remote_branch passing by implementing a remote method BzrDir.find_repository.
1150
        :param remote_bzrdir: The bzrdir hosting this repository.
2018.5.118 by Robert Collins
Fix RemoteRepositoryFormat to have appropriate rich_root_data and support_tree_reference.
1151
        :param format: The RemoteFormat object to use.
2018.5.34 by Robert Collins
Get test_remote.BasicRemoteObjectTests.test_open_remote_branch passing by implementing a remote method BzrDir.find_repository.
1152
        :param real_repository: If not None, a local implementation of the
1153
            repository logic for the repository, usually accessing the data
1154
            via the VFS.
2018.5.57 by Robert Collins
Implement RemoteRepository.is_shared (Robert Collins, Vincent Ladeuil).
1155
        :param _client: Private testing parameter - override the smart client
1156
            to be used by the repository.
2018.5.34 by Robert Collins
Get test_remote.BasicRemoteObjectTests.test_open_remote_branch passing by implementing a remote method BzrDir.find_repository.
1157
        """
1158
        if real_repository:
2018.5.36 by Andrew Bennetts
Fix typo, and clean up some ununsed import warnings from pyflakes at the same time.
1159
            self._real_repository = real_repository
2018.5.70 by Robert Collins
Only try to get real repositories when an operation requires them.
1160
        else:
1161
            self._real_repository = None
1752.2.50 by Andrew Bennetts
Implement RemoteBzrDir.create_{branch,workingtree}
1162
        self.bzrdir = remote_bzrdir
2018.5.57 by Robert Collins
Implement RemoteRepository.is_shared (Robert Collins, Vincent Ladeuil).
1163
        if _client is None:
3313.2.1 by Andrew Bennetts
Change _SmartClient's API to accept a medium and a base, rather than a _SharedConnection.
1164
            self._client = remote_bzrdir._client
2018.5.57 by Robert Collins
Implement RemoteRepository.is_shared (Robert Collins, Vincent Ladeuil).
1165
        else:
1166
            self._client = _client
2018.5.118 by Robert Collins
Fix RemoteRepositoryFormat to have appropriate rich_root_data and support_tree_reference.
1167
        self._format = format
2018.5.75 by Andrew Bennetts
Add Repository.{dont_,}leave_lock_in_place.
1168
        self._lock_mode = None
1169
        self._lock_token = None
6280.7.2 by Jelmer Vernooij
Add HPSS calls ``Repository.start_write_group``, ``Repository.abort_write_group`` and ``Repository.commit_write_group``.
1170
        self._write_group_tokens = None
2018.5.75 by Andrew Bennetts
Add Repository.{dont_,}leave_lock_in_place.
1171
        self._lock_count = 0
2018.5.78 by Andrew Bennetts
Implement RemoteRepository.lock_write/unlock to expect and send tokens over the
1172
        self._leave_lock = False
4307.2.4 by Robert Collins
Enable caching of negative revision lookups in RemoteRepository write locks when no _real_repository has been constructed.
1173
        # Cache of revision parents; misses are cached during read locks, and
1174
        # write locks when no _real_repository has been set.
3835.1.12 by Aaron Bentley
Unify CachingExtraParentsProvider and CachingParentsProvider.
1175
        self._unstacked_provider = graph.CachingParentsProvider(
3896.1.1 by Andrew Bennetts
Remove broken debugging cruft, and some unused imports.
1176
            get_parent_map=self._get_parent_map_rpc)
3835.1.12 by Aaron Bentley
Unify CachingExtraParentsProvider and CachingParentsProvider.
1177
        self._unstacked_provider.disable_cache()
2951.1.10 by Robert Collins
Peer review feedback with Ian.
1178
        # For tests:
1179
        # These depend on the actual remote format, so force them off for
1180
        # maximum compatibility. XXX: In future these should depend on the
1181
        # remote repository instance, but this is irrelevant until we perform
1182
        # reconcile via an RPC call.
2951.1.5 by Robert Collins
Some work towards including the correct changes for TREE_ROOT in check parameterised tests.
1183
        self._reconcile_does_inventory_gc = False
1184
        self._reconcile_fixes_text_parents = False
2951.1.3 by Robert Collins
Partial support for native reconcile with packs.
1185
        self._reconcile_backsup_inventory = False
2592.4.5 by Martin Pool
Add Repository.base on all repositories.
1186
        self.base = self.bzrdir.transport.base
3221.12.1 by Robert Collins
Backport development1 format (stackable packs) to before-shallow-branches.
1187
        # Additional places to query for data.
1188
        self._fallback_repositories = []
2592.4.5 by Martin Pool
Add Repository.base on all repositories.
1189
5158.6.4 by Martin Pool
Repository implements ControlComponent too
1190
    @property
1191
    def user_transport(self):
1192
        return self.bzrdir.user_transport
1193
1194
    @property
1195
    def control_transport(self):
1196
        # XXX: Normally you shouldn't directly get at the remote repository
1197
        # transport, but I'm not sure it's worth making this method
1198
        # optional -- mbp 2010-04-21
1199
        return self.bzrdir.get_repository_transport(None)
5712.3.13 by Jelmer Vernooij
Add Prober.known_formats().
1200
2592.4.5 by Martin Pool
Add Repository.base on all repositories.
1201
    def __str__(self):
1202
        return "%s(%s)" % (self.__class__.__name__, self.base)
1203
1204
    __repr__ = __str__
1752.2.52 by Andrew Bennetts
Flesh out more Remote* methods needed to open and initialise remote branches/trees/repositories.
1205
3825.4.1 by Andrew Bennetts
Add suppress_errors to abort_write_group.
1206
    def abort_write_group(self, suppress_errors=False):
2617.6.7 by Robert Collins
More review feedback.
1207
        """Complete a write group on the decorated repository.
3943.8.1 by Marius Kruger
remove all trailing whitespace from bzr source
1208
4031.3.3 by Matt Nordhoff
Review tweaks from Ben Finney
1209
        Smart methods perform operations in a single step so this API
2617.6.6 by Robert Collins
Some review feedback.
1210
        is not really applicable except as a compatibility thunk
2617.6.2 by Robert Collins
Add abort_write_group and wire write_groups into fetch and commit.
1211
        for older plugins that don't use e.g. the CommitBuilder
1212
        facility.
3825.4.6 by Andrew Bennetts
Document the suppress_errors flag in the docstring.
1213
1214
        :param suppress_errors: see Repository.abort_write_group.
2617.6.2 by Robert Collins
Add abort_write_group and wire write_groups into fetch and commit.
1215
        """
6280.7.5 by Jelmer Vernooij
Bunch of test fixes.
1216
        if self._real_repository:
6280.7.1 by Jelmer Vernooij
Implement RemoteRepository side of write group HPSS methods.
1217
            self._ensure_real()
1218
            return self._real_repository.abort_write_group(
1219
                suppress_errors=suppress_errors)
6280.7.6 by Jelmer Vernooij
Fix remaining tests.
1220
        if not self.is_in_write_group():
1221
            if suppress_errors:
1222
                mutter('(suppressed) not in write group')
1223
                return
1224
            raise errors.BzrError("not in write group")
6280.7.5 by Jelmer Vernooij
Bunch of test fixes.
1225
        path = self.bzrdir._path_for_remote_call(self._client)
1226
        try:
1227
            response = self._call('Repository.abort_write_group', path,
1228
                self._lock_token, self._write_group_tokens)
6619.3.2 by Jelmer Vernooij
Apply 2to3 except fix.
1229
        except Exception as exc:
6280.7.5 by Jelmer Vernooij
Bunch of test fixes.
1230
            self._write_group = None
1231
            if not suppress_errors:
1232
                raise
1233
            mutter('abort_write_group failed')
1234
            log_exception_quietly()
1235
            note(gettext('bzr: ERROR (ignored): %s'), exc)
1236
        else:
1237
            if response != ('ok', ):
1238
                raise errors.UnexpectedSmartServerResponse(response)
1239
            self._write_group_tokens = None
2617.6.2 by Robert Collins
Add abort_write_group and wire write_groups into fetch and commit.
1240
4253.1.1 by Robert Collins
Add chk_bytes property to RemoteRepository
1241
    @property
1242
    def chk_bytes(self):
1243
        """Decorate the real repository for now.
1244
1245
        In the long term a full blown network facility is needed to avoid
1246
        creating a real repository object locally.
1247
        """
1248
        self._ensure_real()
1249
        return self._real_repository.chk_bytes
1250
2617.6.2 by Robert Collins
Add abort_write_group and wire write_groups into fetch and commit.
1251
    def commit_write_group(self):
2617.6.7 by Robert Collins
More review feedback.
1252
        """Complete a write group on the decorated repository.
3943.8.1 by Marius Kruger
remove all trailing whitespace from bzr source
1253
4031.3.3 by Matt Nordhoff
Review tweaks from Ben Finney
1254
        Smart methods perform operations in a single step so this API
2617.6.6 by Robert Collins
Some review feedback.
1255
        is not really applicable except as a compatibility thunk
2617.6.2 by Robert Collins
Add abort_write_group and wire write_groups into fetch and commit.
1256
        for older plugins that don't use e.g. the CommitBuilder
1257
        facility.
1258
        """
6280.7.5 by Jelmer Vernooij
Bunch of test fixes.
1259
        if self._real_repository:
6280.7.1 by Jelmer Vernooij
Implement RemoteRepository side of write group HPSS methods.
1260
            self._ensure_real()
1261
            return self._real_repository.commit_write_group()
6280.7.6 by Jelmer Vernooij
Fix remaining tests.
1262
        if not self.is_in_write_group():
1263
            raise errors.BzrError("not in write group")
6280.7.5 by Jelmer Vernooij
Bunch of test fixes.
1264
        path = self.bzrdir._path_for_remote_call(self._client)
1265
        response = self._call('Repository.commit_write_group', path,
1266
            self._lock_token, self._write_group_tokens)
6280.7.1 by Jelmer Vernooij
Implement RemoteRepository side of write group HPSS methods.
1267
        if response != ('ok', ):
1268
            raise errors.UnexpectedSmartServerResponse(response)
6280.7.4 by Jelmer Vernooij
pass write group tokens as list/tuple.
1269
        self._write_group_tokens = None
6362.5.3 by Jelmer Vernooij
Add comments.
1270
        # Refresh data after writing to the repository.
6362.5.2 by Jelmer Vernooij
Fix tests.
1271
        self.refresh_data()
2617.6.1 by Robert Collins
* New method on Repository - ``start_write_group``, ``end_write_group``
1272
4002.1.1 by Andrew Bennetts
Implement suspend_write_group/resume_write_group.
1273
    def resume_write_group(self, tokens):
6280.7.2 by Jelmer Vernooij
Add HPSS calls ``Repository.start_write_group``, ``Repository.abort_write_group`` and ``Repository.commit_write_group``.
1274
        if self._real_repository:
6280.7.1 by Jelmer Vernooij
Implement RemoteRepository side of write group HPSS methods.
1275
            return self._real_repository.resume_write_group(tokens)
6280.7.6 by Jelmer Vernooij
Fix remaining tests.
1276
        path = self.bzrdir._path_for_remote_call(self._client)
1277
        try:
1278
            response = self._call('Repository.check_write_group', path,
1279
               self._lock_token, tokens)
1280
        except errors.UnknownSmartMethod:
1281
            self._ensure_real()
1282
            return self._real_repository.resume_write_group(tokens)
1283
        if response != ('ok', ):
1284
            raise errors.UnexpectedSmartServerResponse(response)
6280.7.5 by Jelmer Vernooij
Bunch of test fixes.
1285
        self._write_group_tokens = tokens
4002.1.1 by Andrew Bennetts
Implement suspend_write_group/resume_write_group.
1286
1287
    def suspend_write_group(self):
6280.7.2 by Jelmer Vernooij
Add HPSS calls ``Repository.start_write_group``, ``Repository.abort_write_group`` and ``Repository.commit_write_group``.
1288
        if self._real_repository:
6280.7.1 by Jelmer Vernooij
Implement RemoteRepository side of write group HPSS methods.
1289
            return self._real_repository.suspend_write_group()
6280.7.6 by Jelmer Vernooij
Fix remaining tests.
1290
        ret = self._write_group_tokens or []
6280.7.5 by Jelmer Vernooij
Bunch of test fixes.
1291
        self._write_group_tokens = None
1292
        return ret
4002.1.1 by Andrew Bennetts
Implement suspend_write_group/resume_write_group.
1293
4343.3.29 by John Arbash Meinel
Add 'check_for_missing_texts' flag to get_missing_parent_inv..
1294
    def get_missing_parent_inventories(self, check_for_missing_texts=True):
4257.4.6 by Andrew Bennetts
Make get_missing_parent_inventories work for all repo formats (it's a no-op for unstackable formats).
1295
        self._ensure_real()
4343.3.29 by John Arbash Meinel
Add 'check_for_missing_texts' flag to get_missing_parent_inv..
1296
        return self._real_repository.get_missing_parent_inventories(
1297
            check_for_missing_texts=check_for_missing_texts)
4257.4.6 by Andrew Bennetts
Make get_missing_parent_inventories work for all repo formats (it's a no-op for unstackable formats).
1298
4419.2.9 by Andrew Bennetts
Add per_repository_reference test for get_rev_id_for_revno, fix the bugs it revealed.
1299
    def _get_rev_id_for_revno_vfs(self, revno, known_pair):
1300
        self._ensure_real()
1301
        return self._real_repository.get_rev_id_for_revno(
1302
            revno, known_pair)
1303
4419.2.5 by Andrew Bennetts
Add Repository.get_rev_id_for_revno, and use it both as the _ensure_real fallback and as the server-side implementation.
1304
    def get_rev_id_for_revno(self, revno, known_pair):
1305
        """See Repository.get_rev_id_for_revno."""
1306
        path = self.bzrdir._path_for_remote_call(self._client)
1307
        try:
4476.3.33 by Andrew Bennetts
Revert some accidental s/17/18/ in remote.py.
1308
            if self._client._medium._is_remote_before((1, 17)):
4419.2.9 by Andrew Bennetts
Add per_repository_reference test for get_rev_id_for_revno, fix the bugs it revealed.
1309
                return self._get_rev_id_for_revno_vfs(revno, known_pair)
4419.2.5 by Andrew Bennetts
Add Repository.get_rev_id_for_revno, and use it both as the _ensure_real fallback and as the server-side implementation.
1310
            response = self._call(
1311
                'Repository.get_rev_id_for_revno', path, revno, known_pair)
1312
        except errors.UnknownSmartMethod:
4476.3.33 by Andrew Bennetts
Revert some accidental s/17/18/ in remote.py.
1313
            self._client._medium._remember_remote_is_before((1, 17))
4419.2.9 by Andrew Bennetts
Add per_repository_reference test for get_rev_id_for_revno, fix the bugs it revealed.
1314
            return self._get_rev_id_for_revno_vfs(revno, known_pair)
4419.2.5 by Andrew Bennetts
Add Repository.get_rev_id_for_revno, and use it both as the _ensure_real fallback and as the server-side implementation.
1315
        if response[0] == 'ok':
1316
            return True, response[1]
1317
        elif response[0] == 'history-incomplete':
4419.2.8 by Andrew Bennetts
Add unit test for RemoteRepository.get_rev_id_for_revno using fallbacks if it gets a history-incomplete response.
1318
            known_pair = response[1:3]
1319
            for fallback in self._fallback_repositories:
1320
                found, result = fallback.get_rev_id_for_revno(revno, known_pair)
1321
                if found:
1322
                    return True, result
1323
                else:
1324
                    known_pair = result
1325
            # Not found in any fallbacks
1326
            return False, known_pair
4419.2.5 by Andrew Bennetts
Add Repository.get_rev_id_for_revno, and use it both as the _ensure_real fallback and as the server-side implementation.
1327
        else:
1328
            raise errors.UnexpectedSmartServerResponse(response)
1329
2018.5.70 by Robert Collins
Only try to get real repositories when an operation requires them.
1330
    def _ensure_real(self):
1331
        """Ensure that there is a _real_repository set.
1332
2018.5.163 by Andrew Bennetts
Deal with various review comments from Robert.
1333
        Used before calls to self._real_repository.
4145.1.1 by Robert Collins
Explicitly prevent fetching while the target repository is in a write group.
1334
1335
        Note that _ensure_real causes many roundtrips to the server which are
1336
        not desirable, and prevents the use of smart one-roundtrip RPC's to
1337
        perform complex operations (such as accessing parent data, streaming
1338
        revisions etc). Adding calls to _ensure_real should only be done when
1339
        bringing up new functionality, adding fallbacks for smart methods that
1340
        require a fallback path, and never to replace an existing smart method
1341
        invocation. If in doubt chat to the bzr network team.
2018.5.70 by Robert Collins
Only try to get real repositories when an operation requires them.
1342
        """
3692.1.3 by Andrew Bennetts
Delete some cruft (like the _ensure_real call in RemoteBranch.lock_write), improve some comments, and wrap some long lines.
1343
        if self._real_repository is None:
4509.2.2 by Martin Pool
Use only -Dhpssvfs for tracebacks, and document -Dhpssdetail
1344
            if 'hpssvfs' in debug.debug_flags:
4347.1.1 by Robert Collins
Show a traceback when VFS operations are started on a smart server hosted repository.
1345
                import traceback
1346
                warning('VFS Repository access triggered\n%s',
1347
                    ''.join(traceback.format_stack()))
4307.2.4 by Robert Collins
Enable caching of negative revision lookups in RemoteRepository write locks when no _real_repository has been constructed.
1348
            self._unstacked_provider.missing_keys.clear()
2018.5.70 by Robert Collins
Only try to get real repositories when an operation requires them.
1349
            self.bzrdir._ensure_real()
3692.1.3 by Andrew Bennetts
Delete some cruft (like the _ensure_real call in RemoteBranch.lock_write), improve some comments, and wrap some long lines.
1350
            self._set_real_repository(
1351
                self.bzrdir._real_bzrdir.open_repository())
2018.5.70 by Robert Collins
Only try to get real repositories when an operation requires them.
1352
3533.3.1 by Andrew Bennetts
Remove duplication of error translation in bzrlib/remote.py.
1353
    def _translate_error(self, err, **context):
1354
        self.bzrdir._translate_error(err, repository=self, **context)
1355
2988.1.2 by Robert Collins
New Repository API find_text_key_references for use by reconcile and check.
1356
    def find_text_key_references(self):
1357
        """Find the text key references within the repository.
1358
1359
        :return: A dictionary mapping text keys ((fileid, revision_id) tuples)
1360
            to whether they were referred to by the inventory of the
1361
            revision_id that they contain. The inventory texts from all present
1362
            revision ids are assessed to generate this report.
1363
        """
1364
        self._ensure_real()
1365
        return self._real_repository.find_text_key_references()
1366
2988.1.3 by Robert Collins
Add a new repositoy method _generate_text_key_index for use by reconcile/check.
1367
    def _generate_text_key_index(self):
1368
        """Generate a new text key index for the repository.
1369
1370
        This is an expensive function that will take considerable time to run.
1371
1372
        :return: A dict mapping (file_id, revision_id) tuples to a list of
1373
            parents, also (file_id, revision_id) tuples.
1374
        """
1375
        self._ensure_real()
1376
        return self._real_repository._generate_text_key_index()
1377
3287.6.4 by Robert Collins
Fix up deprecation warnings for get_revision_graph.
1378
    def _get_revision_graph(self, revision_id):
1379
        """Private method for using with old (< 1.2) servers to fallback."""
2018.5.67 by Wouter van Heyst
Implement RemoteRepository.get_revision_graph (Wouter van Heyst, Robert Collins)
1380
        if revision_id is None:
1381
            revision_id = ''
5712.3.13 by Jelmer Vernooij
Add Prober.known_formats().
1382
        elif _mod_revision.is_null(revision_id):
2018.5.67 by Wouter van Heyst
Implement RemoteRepository.get_revision_graph (Wouter van Heyst, Robert Collins)
1383
            return {}
1384
1385
        path = self.bzrdir._path_for_remote_call(self._client)
3786.2.3 by Andrew Bennetts
Remove duplicated 'call & translate errors' code in bzrlib.remote.
1386
        response = self._call_expecting_body(
1387
            'Repository.get_revision_graph', path, revision_id)
3245.4.58 by Andrew Bennetts
Unpack call_expecting_body's return value into variables, to avoid lots of ugly subscripting.
1388
        response_tuple, response_handler = response
1389
        if response_tuple[0] != 'ok':
1390
            raise errors.UnexpectedSmartServerResponse(response_tuple)
1391
        coded = response_handler.read_body_bytes()
3245.4.24 by Andrew Bennetts
Consistently raise errors from the server as ErrorFromSmartServer exceptions.
1392
        if coded == '':
1393
            # no revisions in this repository!
1394
            return {}
1395
        lines = coded.split('\n')
1396
        revision_graph = {}
1397
        for line in lines:
1398
            d = tuple(line.split())
1399
            revision_graph[d[0]] = d[1:]
3943.8.1 by Marius Kruger
remove all trailing whitespace from bzr source
1400
3245.4.24 by Andrew Bennetts
Consistently raise errors from the server as ErrorFromSmartServer exceptions.
1401
        return revision_graph
2018.5.67 by Wouter van Heyst
Implement RemoteRepository.get_revision_graph (Wouter van Heyst, Robert Collins)
1402
4022.1.1 by Robert Collins
Refactoring of fetch to have a sender and sink component enabling splitting the logic over a network stream. (Robert Collins, Andrew Bennetts)
1403
    def _get_sink(self):
1404
        """See Repository._get_sink()."""
4022.1.6 by Robert Collins
Cherrypick and polish the RemoteSink for streaming push.
1405
        return RemoteStreamSink(self)
4022.1.1 by Robert Collins
Refactoring of fetch to have a sender and sink component enabling splitting the logic over a network stream. (Robert Collins, Andrew Bennetts)
1406
4060.1.3 by Robert Collins
Implement the separate source component for fetch - repository.StreamSource.
1407
    def _get_source(self, to_format):
1408
        """Return a source for streaming from this repository."""
1409
        return RemoteStreamSource(self, to_format)
1410
4307.2.3 by Robert Collins
Change RemoteRepository.has_revision to use get_parent_map to leverage the caching.
1411
    @needs_read_lock
5815.5.8 by Jelmer Vernooij
Use traditional (fileid, revision) entries in file graph.
1412
    def get_file_graph(self):
1413
        return graph.Graph(self.texts)
5815.5.3 by Jelmer Vernooij
Add basic test for per file graph.
1414
1415
    @needs_read_lock
2018.5.40 by Robert Collins
Implement a remote Repository.has_revision method.
1416
    def has_revision(self, revision_id):
4307.2.3 by Robert Collins
Change RemoteRepository.has_revision to use get_parent_map to leverage the caching.
1417
        """True if this repository has a copy of the revision."""
6622.1.34 by Jelmer Vernooij
Rename brzlib => breezy.
1418
        # Copy of breezy.repository.Repository.has_revision
4307.2.3 by Robert Collins
Change RemoteRepository.has_revision to use get_parent_map to leverage the caching.
1419
        return revision_id in self.has_revisions((revision_id,))
2018.5.40 by Robert Collins
Implement a remote Repository.has_revision method.
1420
4307.2.3 by Robert Collins
Change RemoteRepository.has_revision to use get_parent_map to leverage the caching.
1421
    @needs_read_lock
3172.3.1 by Robert Collins
Repository has a new method ``has_revisions`` which signals the presence
1422
    def has_revisions(self, revision_ids):
4307.2.3 by Robert Collins
Change RemoteRepository.has_revision to use get_parent_map to leverage the caching.
1423
        """Probe to find out the presence of multiple revisions.
1424
1425
        :param revision_ids: An iterable of revision_ids.
1426
        :return: A set of the revision_ids that were present.
1427
        """
6622.1.34 by Jelmer Vernooij
Rename brzlib => breezy.
1428
        # Copy of breezy.repository.Repository.has_revisions
4307.2.3 by Robert Collins
Change RemoteRepository.has_revision to use get_parent_map to leverage the caching.
1429
        parent_map = self.get_parent_map(revision_ids)
1430
        result = set(parent_map)
1431
        if _mod_revision.NULL_REVISION in revision_ids:
1432
            result.add(_mod_revision.NULL_REVISION)
3172.3.1 by Robert Collins
Repository has a new method ``has_revisions`` which signals the presence
1433
        return result
1434
4509.3.37 by Martin Pool
Remove RepositoryBase; make _has_same_location private
1435
    def _has_same_fallbacks(self, other_repo):
1436
        """Returns true if the repositories have the same fallbacks."""
1437
        # XXX: copied from Repository; it should be unified into a base class
5243.1.2 by Martin
Point launchpad links in comments at production server rather than edge
1438
        # <https://bugs.launchpad.net/bzr/+bug/401622>
4509.3.37 by Martin Pool
Remove RepositoryBase; make _has_same_location private
1439
        my_fb = self._fallback_repositories
1440
        other_fb = other_repo._fallback_repositories
1441
        if len(my_fb) != len(other_fb):
1442
            return False
1443
        for f, g in zip(my_fb, other_fb):
1444
            if not f.has_same_location(g):
1445
                return False
1446
        return True
1447
2617.6.9 by Robert Collins
Merge bzr.dev.
1448
    def has_same_location(self, other):
4509.3.23 by Martin Pool
Comment on has_same_location variation
1449
        # TODO: Move to RepositoryBase and unify with the regular Repository
1450
        # one; unfortunately the tests rely on slightly different behaviour at
1451
        # present -- mbp 20090710
4088.3.1 by Benjamin Peterson
compare types with 'is' not ==
1452
        return (self.__class__ is other.__class__ and
2592.3.162 by Robert Collins
Remove some arbitrary differences from bzr.dev.
1453
                self.bzrdir.transport.base == other.bzrdir.transport.base)
3835.1.1 by Aaron Bentley
Stack get_parent_map on fallback repos
1454
2490.2.21 by Aaron Bentley
Rename graph to deprecated_graph
1455
    def get_graph(self, other_repository=None):
1456
        """Return the graph for this repository format"""
3835.1.17 by Aaron Bentley
Fix stacking bug
1457
        parents_provider = self._make_parents_provider(other_repository)
3441.5.24 by Andrew Bennetts
Remove RemoteGraph experiment.
1458
        return graph.Graph(parents_provider)
2490.2.5 by Aaron Bentley
Use GraphWalker.unique_ancestor to determine merge base
1459
4913.4.2 by Jelmer Vernooij
Add Repository.get_known_graph_ancestry.
1460
    @needs_read_lock
1461
    def get_known_graph_ancestry(self, revision_ids):
1462
        """Return the known graph for a set of revision ids and their ancestors.
1463
        """
1464
        st = static_tuple.StaticTuple
1465
        revision_keys = [st(r_id).intern() for r_id in revision_ids]
1466
        known_graph = self.revisions.get_known_graph_ancestry(revision_keys)
1467
        return graph.GraphThunkIdsToKeys(known_graph)
1468
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
1469
    def gather_stats(self, revid=None, committers=None):
2018.5.62 by Robert Collins
Stub out RemoteRepository.gather_stats while its implemented in parallel.
1470
        """See Repository.gather_stats()."""
2018.10.3 by v.ladeuil+lp at free
more tests for gather_stats
1471
        path = self.bzrdir._path_for_remote_call(self._client)
2948.3.4 by John Arbash Meinel
Repository.gather_stats() validly can get None for the revid.
1472
        # revid can be None to indicate no revisions, not just NULL_REVISION
5712.3.13 by Jelmer Vernooij
Add Prober.known_formats().
1473
        if revid is None or _mod_revision.is_null(revid):
2018.10.3 by v.ladeuil+lp at free
more tests for gather_stats
1474
            fmt_revid = ''
1475
        else:
2018.5.83 by Andrew Bennetts
Fix some test failures caused by the switch from unicode to UTF-8-encoded strs for revision IDs.
1476
            fmt_revid = revid
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
1477
        if committers is None or not committers:
2018.10.3 by v.ladeuil+lp at free
more tests for gather_stats
1478
            fmt_committers = 'no'
1479
        else:
1480
            fmt_committers = 'yes'
3786.2.3 by Andrew Bennetts
Remove duplicated 'call & translate errors' code in bzrlib.remote.
1481
        response_tuple, response_handler = self._call_expecting_body(
2018.5.153 by Andrew Bennetts
Rename call2 to call_expecting_body, and other small changes prompted by review.
1482
            'Repository.gather_stats', path, fmt_revid, fmt_committers)
3245.4.58 by Andrew Bennetts
Unpack call_expecting_body's return value into variables, to avoid lots of ugly subscripting.
1483
        if response_tuple[0] != 'ok':
1484
            raise errors.UnexpectedSmartServerResponse(response_tuple)
2018.10.3 by v.ladeuil+lp at free
more tests for gather_stats
1485
3245.4.58 by Andrew Bennetts
Unpack call_expecting_body's return value into variables, to avoid lots of ugly subscripting.
1486
        body = response_handler.read_body_bytes()
2018.10.3 by v.ladeuil+lp at free
more tests for gather_stats
1487
        result = {}
1488
        for line in body.split('\n'):
1489
            if not line:
1490
                continue
1491
            key, val_text = line.split(':')
1492
            if key in ('revisions', 'size', 'committers'):
1493
                result[key] = int(val_text)
1494
            elif key in ('firstrev', 'latestrev'):
1495
                values = val_text.split(' ')[1:]
6621.18.1 by Martin
Remove or fix use of long type and nearby type issues
1496
                result[key] = (float(values[0]), int(values[1]))
2018.10.3 by v.ladeuil+lp at free
more tests for gather_stats
1497
1498
        return result
2018.5.62 by Robert Collins
Stub out RemoteRepository.gather_stats while its implemented in parallel.
1499
3140.1.2 by Aaron Bentley
Add ability to find branches inside repositories
1500
    def find_branches(self, using=False):
1501
        """See Repository.find_branches()."""
1502
        # should be an API call to the server.
1503
        self._ensure_real()
1504
        return self._real_repository.find_branches(using=using)
1505
2018.5.60 by Robert Collins
More missing methods from RemoteBranch and RemoteRepository to let 'info' get further.
1506
    def get_physical_lock_status(self):
1507
        """See Repository.get_physical_lock_status()."""
6280.6.1 by Jelmer Vernooij
Implement remote side of {Branch,Repository}.get_physical_lock_status.
1508
        path = self.bzrdir._path_for_remote_call(self._client)
1509
        try:
1510
            response = self._call('Repository.get_physical_lock_status', path)
1511
        except errors.UnknownSmartMethod:
1512
            self._ensure_real()
1513
            return self._real_repository.get_physical_lock_status()
1514
        if response[0] not in ('yes', 'no'):
1515
            raise errors.UnexpectedSmartServerResponse(response)
6280.6.2 by Jelmer Vernooij
Add HPSS calls Repository.get_physical_lock_status and Branch.get_physical_lock_status.
1516
        return (response[0] == 'yes')
2018.5.60 by Robert Collins
More missing methods from RemoteBranch and RemoteRepository to let 'info' get further.
1517
2617.6.1 by Robert Collins
* New method on Repository - ``start_write_group``, ``end_write_group``
1518
    def is_in_write_group(self):
1519
        """Return True if there is an open write group.
1520
1521
        write groups are only applicable locally for the smart server..
1522
        """
6280.7.3 by Jelmer Vernooij
Fix RemoteRepository.is_in_write_group.
1523
        if self._write_group_tokens is not None:
1524
            return True
2617.6.1 by Robert Collins
* New method on Repository - ``start_write_group``, ``end_write_group``
1525
        if self._real_repository:
1526
            return self._real_repository.is_in_write_group()
1527
1528
    def is_locked(self):
1529
        return self._lock_count >= 1
1530
2018.5.57 by Robert Collins
Implement RemoteRepository.is_shared (Robert Collins, Vincent Ladeuil).
1531
    def is_shared(self):
1532
        """See Repository.is_shared()."""
1533
        path = self.bzrdir._path_for_remote_call(self._client)
3786.2.3 by Andrew Bennetts
Remove duplicated 'call & translate errors' code in bzrlib.remote.
1534
        response = self._call('Repository.is_shared', path)
3376.2.4 by Martin Pool
Remove every assert statement from bzrlib!
1535
        if response[0] not in ('yes', 'no'):
1536
            raise SmartProtocolError('unexpected response code %s' % (response,))
2018.5.57 by Robert Collins
Implement RemoteRepository.is_shared (Robert Collins, Vincent Ladeuil).
1537
        return response[0] == 'yes'
1538
2904.1.1 by Robert Collins
* New method ``bzrlib.repository.Repository.is_write_locked`` useful for
1539
    def is_write_locked(self):
1540
        return self._lock_mode == 'w'
1541
5675.2.2 by Jelmer Vernooij
Revert unnecessary bzrlib.remote changes.
1542
    def _warn_if_deprecated(self, branch=None):
1543
        # If we have a real repository, the check will be done there, if we
1544
        # don't the check will be done remotely.
1545
        pass
1546
2018.5.60 by Robert Collins
More missing methods from RemoteBranch and RemoteRepository to let 'info' get further.
1547
    def lock_read(self):
5200.3.3 by Robert Collins
Lock methods on ``Tree``, ``Branch`` and ``Repository`` are now
1548
        """Lock the repository for read operations.
1549
6622.1.34 by Jelmer Vernooij
Rename brzlib => breezy.
1550
        :return: A breezy.lock.LogicalLockResult.
5200.3.3 by Robert Collins
Lock methods on ``Tree``, ``Branch`` and ``Repository`` are now
1551
        """
2018.5.60 by Robert Collins
More missing methods from RemoteBranch and RemoteRepository to let 'info' get further.
1552
        # wrong eventually - want a local lock cache context
2018.5.75 by Andrew Bennetts
Add Repository.{dont_,}leave_lock_in_place.
1553
        if not self._lock_mode:
4731.1.2 by Andrew Bennetts
Refactor to reduce duplication.
1554
            self._note_lock('r')
2018.5.75 by Andrew Bennetts
Add Repository.{dont_,}leave_lock_in_place.
1555
            self._lock_mode = 'r'
1556
            self._lock_count = 1
4190.1.1 by Robert Collins
Negatively cache misses during read-locks in RemoteRepository.
1557
            self._unstacked_provider.enable_cache(cache_misses=True)
2018.5.78 by Andrew Bennetts
Implement RemoteRepository.lock_write/unlock to expect and send tokens over the
1558
            if self._real_repository is not None:
1559
                self._real_repository.lock_read()
4379.2.1 by John Arbash Meinel
Change the fallback repository code to only lock/unlock on transition.
1560
            for repo in self._fallback_repositories:
1561
                repo.lock_read()
2018.5.75 by Andrew Bennetts
Add Repository.{dont_,}leave_lock_in_place.
1562
        else:
1563
            self._lock_count += 1
5200.3.6 by Robert Collins
Make all lock methods return Result objects, rather than lock_read returning self, as per John's review.
1564
        return lock.LogicalLockResult(self.unlock)
2018.5.78 by Andrew Bennetts
Implement RemoteRepository.lock_write/unlock to expect and send tokens over the
1565
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
1566
    def _remote_lock_write(self, token):
2018.5.78 by Andrew Bennetts
Implement RemoteRepository.lock_write/unlock to expect and send tokens over the
1567
        path = self.bzrdir._path_for_remote_call(self._client)
1568
        if token is None:
1569
            token = ''
3786.2.3 by Andrew Bennetts
Remove duplicated 'call & translate errors' code in bzrlib.remote.
1570
        err_context = {'token': token}
1571
        response = self._call('Repository.lock_write', path, token,
1572
                              **err_context)
2018.5.78 by Andrew Bennetts
Implement RemoteRepository.lock_write/unlock to expect and send tokens over the
1573
        if response[0] == 'ok':
1574
            ok, token = response
1575
            return token
1576
        else:
2555.1.1 by Martin Pool
Remove use of 'assert False' to raise an exception unconditionally
1577
            raise errors.UnexpectedSmartServerResponse(response)
2018.5.60 by Robert Collins
More missing methods from RemoteBranch and RemoteRepository to let 'info' get further.
1578
3692.1.1 by Andrew Bennetts
Make RemoteBranch.lock_write lock the repository too.
1579
    def lock_write(self, token=None, _skip_rpc=False):
2018.5.75 by Andrew Bennetts
Add Repository.{dont_,}leave_lock_in_place.
1580
        if not self._lock_mode:
4731.1.2 by Andrew Bennetts
Refactor to reduce duplication.
1581
            self._note_lock('w')
3692.1.1 by Andrew Bennetts
Make RemoteBranch.lock_write lock the repository too.
1582
            if _skip_rpc:
1583
                if self._lock_token is not None:
1584
                    if token != self._lock_token:
3695.1.1 by Andrew Bennetts
Remove some unused imports and fix a couple of trivially broken raise statements.
1585
                        raise errors.TokenMismatch(token, self._lock_token)
3692.1.1 by Andrew Bennetts
Make RemoteBranch.lock_write lock the repository too.
1586
                self._lock_token = token
1587
            else:
1588
                self._lock_token = self._remote_lock_write(token)
3015.2.9 by Robert Collins
Handle repositories that do not allow remote locking, like pack repositories, in the client side remote server proxy objects.
1589
            # if self._lock_token is None, then this is something like packs or
1590
            # svn where we don't get to lock the repo, or a weave style repository
1591
            # where we cannot lock it over the wire and attempts to do so will
1592
            # fail.
2018.5.78 by Andrew Bennetts
Implement RemoteRepository.lock_write/unlock to expect and send tokens over the
1593
            if self._real_repository is not None:
1594
                self._real_repository.lock_write(token=self._lock_token)
1595
            if token is not None:
1596
                self._leave_lock = True
1597
            else:
1598
                self._leave_lock = False
2018.5.75 by Andrew Bennetts
Add Repository.{dont_,}leave_lock_in_place.
1599
            self._lock_mode = 'w'
1600
            self._lock_count = 1
4307.2.4 by Robert Collins
Enable caching of negative revision lookups in RemoteRepository write locks when no _real_repository has been constructed.
1601
            cache_misses = self._real_repository is None
1602
            self._unstacked_provider.enable_cache(cache_misses=cache_misses)
4379.2.1 by John Arbash Meinel
Change the fallback repository code to only lock/unlock on transition.
1603
            for repo in self._fallback_repositories:
1604
                # Writes don't affect fallback repos
1605
                repo.lock_read()
2018.5.75 by Andrew Bennetts
Add Repository.{dont_,}leave_lock_in_place.
1606
        elif self._lock_mode == 'r':
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
1607
            raise errors.ReadOnlyError(self)
2018.5.75 by Andrew Bennetts
Add Repository.{dont_,}leave_lock_in_place.
1608
        else:
1609
            self._lock_count += 1
5200.3.3 by Robert Collins
Lock methods on ``Tree``, ``Branch`` and ``Repository`` are now
1610
        return RepositoryWriteLockResult(self.unlock, self._lock_token or None)
2018.5.75 by Andrew Bennetts
Add Repository.{dont_,}leave_lock_in_place.
1611
1612
    def leave_lock_in_place(self):
3015.2.9 by Robert Collins
Handle repositories that do not allow remote locking, like pack repositories, in the client side remote server proxy objects.
1613
        if not self._lock_token:
1614
            raise NotImplementedError(self.leave_lock_in_place)
2018.5.78 by Andrew Bennetts
Implement RemoteRepository.lock_write/unlock to expect and send tokens over the
1615
        self._leave_lock = True
2018.5.75 by Andrew Bennetts
Add Repository.{dont_,}leave_lock_in_place.
1616
1617
    def dont_leave_lock_in_place(self):
3015.2.9 by Robert Collins
Handle repositories that do not allow remote locking, like pack repositories, in the client side remote server proxy objects.
1618
        if not self._lock_token:
3015.2.15 by Robert Collins
Review feedback.
1619
            raise NotImplementedError(self.dont_leave_lock_in_place)
2018.5.78 by Andrew Bennetts
Implement RemoteRepository.lock_write/unlock to expect and send tokens over the
1620
        self._leave_lock = False
2018.5.75 by Andrew Bennetts
Add Repository.{dont_,}leave_lock_in_place.
1621
1622
    def _set_real_repository(self, repository):
1623
        """Set the _real_repository for this repository.
1624
1625
        :param repository: The repository to fallback to for non-hpss
1626
            implemented operations.
1627
        """
4053.1.5 by Robert Collins
Review feedback on RemoteRepository._set_real_revision.
1628
        if self._real_repository is not None:
1629
            # Replacing an already set real repository.
1630
            # We cannot do this [currently] if the repository is locked -
1631
            # synchronised state might be lost.
1632
            if self.is_locked():
1633
                raise AssertionError('_real_repository is already set')
3376.2.4 by Martin Pool
Remove every assert statement from bzrlib!
1634
        if isinstance(repository, RemoteRepository):
1635
            raise AssertionError()
2018.5.75 by Andrew Bennetts
Add Repository.{dont_,}leave_lock_in_place.
1636
        self._real_repository = repository
4226.2.5 by Robert Collins
Fix handling of fallback repositories some more.
1637
        # three code paths happen here:
1638
        # 1) old servers, RemoteBranch.open() calls _ensure_real before setting
1639
        # up stacking. In this case self._fallback_repositories is [], and the
1640
        # real repo is already setup. Preserve the real repo and
1641
        # RemoteRepository.add_fallback_repository will avoid adding
1642
        # duplicates.
1643
        # 2) new servers, RemoteBranch.open() sets up stacking, and when
1644
        # ensure_real is triggered from a branch, the real repository to
1645
        # set already has a matching list with separate instances, but
1646
        # as they are also RemoteRepositories we don't worry about making the
1647
        # lists be identical.
1648
        # 3) new servers, RemoteRepository.ensure_real is triggered before
1649
        # RemoteBranch.ensure real, in this case we get a repo with no fallbacks
1650
        # and need to populate it.
1651
        if (self._fallback_repositories and
1652
            len(self._real_repository._fallback_repositories) !=
4226.2.2 by Robert Collins
Fix setting config options to support unicode values and don't attempt to reset repositories _fallback_repositories as the simple approach fails to work.
1653
            len(self._fallback_repositories)):
1654
            if len(self._real_repository._fallback_repositories):
1655
                raise AssertionError(
1656
                    "cannot cleanly remove existing _fallback_repositories")
3691.2.12 by Martin Pool
Add test for coping without Branch.get_stacked_on_url
1657
        for fb in self._fallback_repositories:
1658
            self._real_repository.add_fallback_repository(fb)
2018.5.75 by Andrew Bennetts
Add Repository.{dont_,}leave_lock_in_place.
1659
        if self._lock_mode == 'w':
1660
            # if we are already locked, the real repository must be able to
1661
            # acquire the lock with our token.
1662
            self._real_repository.lock_write(self._lock_token)
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
1663
        elif self._lock_mode == 'r':
1664
            self._real_repository.lock_read()
6280.7.5 by Jelmer Vernooij
Bunch of test fixes.
1665
        if self._write_group_tokens is not None:
1666
            # if we are already in a write group, resume it
1667
            self._real_repository.resume_write_group(self._write_group_tokens)
1668
            self._write_group_tokens = None
2018.5.60 by Robert Collins
More missing methods from RemoteBranch and RemoteRepository to let 'info' get further.
1669
2617.6.1 by Robert Collins
* New method on Repository - ``start_write_group``, ``end_write_group``
1670
    def start_write_group(self):
1671
        """Start a write group on the decorated repository.
3943.8.1 by Marius Kruger
remove all trailing whitespace from bzr source
1672
4031.3.3 by Matt Nordhoff
Review tweaks from Ben Finney
1673
        Smart methods perform operations in a single step so this API
2617.6.6 by Robert Collins
Some review feedback.
1674
        is not really applicable except as a compatibility thunk
2617.6.1 by Robert Collins
* New method on Repository - ``start_write_group``, ``end_write_group``
1675
        for older plugins that don't use e.g. the CommitBuilder
1676
        facility.
1677
        """
6280.7.5 by Jelmer Vernooij
Bunch of test fixes.
1678
        if self._real_repository:
1679
            self._ensure_real()
1680
            return self._real_repository.start_write_group()
1681
        if not self.is_write_locked():
1682
            raise errors.NotWriteLocked(self)
1683
        if self._write_group_tokens is not None:
1684
            raise errors.BzrError('already in a write group')
6280.7.1 by Jelmer Vernooij
Implement RemoteRepository side of write group HPSS methods.
1685
        path = self.bzrdir._path_for_remote_call(self._client)
1686
        try:
6280.7.2 by Jelmer Vernooij
Add HPSS calls ``Repository.start_write_group``, ``Repository.abort_write_group`` and ``Repository.commit_write_group``.
1687
            response = self._call('Repository.start_write_group', path,
1688
                self._lock_token)
6280.7.8 by Jelmer Vernooij
make sure start_write_group falls back to real_repository if write groups aren't suspendable.
1689
        except (errors.UnknownSmartMethod, errors.UnsuspendableWriteGroup):
6280.7.1 by Jelmer Vernooij
Implement RemoteRepository side of write group HPSS methods.
1690
            self._ensure_real()
1691
            return self._real_repository.start_write_group()
6280.7.2 by Jelmer Vernooij
Add HPSS calls ``Repository.start_write_group``, ``Repository.abort_write_group`` and ``Repository.commit_write_group``.
1692
        if response[0] != 'ok':
6280.7.1 by Jelmer Vernooij
Implement RemoteRepository side of write group HPSS methods.
1693
            raise errors.UnexpectedSmartServerResponse(response)
6280.7.6 by Jelmer Vernooij
Fix remaining tests.
1694
        self._write_group_tokens = response[1]
2617.6.1 by Robert Collins
* New method on Repository - ``start_write_group``, ``end_write_group``
1695
2018.5.78 by Andrew Bennetts
Implement RemoteRepository.lock_write/unlock to expect and send tokens over the
1696
    def _unlock(self, token):
1697
        path = self.bzrdir._path_for_remote_call(self._client)
3015.2.9 by Robert Collins
Handle repositories that do not allow remote locking, like pack repositories, in the client side remote server proxy objects.
1698
        if not token:
1699
            # with no token the remote repository is not persistently locked.
1700
            return
3786.2.3 by Andrew Bennetts
Remove duplicated 'call & translate errors' code in bzrlib.remote.
1701
        err_context = {'token': token}
1702
        response = self._call('Repository.unlock', path, token,
1703
                              **err_context)
2018.5.78 by Andrew Bennetts
Implement RemoteRepository.lock_write/unlock to expect and send tokens over the
1704
        if response == ('ok',):
1705
            return
1706
        else:
2555.1.1 by Martin Pool
Remove use of 'assert False' to raise an exception unconditionally
1707
            raise errors.UnexpectedSmartServerResponse(response)
2018.5.78 by Andrew Bennetts
Implement RemoteRepository.lock_write/unlock to expect and send tokens over the
1708
4634.85.9 by Andrew Bennetts
Add some experimental decorators: @only_raises(..) and @cleanup_method.
1709
    @only_raises(errors.LockNotHeld, errors.LockBroken)
2018.5.60 by Robert Collins
More missing methods from RemoteBranch and RemoteRepository to let 'info' get further.
1710
    def unlock(self):
4032.3.2 by Robert Collins
Create and use a RPC call to create branches on bzr servers rather than using VFS calls.
1711
        if not self._lock_count:
4509.3.25 by Martin Pool
Add an option for unlock errors to be non-fatal
1712
            return lock.cant_unlock_not_held(self)
2018.5.75 by Andrew Bennetts
Add Repository.{dont_,}leave_lock_in_place.
1713
        self._lock_count -= 1
2592.3.244 by Martin Pool
unlock while in a write group now aborts the write group, unlocks, and errors.
1714
        if self._lock_count > 0:
1715
            return
3835.1.8 by Aaron Bentley
Make UnstackedParentsProvider manage the cache
1716
        self._unstacked_provider.disable_cache()
2592.3.244 by Martin Pool
unlock while in a write group now aborts the write group, unlocks, and errors.
1717
        old_mode = self._lock_mode
1718
        self._lock_mode = None
1719
        try:
1720
            # The real repository is responsible at present for raising an
1721
            # exception if it's in an unfinished write group.  However, it
1722
            # normally will *not* actually remove the lock from disk - that's
1723
            # done by the server on receiving the Repository.unlock call.
1724
            # This is just to let the _real_repository stay up to date.
2018.5.78 by Andrew Bennetts
Implement RemoteRepository.lock_write/unlock to expect and send tokens over the
1725
            if self._real_repository is not None:
1726
                self._real_repository.unlock()
6280.7.6 by Jelmer Vernooij
Fix remaining tests.
1727
            elif self._write_group_tokens is not None:
1728
                self.abort_write_group()
2592.3.244 by Martin Pool
unlock while in a write group now aborts the write group, unlocks, and errors.
1729
        finally:
1730
            # The rpc-level lock should be released even if there was a
1731
            # problem releasing the vfs-based lock.
1732
            if old_mode == 'w':
2018.5.163 by Andrew Bennetts
Deal with various review comments from Robert.
1733
                # Only write-locked repositories need to make a remote method
4031.3.1 by Frank Aspell
Fixing various typos
1734
                # call to perform the unlock.
2592.3.244 by Martin Pool
unlock while in a write group now aborts the write group, unlocks, and errors.
1735
                old_token = self._lock_token
1736
                self._lock_token = None
1737
                if not self._leave_lock:
1738
                    self._unlock(old_token)
4379.2.1 by John Arbash Meinel
Change the fallback repository code to only lock/unlock on transition.
1739
        # Fallbacks are always 'lock_read()' so we don't pay attention to
1740
        # self._leave_lock
1741
        for repo in self._fallback_repositories:
1742
            repo.unlock()
2018.5.60 by Robert Collins
More missing methods from RemoteBranch and RemoteRepository to let 'info' get further.
1743
1744
    def break_lock(self):
2018.5.78 by Andrew Bennetts
Implement RemoteRepository.lock_write/unlock to expect and send tokens over the
1745
        # should hand off to the network
6280.4.5 by Jelmer Vernooij
Fix tests.
1746
        path = self.bzrdir._path_for_remote_call(self._client)
6280.4.1 by Jelmer Vernooij
Add remote side of Repository.break_lock.
1747
        try:
6280.4.5 by Jelmer Vernooij
Fix tests.
1748
            response = self._call("Repository.break_lock", path)
6280.4.1 by Jelmer Vernooij
Add remote side of Repository.break_lock.
1749
        except errors.UnknownSmartMethod:
1750
            self._ensure_real()
1751
            return self._real_repository.break_lock()
1752
        if response != ('ok',):
1753
            raise errors.UnexpectedSmartServerResponse(response)
2018.5.60 by Robert Collins
More missing methods from RemoteBranch and RemoteRepository to let 'info' get further.
1754
2018.18.8 by Ian Clatworthy
Tarball proxy code & tests
1755
    def _get_tarball(self, compression):
2814.10.2 by Andrew Bennetts
Make the fallback a little tidier.
1756
        """Return a TemporaryFile containing a repository tarball.
3943.8.1 by Marius Kruger
remove all trailing whitespace from bzr source
1757
2814.10.2 by Andrew Bennetts
Make the fallback a little tidier.
1758
        Returns None if the server does not support sending tarballs.
1759
        """
2018.18.25 by Martin Pool
Repository.tarball fixes for python2.4
1760
        import tempfile
2018.18.8 by Ian Clatworthy
Tarball proxy code & tests
1761
        path = self.bzrdir._path_for_remote_call(self._client)
3297.3.3 by Andrew Bennetts
SmartClientRequestProtocol*.read_response_tuple can now raise UnknownSmartMethod. Callers no longer need to do their own ad hoc unknown smart method error detection.
1762
        try:
3786.2.3 by Andrew Bennetts
Remove duplicated 'call & translate errors' code in bzrlib.remote.
1763
            response, protocol = self._call_expecting_body(
3297.3.3 by Andrew Bennetts
SmartClientRequestProtocol*.read_response_tuple can now raise UnknownSmartMethod. Callers no longer need to do their own ad hoc unknown smart method error detection.
1764
                'Repository.tarball', path, compression)
1765
        except errors.UnknownSmartMethod:
1766
            protocol.cancel_read_body()
1767
            return None
2018.18.8 by Ian Clatworthy
Tarball proxy code & tests
1768
        if response[0] == 'ok':
1769
            # Extract the tarball and return it
2018.18.25 by Martin Pool
Repository.tarball fixes for python2.4
1770
            t = tempfile.NamedTemporaryFile()
1771
            # TODO: rpc layer should read directly into it...
1772
            t.write(protocol.read_body_bytes())
1773
            t.seek(0)
1774
            return t
2814.10.1 by Andrew Bennetts
Cope gracefully if the server doesn't support the Repository.tarball smart request.
1775
        raise errors.UnexpectedSmartServerResponse(response)
2018.18.8 by Ian Clatworthy
Tarball proxy code & tests
1776
6267.1.2 by Jelmer Vernooij
Avoid _ensure_real in some more calls.
1777
    @needs_read_lock
2440.1.1 by Martin Pool
Add new Repository.sprout,
1778
    def sprout(self, to_bzrdir, revision_id=None):
6267.1.2 by Jelmer Vernooij
Avoid _ensure_real in some more calls.
1779
        """Create a descendent repository for new development.
1780
1781
        Unlike clone, this does not copy the settings of the repository.
1782
        """
1783
        dest_repo = self._create_sprouting_repo(to_bzrdir, shared=False)
2535.3.17 by Andrew Bennetts
[broken] Closer to a working Repository.fetch_revisions smart request.
1784
        dest_repo.fetch(self, revision_id=revision_id)
1785
        return dest_repo
2440.1.1 by Martin Pool
Add new Repository.sprout,
1786
6267.1.2 by Jelmer Vernooij
Avoid _ensure_real in some more calls.
1787
    def _create_sprouting_repo(self, a_bzrdir, shared):
1788
        if not isinstance(a_bzrdir._format, self.bzrdir._format.__class__):
1789
            # use target default format.
1790
            dest_repo = a_bzrdir.create_repository()
1791
        else:
1792
            # Most control formats need the repository to be specifically
1793
            # created, but on some old all-in-one formats it's not needed
1794
            try:
1795
                dest_repo = self._format.initialize(a_bzrdir, shared=shared)
1796
            except errors.UninitializableFormat:
1797
                dest_repo = a_bzrdir.open_repository()
1798
        return dest_repo
1799
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
1800
    ### These methods are just thin shims to the VFS object for now.
1801
6267.1.3 by Jelmer Vernooij
Fix tests.
1802
    @needs_read_lock
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
1803
    def revision_tree(self, revision_id):
6267.1.3 by Jelmer Vernooij
Fix tests.
1804
        revision_id = _mod_revision.ensure_null(revision_id)
1805
        if revision_id == _mod_revision.NULL_REVISION:
1806
            return InventoryRevisionTree(self,
1807
                Inventory(root_id=None), _mod_revision.NULL_REVISION)
1808
        else:
1809
            return list(self.revision_trees([revision_id]))[0]
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
1810
2520.4.113 by Aaron Bentley
Avoid peeking at Repository._serializer
1811
    def get_serializer_format(self):
6280.5.1 by Jelmer Vernooij
Add client side of Repository.get_serializer_format.
1812
        path = self.bzrdir._path_for_remote_call(self._client)
1813
        try:
1814
            response = self._call('VersionedFileRepository.get_serializer_format',
1815
                path)
1816
        except errors.UnknownSmartMethod:
1817
            self._ensure_real()
1818
            return self._real_repository.get_serializer_format()
1819
        if response[0] != 'ok':
1820
            raise errors.UnexpectedSmartServerResponse(response)
6280.5.2 by Jelmer Vernooij
New HPSS call VersionedFileRepository.get_serializer_format.
1821
        return response[1]
2520.4.113 by Aaron Bentley
Avoid peeking at Repository._serializer
1822
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
1823
    def get_commit_builder(self, branch, parents, config, timestamp=None,
1824
                           timezone=None, committer=None, revprops=None,
5777.6.1 by Jelmer Vernooij
Add --lossy option to 'bzr commit'.
1825
                           revision_id=None, lossy=False):
6362.5.1 by Jelmer Vernooij
Implement RemoteRepository.get_commit_builder.
1826
        """Obtain a CommitBuilder for this repository.
1827
1828
        :param branch: Branch to commit to.
1829
        :param parents: Revision ids of the parents of the new revision.
1830
        :param config: Configuration to use.
1831
        :param timestamp: Optional timestamp recorded for commit.
1832
        :param timezone: Optional timezone for timestamp.
1833
        :param committer: Optional committer to set for commit.
1834
        :param revprops: Optional dictionary of revision properties.
1835
        :param revision_id: Optional revision id.
1836
        :param lossy: Whether to discard data that can not be natively
1837
            represented, when pushing to a foreign VCS
1838
        """
1839
        if self._fallback_repositories and not self._format.supports_chks:
1840
            raise errors.BzrError("Cannot commit directly to a stacked branch"
1841
                " in pre-2a formats. See "
1842
                "https://bugs.launchpad.net/bzr/+bug/375013 for details.")
1843
        if self._format.rich_root_data:
1844
            commit_builder_kls = vf_repository.VersionedFileRootCommitBuilder
1845
        else:
1846
            commit_builder_kls = vf_repository.VersionedFileCommitBuilder
1847
        result = commit_builder_kls(self, parents, config,
1848
            timestamp, timezone, committer, revprops, revision_id,
1849
            lossy)
1850
        self.start_write_group()
1851
        return result
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
1852
3221.12.1 by Robert Collins
Backport development1 format (stackable packs) to before-shallow-branches.
1853
    def add_fallback_repository(self, repository):
1854
        """Add a repository to use for looking up data not held locally.
3943.8.1 by Marius Kruger
remove all trailing whitespace from bzr source
1855
3221.12.1 by Robert Collins
Backport development1 format (stackable packs) to before-shallow-branches.
1856
        :param repository: A repository.
1857
        """
4118.1.1 by Andrew Bennetts
Fix performance regression (many small round-trips) when pushing to a remote pack, and tidy the tests.
1858
        if not self._format.supports_external_lookups:
1859
            raise errors.UnstackableRepositoryFormat(
1860
                self._format.network_name(), self.base)
3221.12.1 by Robert Collins
Backport development1 format (stackable packs) to before-shallow-branches.
1861
        # We need to accumulate additional repositories here, to pass them in
1862
        # on various RPC's.
4035.2.3 by Robert Collins
Fix trailing whitespace.
1863
        #
5609.54.1 by Gary Poster
repositories should not be locked in add_fallback_repository if they will not be used.
1864
        # Make the check before we lock: this raises an exception.
1865
        self._check_fallback_repository(repository)
4379.2.2 by John Arbash Meinel
Change the Repository.add_fallback_repository() contract slightly.
1866
        if self.is_locked():
1867
            # We will call fallback.unlock() when we transition to the unlocked
1868
            # state, so always add a lock here. If a caller passes us a locked
1869
            # repository, they are responsible for unlocking it later.
1870
            repository.lock_read()
3221.12.1 by Robert Collins
Backport development1 format (stackable packs) to before-shallow-branches.
1871
        self._fallback_repositories.append(repository)
4035.2.2 by Robert Collins
Minor tweaks to fix failing tests.
1872
        # If self._real_repository was parameterised already (e.g. because a
1873
        # _real_branch had its get_stacked_on_url method called), then the
1874
        # repository to be added may already be in the _real_repositories list.
4035.2.1 by Andrew Bennetts
Fix unnecessary get_parent_map calls after insert_stream during push.
1875
        if self._real_repository is not None:
5158.6.7 by Martin Pool
More conversions to using user_url
1876
            fallback_locations = [repo.user_url for repo in
4226.2.5 by Robert Collins
Fix handling of fallback repositories some more.
1877
                self._real_repository._fallback_repositories]
5158.6.7 by Martin Pool
More conversions to using user_url
1878
            if repository.user_url not in fallback_locations:
4035.2.2 by Robert Collins
Minor tweaks to fix failing tests.
1879
                self._real_repository.add_fallback_repository(repository)
3221.12.1 by Robert Collins
Backport development1 format (stackable packs) to before-shallow-branches.
1880
5158.4.1 by Andrew Bennetts
Don't allow RemoteRepository to stack on incompatible formats.
1881
    def _check_fallback_repository(self, repository):
1882
        """Check that this repository can fallback to repository safely.
1883
1884
        Raise an error if not.
1885
1886
        :param repository: A repository to fallback to.
1887
        """
1888
        return _mod_repository.InterRepository._assert_same_model(
1889
            self, repository)
1890
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
1891
    def add_inventory(self, revid, inv, parents):
1892
        self._ensure_real()
1893
        return self._real_repository.add_inventory(revid, inv, parents)
1894
3879.2.2 by John Arbash Meinel
Rename add_inventory_delta to add_inventory_by_delta.
1895
    def add_inventory_by_delta(self, basis_revision_id, delta, new_revision_id,
5076.1.1 by Jelmer Vernooij
Allow additional arguments to RemoteRepository.add_inventory_by_delta().
1896
            parents, basis_inv=None, propagate_caches=False):
3775.2.1 by Robert Collins
Create bzrlib.repository.Repository.add_inventory_delta for adding inventories via deltas.
1897
        self._ensure_real()
3879.2.2 by John Arbash Meinel
Rename add_inventory_delta to add_inventory_by_delta.
1898
        return self._real_repository.add_inventory_by_delta(basis_revision_id,
5076.1.2 by Jelmer Vernooij
pass the keyword args as keyword args, per Rob's review.
1899
            delta, new_revision_id, parents, basis_inv=basis_inv,
1900
            propagate_caches=propagate_caches)
3775.2.1 by Robert Collins
Create bzrlib.repository.Repository.add_inventory_delta for adding inventories via deltas.
1901
6421.2.1 by Jelmer Vernooij
Move revision signing to CommitBuilder.
1902
    def add_revision(self, revision_id, rev, inv=None):
6362.6.1 by Jelmer Vernooij
Implement RemoteRepository.add_revision.
1903
        _mod_revision.check_not_reserved_id(revision_id)
1904
        key = (revision_id,)
1905
        # check inventory present
1906
        if not self.inventories.get_parent_map([key]):
1907
            if inv is None:
1908
                raise errors.WeaveRevisionNotPresent(revision_id,
1909
                                                     self.inventories)
1910
            else:
1911
                # yes, this is not suitable for adding with ghosts.
1912
                rev.inventory_sha1 = self.add_inventory(revision_id, inv,
1913
                                                        rev.parent_ids)
1914
        else:
1915
            rev.inventory_sha1 = self.inventories.get_sha1s([key])[key]
6421.2.1 by Jelmer Vernooij
Move revision signing to CommitBuilder.
1916
        self._add_revision(rev)
1917
1918
    def _add_revision(self, rev):
6362.6.1 by Jelmer Vernooij
Implement RemoteRepository.add_revision.
1919
        if self._real_repository is not None:
6421.2.1 by Jelmer Vernooij
Move revision signing to CommitBuilder.
1920
            return self._real_repository._add_revision(rev)
6362.6.1 by Jelmer Vernooij
Implement RemoteRepository.add_revision.
1921
        text = self._serializer.write_revision_to_string(rev)
6421.2.1 by Jelmer Vernooij
Move revision signing to CommitBuilder.
1922
        key = (rev.revision_id,)
6362.6.1 by Jelmer Vernooij
Implement RemoteRepository.add_revision.
1923
        parents = tuple((parent,) for parent in rev.parent_ids)
1924
        self._write_group_tokens, missing_keys = self._get_sink().insert_stream(
1925
            [('revisions', [FulltextContentFactory(key, parents, None, text)])],
1926
            self._format, self._write_group_tokens)
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
1927
1928
    @needs_read_lock
1929
    def get_inventory(self, revision_id):
6280.11.1 by Jelmer Vernooij
Implement RemoteRepository.get_inventory using RemoteRepository.iter_inventories
1930
        return list(self.iter_inventories([revision_id]))[0]
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
1931
6282.6.9 by Jelmer Vernooij
More tests.
1932
    def _iter_inventories_rpc(self, revision_ids, ordering):
6282.6.3 by Jelmer Vernooij
Add stub for remote iter inventories.
1933
        if ordering is None:
6282.6.19 by Jelmer Vernooij
More test fixes.
1934
            ordering = 'unordered'
6282.6.3 by Jelmer Vernooij
Add stub for remote iter inventories.
1935
        path = self.bzrdir._path_for_remote_call(self._client)
6282.6.9 by Jelmer Vernooij
More tests.
1936
        body = "\n".join(revision_ids)
6282.6.3 by Jelmer Vernooij
Add stub for remote iter inventories.
1937
        response_tuple, response_handler = (
1938
            self._call_with_body_bytes_expecting_body(
6282.6.28 by Jelmer Vernooij
Rename VersionedFileRepository.iter_inventories to VersionedFileRepository.get_inventories.
1939
                "VersionedFileRepository.get_inventories",
6282.6.9 by Jelmer Vernooij
More tests.
1940
                (path, ordering), body))
6282.6.5 by Jelmer Vernooij
Use iter_inventory_deltas.
1941
        if response_tuple[0] != "ok":
6282.6.3 by Jelmer Vernooij
Add stub for remote iter inventories.
1942
            raise errors.UnexpectedSmartServerResponse(response_tuple)
6282.6.5 by Jelmer Vernooij
Use iter_inventory_deltas.
1943
        deserializer = inventory_delta.InventoryDeltaDeserializer()
6282.6.3 by Jelmer Vernooij
Add stub for remote iter inventories.
1944
        byte_stream = response_handler.read_streamed_body()
6282.6.37 by Jelmer Vernooij
Cope with empty results.
1945
        decoded = smart_repo._byte_stream_to_stream(byte_stream)
1946
        if decoded is None:
1947
            # no results whatsoever
1948
            return
1949
        src_format, stream = decoded
6282.6.31 by Jelmer Vernooij
Use record streams in get_inventories call.
1950
        if src_format.network_name() != self._format.network_name():
1951
            raise AssertionError(
1952
                "Mismatched RemoteRepository and stream src %r, %r" % (
1953
                src_format.network_name(), self._format.network_name()))
1954
        # ignore the src format, it's not really relevant
6282.6.9 by Jelmer Vernooij
More tests.
1955
        prev_inv = Inventory(root_id=None,
1956
            revision_id=_mod_revision.NULL_REVISION)
6282.6.31 by Jelmer Vernooij
Use record streams in get_inventories call.
1957
        # there should be just one substream, with inventory deltas
6634.2.1 by Martin
Apply 2to3 next fixer and make compatible
1958
        substream_kind, substream = next(stream)
6282.6.39 by Jelmer Vernooij
add an extra assertion.
1959
        if substream_kind != "inventory-deltas":
1960
            raise AssertionError(
1961
                 "Unexpected stream %r received" % substream_kind)
6282.6.31 by Jelmer Vernooij
Use record streams in get_inventories call.
1962
        for record in substream:
6282.6.9 by Jelmer Vernooij
More tests.
1963
            (parent_id, new_id, versioned_root, tree_references, invdelta) = (
6282.6.31 by Jelmer Vernooij
Use record streams in get_inventories call.
1964
                deserializer.parse_text_bytes(record.get_bytes_as("fulltext")))
6282.6.9 by Jelmer Vernooij
More tests.
1965
            if parent_id != prev_inv.revision_id:
1966
                raise AssertionError("invalid base %r != %r" % (parent_id,
1967
                    prev_inv.revision_id))
6282.6.31 by Jelmer Vernooij
Use record streams in get_inventories call.
1968
            inv = prev_inv.create_by_apply_delta(invdelta, new_id)
6282.6.18 by Jelmer Vernooij
Fix tests.
1969
            yield inv, inv.revision_id
6282.6.31 by Jelmer Vernooij
Use record streams in get_inventories call.
1970
            prev_inv = inv
6282.6.9 by Jelmer Vernooij
More tests.
1971
1972
    def _iter_inventories_vfs(self, revision_ids, ordering=None):
1973
        self._ensure_real()
6282.6.18 by Jelmer Vernooij
Fix tests.
1974
        return self._real_repository._iter_inventories(revision_ids, ordering)
6282.6.3 by Jelmer Vernooij
Add stub for remote iter inventories.
1975
4476.3.86 by Andrew Bennetts
Fix bug in declaration of RemoteRepository.iter_inventories that was causing intermittent failures in test_iter_inventories_is_ordered.
1976
    def iter_inventories(self, revision_ids, ordering=None):
6282.6.18 by Jelmer Vernooij
Fix tests.
1977
        """Get many inventories by revision_ids.
1978
1979
        This will buffer some or all of the texts used in constructing the
1980
        inventories in memory, but will only parse a single inventory at a
1981
        time.
1982
1983
        :param revision_ids: The expected revision ids of the inventories.
1984
        :param ordering: optional ordering, e.g. 'topological'.  If not
1985
            specified, the order of revision_ids will be preserved (by
1986
            buffering if necessary).
1987
        :return: An iterator of inventories.
1988
        """
6282.6.3 by Jelmer Vernooij
Add stub for remote iter inventories.
1989
        if ((None in revision_ids)
1990
            or (_mod_revision.NULL_REVISION in revision_ids)):
1991
            raise ValueError('cannot get null revision inventory')
6282.6.18 by Jelmer Vernooij
Fix tests.
1992
        for inv, revid in self._iter_inventories(revision_ids, ordering):
1993
            if inv is None:
1994
                raise errors.NoSuchRevision(self, revid)
1995
            yield inv
1996
1997
    def _iter_inventories(self, revision_ids, ordering=None):
6282.6.9 by Jelmer Vernooij
More tests.
1998
        if len(revision_ids) == 0:
1999
            return
2000
        missing = set(revision_ids)
2001
        if ordering is None:
2002
            order_as_requested = True
2003
            invs = {}
2004
            order = list(revision_ids)
2005
            order.reverse()
2006
            next_revid = order.pop()
6282.6.10 by Jelmer Vernooij
Fix smart tests.
2007
        else:
6282.6.9 by Jelmer Vernooij
More tests.
2008
            order_as_requested = False
6282.6.10 by Jelmer Vernooij
Fix smart tests.
2009
            if ordering != 'unordered' and self._fallback_repositories:
2010
                raise ValueError('unsupported ordering %r' % ordering)
6282.6.9 by Jelmer Vernooij
More tests.
2011
        iter_inv_fns = [self._iter_inventories_rpc] + [
2012
            fallback._iter_inventories for fallback in
2013
            self._fallback_repositories]
6282.6.3 by Jelmer Vernooij
Add stub for remote iter inventories.
2014
        try:
6282.6.9 by Jelmer Vernooij
More tests.
2015
            for iter_inv in iter_inv_fns:
2016
                request = [revid for revid in revision_ids if revid in missing]
6282.6.18 by Jelmer Vernooij
Fix tests.
2017
                for inv, revid in iter_inv(request, ordering):
6282.6.21 by Jelmer Vernooij
Fix nosuchrevision.
2018
                    if inv is None:
2019
                        continue
6282.6.9 by Jelmer Vernooij
More tests.
2020
                    missing.remove(inv.revision_id)
2021
                    if ordering != 'unordered':
6282.6.18 by Jelmer Vernooij
Fix tests.
2022
                        invs[revid] = inv
6282.6.9 by Jelmer Vernooij
More tests.
2023
                    else:
6282.6.18 by Jelmer Vernooij
Fix tests.
2024
                        yield inv, revid
6282.6.9 by Jelmer Vernooij
More tests.
2025
                if order_as_requested:
2026
                    # Yield as many results as we can while preserving order.
2027
                    while next_revid in invs:
2028
                        inv = invs.pop(next_revid)
6282.6.18 by Jelmer Vernooij
Fix tests.
2029
                        yield inv, inv.revision_id
6282.6.9 by Jelmer Vernooij
More tests.
2030
                        try:
2031
                            next_revid = order.pop()
2032
                        except IndexError:
2033
                            # We still want to fully consume the stream, just
2034
                            # in case it is not actually finished at this point
2035
                            next_revid = None
2036
                            break
6282.6.3 by Jelmer Vernooij
Add stub for remote iter inventories.
2037
        except errors.UnknownSmartMethod:
6282.6.26 by Jelmer Vernooij
Fix iteration.
2038
            for inv, revid in self._iter_inventories_vfs(revision_ids, ordering):
2039
                yield inv, revid
6282.6.9 by Jelmer Vernooij
More tests.
2040
            return
6282.6.18 by Jelmer Vernooij
Fix tests.
2041
        # Report missing
2042
        if order_as_requested:
6282.6.21 by Jelmer Vernooij
Fix nosuchrevision.
2043
            if next_revid is not None:
2044
                yield None, next_revid
6282.6.18 by Jelmer Vernooij
Fix tests.
2045
            while order:
6282.6.19 by Jelmer Vernooij
More test fixes.
2046
                revid = order.pop()
2047
                yield invs.get(revid), revid
6282.6.18 by Jelmer Vernooij
Fix tests.
2048
        else:
2049
            while missing:
2050
                yield None, missing.pop()
3169.2.1 by Robert Collins
New method ``iter_inventories`` on Repository for access to many
2051
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
2052
    @needs_read_lock
2053
    def get_revision(self, revision_id):
6267.1.1 by Jelmer Vernooij
Avoid _ensure_real in a couple more places.
2054
        return self.get_revisions([revision_id])[0]
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
2055
2056
    def get_transaction(self):
2057
        self._ensure_real()
2058
        return self._real_repository.get_transaction()
2059
2060
    @needs_read_lock
2018.5.138 by Robert Collins
Merge bzr.dev.
2061
    def clone(self, a_bzrdir, revision_id=None):
6267.1.2 by Jelmer Vernooij
Avoid _ensure_real in some more calls.
2062
        dest_repo = self._create_sprouting_repo(
6267.1.3 by Jelmer Vernooij
Fix tests.
2063
            a_bzrdir, shared=self.is_shared())
6267.1.2 by Jelmer Vernooij
Avoid _ensure_real in some more calls.
2064
        self.copy_content_into(dest_repo, revision_id)
2065
        return dest_repo
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
2066
2067
    def make_working_trees(self):
3349.1.1 by Aaron Bentley
Enable setting and getting make_working_trees for all repositories
2068
        """See Repository.make_working_trees"""
6263.2.1 by Jelmer Vernooij
Add hpss call ``Repository.make_working_trees``
2069
        path = self.bzrdir._path_for_remote_call(self._client)
2070
        try:
2071
            response = self._call('Repository.make_working_trees', path)
2072
        except errors.UnknownSmartMethod:
2073
            self._ensure_real()
2074
            return self._real_repository.make_working_trees()
2075
        if response[0] not in ('yes', 'no'):
2076
            raise SmartProtocolError('unexpected response code %s' % (response,))
2077
        return response[0] == 'yes'
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
2078
4145.1.2 by Robert Collins
Add a refresh_data method on Repository allowing cleaner handling of insertions into RemoteRepository objects with _real_repository instances.
2079
    def refresh_data(self):
5199.1.3 by Andrew Bennetts
Use Robert's text for the refresh_data docstring.
2080
        """Re-read any data needed to synchronise with disk.
4145.1.2 by Robert Collins
Add a refresh_data method on Repository allowing cleaner handling of insertions into RemoteRepository objects with _real_repository instances.
2081
2082
        This method is intended to be called after another repository instance
2083
        (such as one used by a smart server) has inserted data into the
5199.1.3 by Andrew Bennetts
Use Robert's text for the refresh_data docstring.
2084
        repository. On all repositories this will work outside of write groups.
6622.1.34 by Jelmer Vernooij
Rename brzlib => breezy.
2085
        Some repository formats (pack and newer for breezy native formats)
5199.1.3 by Andrew Bennetts
Use Robert's text for the refresh_data docstring.
2086
        support refresh_data inside write groups. If called inside a write
2087
        group on a repository that does not support refreshing in a write group
2088
        IsInWriteGroupError will be raised.
4145.1.2 by Robert Collins
Add a refresh_data method on Repository allowing cleaner handling of insertions into RemoteRepository objects with _real_repository instances.
2089
        """
2090
        if self._real_repository is not None:
2091
            self._real_repository.refresh_data()
6362.5.3 by Jelmer Vernooij
Add comments.
2092
        # Refresh the parents cache for this object
6362.5.2 by Jelmer Vernooij
Fix tests.
2093
        self._unstacked_provider.disable_cache()
2094
        self._unstacked_provider.enable_cache()
4145.1.2 by Robert Collins
Add a refresh_data method on Repository allowing cleaner handling of insertions into RemoteRepository objects with _real_repository instances.
2095
3184.1.9 by Robert Collins
* ``Repository.get_data_stream`` is now deprecated in favour of
2096
    def revision_ids_to_search_result(self, result_set):
2097
        """Convert a set of revision ids to a graph SearchResult."""
2098
        result_parents = set()
6656.1.1 by Martin
Apply 2to3 dict fixer and clean up resulting mess using view helpers
2099
        for parents in viewvalues(self.get_graph().get_parent_map(result_set)):
3184.1.9 by Robert Collins
* ``Repository.get_data_stream`` is now deprecated in favour of
2100
            result_parents.update(parents)
2101
        included_keys = result_set.intersection(result_parents)
2102
        start_keys = result_set.difference(included_keys)
2103
        exclude_keys = result_parents.difference(result_set)
6341.1.4 by Jelmer Vernooij
Move more functionality to vf_search.
2104
        result = vf_search.SearchResult(start_keys, exclude_keys,
3184.1.9 by Robert Collins
* ``Repository.get_data_stream`` is now deprecated in favour of
2105
            len(result_set), result_set)
2106
        return result
2107
2108
    @needs_read_lock
5539.2.10 by Andrew Bennetts
s/NotInOtherForRev/NotInOtherForRevs/, and allow passing multiple revision_ids to search_missing_revision_ids.
2109
    def search_missing_revision_ids(self, other,
5852.1.6 by Jelmer Vernooij
Add extra test for Repository.search_missing_revision_ids.
2110
            find_ghosts=True, revision_ids=None, if_present_ids=None,
2111
            limit=None):
3184.1.9 by Robert Collins
* ``Repository.get_data_stream`` is now deprecated in favour of
2112
        """Return the revision ids that other has that this does not.
3943.8.1 by Marius Kruger
remove all trailing whitespace from bzr source
2113
3184.1.9 by Robert Collins
* ``Repository.get_data_stream`` is now deprecated in favour of
2114
        These are returned in topological order.
2115
2116
        revision_id: only return revision ids included by revision_id.
2117
        """
5712.3.13 by Jelmer Vernooij
Add Prober.known_formats().
2118
        inter_repo = _mod_repository.InterRepository.get(other, self)
5539.2.10 by Andrew Bennetts
s/NotInOtherForRev/NotInOtherForRevs/, and allow passing multiple revision_ids to search_missing_revision_ids.
2119
        return inter_repo.search_missing_revision_ids(
5535.3.32 by Andrew Bennetts
Implement if_present_ids behaviour in all implementations and code paths of searching_missing_revision_ids
2120
            find_ghosts=find_ghosts, revision_ids=revision_ids,
5852.1.6 by Jelmer Vernooij
Add extra test for Repository.search_missing_revision_ids.
2121
            if_present_ids=if_present_ids, limit=limit)
3184.1.9 by Robert Collins
* ``Repository.get_data_stream`` is now deprecated in favour of
2122
5670.1.1 by Jelmer Vernooij
Remove all methods and arguments that were deprecated before bzr 2.0.0.
2123
    def fetch(self, source, revision_id=None, find_ghosts=False,
4070.9.2 by Andrew Bennetts
Rough prototype of allowing a SearchResult to be passed to fetch, and using that to improve network conversations.
2124
            fetch_spec=None):
4145.1.1 by Robert Collins
Explicitly prevent fetching while the target repository is in a write group.
2125
        # No base implementation to use as RemoteRepository is not a subclass
2126
        # of Repository; so this is a copy of Repository.fetch().
4070.9.2 by Andrew Bennetts
Rough prototype of allowing a SearchResult to be passed to fetch, and using that to improve network conversations.
2127
        if fetch_spec is not None and revision_id is not None:
2128
            raise AssertionError(
2129
                "fetch_spec and revision_id are mutually exclusive.")
4145.1.1 by Robert Collins
Explicitly prevent fetching while the target repository is in a write group.
2130
        if self.is_in_write_group():
4145.1.3 by Robert Collins
NEWS conflicts.
2131
            raise errors.InternalBzrError(
2132
                "May not fetch while in a write group.")
4145.1.1 by Robert Collins
Explicitly prevent fetching while the target repository is in a write group.
2133
        # fast path same-url fetch operations
4509.3.19 by Martin Pool
RemoteRepository.fetch is not a no-op if there's different stacking
2134
        if (self.has_same_location(source)
2135
            and fetch_spec is None
4509.3.37 by Martin Pool
Remove RepositoryBase; make _has_same_location private
2136
            and self._has_same_fallbacks(source)):
2881.4.1 by Robert Collins
Move responsibility for detecting same-repo fetching from the
2137
            # check that last_revision is in 'from' and then return a
2138
            # no-operation.
2139
            if (revision_id is not None and
5712.3.13 by Jelmer Vernooij
Add Prober.known_formats().
2140
                not _mod_revision.is_null(revision_id)):
2881.4.1 by Robert Collins
Move responsibility for detecting same-repo fetching from the
2141
                self.get_revision(revision_id)
2592.4.5 by Martin Pool
Add Repository.base on all repositories.
2142
            return 0, []
4145.1.1 by Robert Collins
Explicitly prevent fetching while the target repository is in a write group.
2143
        # if there is no specific appropriate InterRepository, this will get
2144
        # the InterRepository base class, which raises an
2145
        # IncompatibleRepositories when asked to fetch.
5712.3.13 by Jelmer Vernooij
Add Prober.known_formats().
2146
        inter = _mod_repository.InterRepository.get(source, self)
6341.1.2 by Jelmer Vernooij
Update remote, too.
2147
        if (fetch_spec is not None and
2148
            not getattr(inter, "supports_fetch_spec", False)):
2149
            raise errors.UnsupportedOperation(
2150
                "fetch_spec not supported for %r" % inter)
5670.1.1 by Jelmer Vernooij
Remove all methods and arguments that were deprecated before bzr 2.0.0.
2151
        return inter.fetch(revision_id=revision_id,
4145.1.1 by Robert Collins
Explicitly prevent fetching while the target repository is in a write group.
2152
            find_ghosts=find_ghosts, fetch_spec=fetch_spec)
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
2153
2520.4.54 by Aaron Bentley
Hang a create_bundle method off repository
2154
    def create_bundle(self, target, base, fileobj, format=None):
2155
        self._ensure_real()
2156
        self._real_repository.create_bundle(target, base, fileobj, format)
2157
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
2158
    def fileids_altered_by_revision_ids(self, revision_ids):
2159
        self._ensure_real()
2160
        return self._real_repository.fileids_altered_by_revision_ids(revision_ids)
2161
3036.1.3 by Robert Collins
Privatise VersionedFileChecker.
2162
    def _get_versioned_file_checker(self, revisions, revision_versions_cache):
2745.6.1 by Aaron Bentley
Initial checking of knit graphs
2163
        self._ensure_real()
3036.1.3 by Robert Collins
Privatise VersionedFileChecker.
2164
        return self._real_repository._get_versioned_file_checker(
2745.6.50 by Andrew Bennetts
Remove find_bad_ancestors; it's not needed anymore.
2165
            revisions, revision_versions_cache)
3943.8.1 by Marius Kruger
remove all trailing whitespace from bzr source
2166
6280.10.12 by Jelmer Vernooij
Handle stacking.
2167
    def _iter_files_bytes_rpc(self, desired_files, absent):
6280.10.7 by Jelmer Vernooij
Fix remote.
2168
        path = self.bzrdir._path_for_remote_call(self._client)
2169
        lines = []
2170
        identifiers = []
2171
        for (file_id, revid, identifier) in desired_files:
6280.10.18 by Jelmer Vernooij
Ensure file ids are always utf8.
2172
            lines.append("%s\0%s" % (
2173
                osutils.safe_file_id(file_id),
2174
                osutils.safe_revision_id(revid)))
6280.10.7 by Jelmer Vernooij
Fix remote.
2175
            identifiers.append(identifier)
2176
        (response_tuple, response_handler) = (
2177
            self._call_with_body_bytes_expecting_body(
6280.10.19 by Jelmer Vernooij
Convert remote side to zlib.
2178
            "Repository.iter_files_bytes", (path, ), "\n".join(lines)))
6280.10.7 by Jelmer Vernooij
Fix remote.
2179
        if response_tuple != ('ok', ):
2180
            response_handler.cancel_read_body()
2181
            raise errors.UnexpectedSmartServerResponse(response_tuple)
2182
        byte_stream = response_handler.read_streamed_body()
6280.10.10 by Jelmer Vernooij
Use streaming.
2183
        def decompress_stream(start, byte_stream, unused):
6280.10.19 by Jelmer Vernooij
Convert remote side to zlib.
2184
            decompressor = zlib.decompressobj()
6280.10.10 by Jelmer Vernooij
Use streaming.
2185
            yield decompressor.decompress(start)
6280.10.8 by Jelmer Vernooij
Fix iterator handling.
2186
            while decompressor.unused_data == "":
2187
                try:
6634.2.1 by Martin
Apply 2to3 next fixer and make compatible
2188
                    data = next(byte_stream)
6280.10.9 by Jelmer Vernooij
Works.
2189
                except StopIteration:
6280.10.8 by Jelmer Vernooij
Fix iterator handling.
2190
                    break
6280.10.22 by Jelmer Vernooij
Simplify code a bit.
2191
                yield decompressor.decompress(data)
2192
            yield decompressor.flush()
6280.10.10 by Jelmer Vernooij
Use streaming.
2193
            unused.append(decompressor.unused_data)
6280.10.8 by Jelmer Vernooij
Fix iterator handling.
2194
        unused = ""
6280.10.7 by Jelmer Vernooij
Fix remote.
2195
        while True:
6280.10.8 by Jelmer Vernooij
Fix iterator handling.
2196
            while not "\n" in unused:
6634.2.1 by Martin
Apply 2to3 next fixer and make compatible
2197
                unused += next(byte_stream)
6280.10.11 by Jelmer Vernooij
mark absent entries.
2198
            header, rest = unused.split("\n", 1)
2199
            args = header.split("\0")
2200
            if args[0] == "absent":
6280.10.12 by Jelmer Vernooij
Handle stacking.
2201
                absent[identifiers[int(args[3])]] = (args[1], args[2])
6280.10.13 by Jelmer Vernooij
Handle absent.
2202
                unused = rest
2203
                continue
6280.10.11 by Jelmer Vernooij
mark absent entries.
2204
            elif args[0] == "ok":
2205
                idx = int(args[1])
2206
            else:
2207
                raise errors.UnexpectedSmartServerResponse(args)
6280.10.22 by Jelmer Vernooij
Simplify code a bit.
2208
            unused_chunks = []
6280.10.11 by Jelmer Vernooij
mark absent entries.
2209
            yield (identifiers[idx],
6280.10.22 by Jelmer Vernooij
Simplify code a bit.
2210
                decompress_stream(rest, byte_stream, unused_chunks))
2211
            unused = "".join(unused_chunks)
6280.10.1 by Jelmer Vernooij
Add remote side of Repository.iter_file_bytes.
2212
2708.1.7 by Aaron Bentley
Rename extract_files_bytes to iter_files_bytes
2213
    def iter_files_bytes(self, desired_files):
2708.1.9 by Aaron Bentley
Clean-up docs and imports
2214
        """See Repository.iter_file_bytes.
2708.1.3 by Aaron Bentley
Implement extract_files_bytes on Repository
2215
        """
6280.10.1 by Jelmer Vernooij
Add remote side of Repository.iter_file_bytes.
2216
        try:
6280.10.12 by Jelmer Vernooij
Handle stacking.
2217
            absent = {}
6280.10.1 by Jelmer Vernooij
Add remote side of Repository.iter_file_bytes.
2218
            for (identifier, bytes_iterator) in self._iter_files_bytes_rpc(
6280.10.12 by Jelmer Vernooij
Handle stacking.
2219
                    desired_files, absent):
6280.10.1 by Jelmer Vernooij
Add remote side of Repository.iter_file_bytes.
2220
                yield identifier, bytes_iterator
6280.10.13 by Jelmer Vernooij
Handle absent.
2221
            for fallback in self._fallback_repositories:
2222
                if not absent:
2223
                    break
6656.1.1 by Martin
Apply 2to3 dict fixer and clean up resulting mess using view helpers
2224
                desired_files = [(key[0], key[1], identifier)
2225
                    for identifier, key in viewitems(absent)]
6280.10.23 by Jelmer Vernooij
Fix access to fallback repositories.
2226
                for (identifier, bytes_iterator) in fallback.iter_files_bytes(desired_files):
6280.10.13 by Jelmer Vernooij
Handle absent.
2227
                    del absent[identifier]
2228
                    yield identifier, bytes_iterator
2229
            if absent:
2230
                # There may be more missing items, but raise an exception
2231
                # for just one.
6656.1.1 by Martin
Apply 2to3 dict fixer and clean up resulting mess using view helpers
2232
                missing_identifier = next(iter(absent))
6280.10.13 by Jelmer Vernooij
Handle absent.
2233
                missing_key = absent[missing_identifier]
6280.10.23 by Jelmer Vernooij
Fix access to fallback repositories.
2234
                raise errors.RevisionNotPresent(revision_id=missing_key[1],
2235
                    file_id=missing_key[0])
6280.10.1 by Jelmer Vernooij
Add remote side of Repository.iter_file_bytes.
2236
        except errors.UnknownSmartMethod:
2237
            self._ensure_real()
2238
            for (identifier, bytes_iterator) in (
2239
                self._real_repository.iter_files_bytes(desired_files)):
2240
                yield identifier, bytes_iterator
2708.1.3 by Aaron Bentley
Implement extract_files_bytes on Repository
2241
6015.24.4 by John Arbash Meinel
For it to all work properly, we have to expose get_parent_map_cached on RemoteRepository.
2242
    def get_cached_parent_map(self, revision_ids):
6622.1.34 by Jelmer Vernooij
Rename brzlib => breezy.
2243
        """See breezy.CachingParentsProvider.get_cached_parent_map"""
6015.24.4 by John Arbash Meinel
For it to all work properly, we have to expose get_parent_map_cached on RemoteRepository.
2244
        return self._unstacked_provider.get_cached_parent_map(revision_ids)
2245
3835.1.1 by Aaron Bentley
Stack get_parent_map on fallback repos
2246
    def get_parent_map(self, revision_ids):
6622.1.34 by Jelmer Vernooij
Rename brzlib => breezy.
2247
        """See breezy.Graph.get_parent_map()."""
3835.1.5 by Aaron Bentley
Fix make_parents_provider
2248
        return self._make_parents_provider().get_parent_map(revision_ids)
3835.1.1 by Aaron Bentley
Stack get_parent_map on fallback repos
2249
2250
    def _get_parent_map_rpc(self, keys):
3172.5.6 by Robert Collins
Create new smart server verb Repository.get_parent_map.
2251
        """Helper for get_parent_map that performs the RPC."""
3313.2.1 by Andrew Bennetts
Change _SmartClient's API to accept a medium and a base, rather than a _SharedConnection.
2252
        medium = self._client._medium
3453.4.10 by Andrew Bennetts
Change _is_remote_at_least to _is_remote_before.
2253
        if medium._is_remote_before((1, 2)):
3213.1.1 by Andrew Bennetts
Recover (by reconnecting) if the server turns out not to understand the new requests in 1.2 that send bodies.
2254
            # We already found out that the server can't understand
3213.1.3 by Andrew Bennetts
Fix typo in comment.
2255
            # Repository.get_parent_map requests, so just fetch the whole
3213.1.1 by Andrew Bennetts
Recover (by reconnecting) if the server turns out not to understand the new requests in 1.2 that send bodies.
2256
            # graph.
3948.3.7 by Martin Pool
Updated tests for RemoteRepository.get_parent_map on old servers.
2257
            #
2258
            # Note that this reads the whole graph, when only some keys are
2259
            # wanted.  On this old server there's no way (?) to get them all
2260
            # in one go, and the user probably will have seen a warning about
2261
            # the server being old anyhow.
2262
            rg = self._get_revision_graph(None)
4031.3.3 by Matt Nordhoff
Review tweaks from Ben Finney
2263
            # There is an API discrepancy between get_parent_map and
3389.1.1 by John Arbash Meinel
Fix bug #214894. Fix RemoteRepository.get_parent_map() when server is <v1.2
2264
            # get_revision_graph. Specifically, a "key:()" pair in
2265
            # get_revision_graph just means a node has no parents. For
2266
            # "get_parent_map" it means the node is a ghost. So fix up the
2267
            # graph to correct this.
2268
            #   https://bugs.launchpad.net/bzr/+bug/214894
2269
            # There is one other "bug" which is that ghosts in
2270
            # get_revision_graph() are not returned at all. But we won't worry
2271
            # about that for now.
6656.1.1 by Martin
Apply 2to3 dict fixer and clean up resulting mess using view helpers
2272
            for node_id, parent_ids in viewitems(rg):
3389.1.1 by John Arbash Meinel
Fix bug #214894. Fix RemoteRepository.get_parent_map() when server is <v1.2
2273
                if parent_ids == ():
2274
                    rg[node_id] = (NULL_REVISION,)
2275
            rg[NULL_REVISION] = ()
2276
            return rg
3213.1.1 by Andrew Bennetts
Recover (by reconnecting) if the server turns out not to understand the new requests in 1.2 that send bodies.
2277
3172.5.6 by Robert Collins
Create new smart server verb Repository.get_parent_map.
2278
        keys = set(keys)
3373.5.2 by John Arbash Meinel
Add repository_implementation tests for get_parent_map
2279
        if None in keys:
2280
            raise ValueError('get_parent_map(None) is not valid')
3172.5.6 by Robert Collins
Create new smart server verb Repository.get_parent_map.
2281
        if NULL_REVISION in keys:
2282
            keys.discard(NULL_REVISION)
2283
            found_parents = {NULL_REVISION:()}
2284
            if not keys:
2285
                return found_parents
2286
        else:
2287
            found_parents = {}
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.
2288
        # TODO(Needs analysis): We could assume that the keys being requested
2289
        # from get_parent_map are in a breadth first search, so typically they
2290
        # will all be depth N from some common parent, and we don't have to
2291
        # have the server iterate from the root parent, but rather from the
2292
        # keys we're searching; and just tell the server the keyspace we
2293
        # already have; but this may be more traffic again.
2294
2295
        # Transform self._parents_map into a search request recipe.
2296
        # TODO: Manage this incrementally to avoid covering the same path
2297
        # repeatedly. (The server will have to on each request, but the less
2298
        # work done the better).
4190.1.3 by Robert Collins
Allow optional inclusion of ghost data in server get_parent_map calls.
2299
        #
2300
        # Negative caching notes:
2301
        # new server sends missing when a request including the revid
2302
        # 'include-missing:' is present in the request.
2303
        # missing keys are serialised as missing:X, and we then call
2304
        # provider.note_missing(X) for-all X
3835.1.8 by Aaron Bentley
Make UnstackedParentsProvider manage the cache
2305
        parents_map = self._unstacked_provider.get_cached_map()
3213.1.8 by Andrew Bennetts
Merge from bzr.dev.
2306
        if parents_map is None:
2307
            # Repository is not locked, so there's no cache.
2308
            parents_map = {}
6015.23.11 by John Arbash Meinel
allow a bit more flexibilty in how we walk the searches.
2309
        if _DEFAULT_SEARCH_DEPTH <= 0:
2310
            (start_set, stop_keys,
6341.1.4 by Jelmer Vernooij
Move more functionality to vf_search.
2311
             key_count) = vf_search.search_result_from_parent_map(
6015.23.11 by John Arbash Meinel
allow a bit more flexibilty in how we walk the searches.
2312
                parents_map, self._unstacked_provider.missing_keys)
2313
        else:
6015.23.8 by John Arbash Meinel
Play around with when to activate how much history searching.
2314
            (start_set, stop_keys,
6341.1.4 by Jelmer Vernooij
Move more functionality to vf_search.
2315
             key_count) = vf_search.limited_search_result_from_parent_map(
6015.23.8 by John Arbash Meinel
Play around with when to activate how much history searching.
2316
                parents_map, self._unstacked_provider.missing_keys,
6015.23.11 by John Arbash Meinel
allow a bit more flexibilty in how we walk the searches.
2317
                keys, depth=_DEFAULT_SEARCH_DEPTH)
6015.23.3 by John Arbash Meinel
Start refactoring code into graph.py code for easier testing.
2318
        recipe = ('manual', start_set, stop_keys, key_count)
3842.3.20 by Andrew Bennetts
Re-revert changes from another thread that accidentally got reinstated here.
2319
        body = self._serialise_search_recipe(recipe)
3172.5.6 by Robert Collins
Create new smart server verb Repository.get_parent_map.
2320
        path = self.bzrdir._path_for_remote_call(self._client)
2321
        for key in keys:
6619.3.18 by Jelmer Vernooij
Run 2to3 idioms fixer.
2322
            if not isinstance(key, str):
3360.2.8 by Martin Pool
Change assertion to a plain raise
2323
                raise ValueError(
2324
                    "key %r not a plain string" % (key,))
3172.5.8 by Robert Collins
Review feedback.
2325
        verb = 'Repository.get_parent_map'
4190.1.4 by Robert Collins
Cache ghosts when we can get them from a RemoteRepository in get_parent_map.
2326
        args = (path, 'include-missing:') + tuple(keys)
3297.3.3 by Andrew Bennetts
SmartClientRequestProtocol*.read_response_tuple can now raise UnknownSmartMethod. Callers no longer need to do their own ad hoc unknown smart method error detection.
2327
        try:
3786.2.3 by Andrew Bennetts
Remove duplicated 'call & translate errors' code in bzrlib.remote.
2328
            response = self._call_with_body_bytes_expecting_body(
3842.3.20 by Andrew Bennetts
Re-revert changes from another thread that accidentally got reinstated here.
2329
                verb, args, body)
3297.3.3 by Andrew Bennetts
SmartClientRequestProtocol*.read_response_tuple can now raise UnknownSmartMethod. Callers no longer need to do their own ad hoc unknown smart method error detection.
2330
        except errors.UnknownSmartMethod:
3213.1.2 by Andrew Bennetts
Add test for reconnection if get_parent_map is unknown by the server.
2331
            # Server does not support this method, so get the whole graph.
3213.1.1 by Andrew Bennetts
Recover (by reconnecting) if the server turns out not to understand the new requests in 1.2 that send bodies.
2332
            # Worse, we have to force a disconnection, because the server now
2333
            # doesn't realise it has a body on the wire to consume, so the
2334
            # only way to recover is to abandon the connection.
3213.1.6 by Andrew Bennetts
Emit warnings when forcing a reconnect.
2335
            warning(
2336
                'Server is too old for fast get_parent_map, reconnecting.  '
2337
                '(Upgrade the server to Bazaar 1.2 to avoid this)')
3213.1.1 by Andrew Bennetts
Recover (by reconnecting) if the server turns out not to understand the new requests in 1.2 that send bodies.
2338
            medium.disconnect()
2339
            # To avoid having to disconnect repeatedly, we keep track of the
2340
            # fact the server doesn't understand remote methods added in 1.2.
3453.4.9 by Andrew Bennetts
Rename _remote_is_not to _remember_remote_is_before.
2341
            medium._remember_remote_is_before((1, 2))
3948.3.7 by Martin Pool
Updated tests for RemoteRepository.get_parent_map on old servers.
2342
            # Recurse just once and we should use the fallback code.
2343
            return self._get_parent_map_rpc(keys)
3245.4.58 by Andrew Bennetts
Unpack call_expecting_body's return value into variables, to avoid lots of ugly subscripting.
2344
        response_tuple, response_handler = response
2345
        if response_tuple[0] not in ['ok']:
2346
            response_handler.cancel_read_body()
2347
            raise errors.UnexpectedSmartServerResponse(response_tuple)
2348
        if response_tuple[0] == 'ok':
2349
            coded = bz2.decompress(response_handler.read_body_bytes())
3172.5.6 by Robert Collins
Create new smart server verb Repository.get_parent_map.
2350
            if coded == '':
2351
                # no revisions found
2352
                return {}
2353
            lines = coded.split('\n')
2354
            revision_graph = {}
2355
            for line in lines:
2356
                d = tuple(line.split())
2357
                if len(d) > 1:
2358
                    revision_graph[d[0]] = d[1:]
2359
                else:
4190.1.4 by Robert Collins
Cache ghosts when we can get them from a RemoteRepository in get_parent_map.
2360
                    # No parents:
2361
                    if d[0].startswith('missing:'):
2362
                        revid = d[0][8:]
2363
                        self._unstacked_provider.note_missing_key(revid)
2364
                    else:
2365
                        # no parents - so give the Graph result
2366
                        # (NULL_REVISION,).
2367
                        revision_graph[d[0]] = (NULL_REVISION,)
3172.5.6 by Robert Collins
Create new smart server verb Repository.get_parent_map.
2368
            return revision_graph
2369
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
2370
    @needs_read_lock
2371
    def get_signature_text(self, revision_id):
6263.3.2 by Jelmer Vernooij
Add new HPSS call 'Repository.get_revision_signature_text'.
2372
        path = self.bzrdir._path_for_remote_call(self._client)
2373
        try:
2374
            response_tuple, response_handler = self._call_expecting_body(
2375
                'Repository.get_revision_signature_text', path, revision_id)
6263.3.5 by Jelmer Vernooij
Add support for fallback repositories.
2376
        except errors.UnknownSmartMethod:
2377
            self._ensure_real()
2378
            return self._real_repository.get_signature_text(revision_id)
6619.3.2 by Jelmer Vernooij
Apply 2to3 except fix.
2379
        except errors.NoSuchRevision as err:
6263.3.5 by Jelmer Vernooij
Add support for fallback repositories.
2380
            for fallback in self._fallback_repositories:
2381
                try:
2382
                    return fallback.get_signature_text(revision_id)
2383
                except errors.NoSuchRevision:
2384
                    pass
2385
            raise err
2386
        else:
6263.3.2 by Jelmer Vernooij
Add new HPSS call 'Repository.get_revision_signature_text'.
2387
            if response_tuple[0] != 'ok':
2388
                raise errors.UnexpectedSmartServerResponse(response_tuple)
2389
            return response_handler.read_body_bytes()
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
2390
2391
    @needs_read_lock
4988.5.1 by Jelmer Vernooij
Rename Repository.get_inventory_xml -> Repository._get_inventory_xml.
2392
    def _get_inventory_xml(self, revision_id):
6282.6.1 by Jelmer Vernooij
Add comment about Repository._get_inventory_xml being obsolete.
2393
        # This call is used by older working tree formats,
2394
        # which stored a serialized basis inventory.
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
2395
        self._ensure_real()
4988.5.1 by Jelmer Vernooij
Rename Repository.get_inventory_xml -> Repository._get_inventory_xml.
2396
        return self._real_repository._get_inventory_xml(revision_id)
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
2397
6300.1.7 by Jelmer Vernooij
Fix test.
2398
    @needs_write_lock
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
2399
    def reconcile(self, other=None, thorough=False):
6624 by Jelmer Vernooij
Merge Python3 porting work ('py3 pokes')
2400
        from .reconcile import RepoReconciler
6300.1.1 by Jelmer Vernooij
Add remote implementation of RemoteRepository.reconcile.
2401
        path = self.bzrdir._path_for_remote_call(self._client)
2402
        try:
6300.1.4 by Jelmer Vernooij
Add reconcile results.
2403
            response, handler = self._call_expecting_body(
6300.1.7 by Jelmer Vernooij
Fix test.
2404
                'Repository.reconcile', path, self._lock_token)
2405
        except (errors.UnknownSmartMethod, errors.TokenLockingNotSupported):
6300.1.1 by Jelmer Vernooij
Add remote implementation of RemoteRepository.reconcile.
2406
            self._ensure_real()
2407
            return self._real_repository.reconcile(other=other, thorough=thorough)
2408
        if response != ('ok', ):
2409
            raise errors.UnexpectedSmartServerResponse(response)
6300.1.4 by Jelmer Vernooij
Add reconcile results.
2410
        body = handler.read_body_bytes()
2411
        result = RepoReconciler(self)
2412
        for line in body.split('\n'):
2413
            if not line:
2414
                continue
2415
            key, val_text = line.split(':')
2416
            if key == "garbage_inventories":
2417
                result.garbage_inventories = int(val_text)
2418
            elif key == "inconsistent_parents":
2419
                result.inconsistent_parents = int(val_text)
2420
            else:
2421
                mutter("unknown reconcile key %r" % key)
2422
        return result
3943.8.1 by Marius Kruger
remove all trailing whitespace from bzr source
2423
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
2424
    def all_revision_ids(self):
6280.3.1 by Jelmer Vernooij
Add remote side of Repository.all_revision_ids.
2425
        path = self.bzrdir._path_for_remote_call(self._client)
2426
        try:
2427
            response_tuple, response_handler = self._call_expecting_body(
2428
                "Repository.all_revision_ids", path)
2429
        except errors.UnknownSmartMethod:
2430
            self._ensure_real()
2431
            return self._real_repository.all_revision_ids()
2432
        if response_tuple != ("ok", ):
2433
            raise errors.UnexpectedSmartServerResponse(response_tuple)
6280.3.3 by Jelmer Vernooij
Cope with fallback repositories.
2434
        revids = set(response_handler.read_body_bytes().splitlines())
2435
        for fallback in self._fallback_repositories:
2436
            revids.update(set(fallback.all_revision_ids()))
2437
        return list(revids)
3943.8.1 by Marius Kruger
remove all trailing whitespace from bzr source
2438
6282.6.16 by Jelmer Vernooij
More tests.
2439
    def _filtered_revision_trees(self, revision_ids, file_ids):
2440
        """Return Tree for a revision on this branch with only some files.
2441
2442
        :param revision_ids: a sequence of revision-ids;
2443
          a revision-id may not be None or 'null:'
2444
        :param file_ids: if not None, the result is filtered
2445
          so that only those file-ids, their parents and their
2446
          children are included.
2447
        """
2448
        inventories = self.iter_inventories(revision_ids)
2449
        for inv in inventories:
2450
            # Should we introduce a FilteredRevisionTree class rather
2451
            # than pre-filter the inventory here?
2452
            filtered_inv = inv.filter(file_ids)
2453
            yield InventoryRevisionTree(self, filtered_inv, filtered_inv.revision_id)
2454
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
2455
    @needs_read_lock
4137.3.2 by Ian Clatworthy
Repository.get_deltas_for_revisions() now supports file-id filtering
2456
    def get_deltas_for_revisions(self, revisions, specific_fileids=None):
6282.6.15 by Jelmer Vernooij
Fix verbose log.
2457
        medium = self._client._medium
2458
        if medium._is_remote_before((1, 2)):
2459
            self._ensure_real()
6282.6.16 by Jelmer Vernooij
More tests.
2460
            for delta in self._real_repository.get_deltas_for_revisions(
2461
                    revisions, specific_fileids):
2462
                yield delta
2463
            return
6282.6.15 by Jelmer Vernooij
Fix verbose log.
2464
        # Get the revision-ids of interest
2465
        required_trees = set()
2466
        for revision in revisions:
2467
            required_trees.add(revision.revision_id)
2468
            required_trees.update(revision.parent_ids[:1])
2469
2470
        # Get the matching filtered trees. Note that it's more
2471
        # efficient to pass filtered trees to changes_from() rather
2472
        # than doing the filtering afterwards. changes_from() could
2473
        # arguably do the filtering itself but it's path-based, not
2474
        # file-id based, so filtering before or afterwards is
2475
        # currently easier.
2476
        if specific_fileids is None:
2477
            trees = dict((t.get_revision_id(), t) for
2478
                t in self.revision_trees(required_trees))
2479
        else:
2480
            trees = dict((t.get_revision_id(), t) for
2481
                t in self._filtered_revision_trees(required_trees,
2482
                specific_fileids))
2483
2484
        # Calculate the deltas
2485
        for revision in revisions:
2486
            if not revision.parent_ids:
2487
                old_tree = self.revision_tree(_mod_revision.NULL_REVISION)
2488
            else:
2489
                old_tree = trees[revision.parent_ids[0]]
2490
            yield trees[revision.revision_id].changes_from(old_tree)
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
2491
2492
    @needs_read_lock
4137.3.2 by Ian Clatworthy
Repository.get_deltas_for_revisions() now supports file-id filtering
2493
    def get_revision_delta(self, revision_id, specific_fileids=None):
6267.1.2 by Jelmer Vernooij
Avoid _ensure_real in some more calls.
2494
        r = self.get_revision(revision_id)
2495
        return list(self.get_deltas_for_revisions([r],
2496
            specific_fileids=specific_fileids))[0]
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
2497
2498
    @needs_read_lock
2499
    def revision_trees(self, revision_ids):
6280.11.2 by Jelmer Vernooij
Implement RemoteRepository.revision_trees() using RemoteRepository.iter_inventories()
2500
        inventories = self.iter_inventories(revision_ids)
2501
        for inv in inventories:
2502
            yield InventoryRevisionTree(self, inv, inv.revision_id)
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
2503
2504
    @needs_read_lock
2505
    def get_revision_reconcile(self, revision_id):
2506
        self._ensure_real()
2507
        return self._real_repository.get_revision_reconcile(revision_id)
2508
2509
    @needs_read_lock
4332.3.35 by Robert Collins
Fix failing tests.
2510
    def check(self, revision_ids=None, callback_refs=None, check_repo=True):
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
2511
        self._ensure_real()
4332.3.11 by Robert Collins
Move tree and back callbacks into the repository check core.
2512
        return self._real_repository.check(revision_ids=revision_ids,
4332.3.35 by Robert Collins
Fix failing tests.
2513
            callback_refs=callback_refs, check_repo=check_repo)
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
2514
2018.5.138 by Robert Collins
Merge bzr.dev.
2515
    def copy_content_into(self, destination, revision_id=None):
6267.1.1 by Jelmer Vernooij
Avoid _ensure_real in a couple more places.
2516
        """Make a complete copy of the content in self into destination.
2517
2518
        This is a destructive operation! Do not use it on existing
2519
        repositories.
2520
        """
2521
        interrepo = _mod_repository.InterRepository.get(self, destination)
2522
        return interrepo.copy_content(revision_id)
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
2523
2814.10.2 by Andrew Bennetts
Make the fallback a little tidier.
2524
    def _copy_repository_tarball(self, to_bzrdir, revision_id=None):
2018.18.10 by Martin Pool
copy_content_into from Remote repositories by using temporary directories on both ends.
2525
        # get a tarball of the remote repository, and copy from that into the
2526
        # destination
2018.18.9 by Martin Pool
remote Repository.tarball builds a temporary directory and tars that
2527
        import tarfile
2018.18.20 by Martin Pool
Route branch operations through remote copy_content_into
2528
        # TODO: Maybe a progress bar while streaming the tarball?
6138.3.4 by Jonathan Riddell
add gettext() to uses of trace.note()
2529
        note(gettext("Copying repository content as tarball..."))
2018.18.25 by Martin Pool
Repository.tarball fixes for python2.4
2530
        tar_file = self._get_tarball('bz2')
2814.10.2 by Andrew Bennetts
Make the fallback a little tidier.
2531
        if tar_file is None:
2532
            return None
2533
        destination = to_bzrdir.create_repository()
2018.18.10 by Martin Pool
copy_content_into from Remote repositories by using temporary directories on both ends.
2534
        try:
2018.18.25 by Martin Pool
Repository.tarball fixes for python2.4
2535
            tar = tarfile.open('repository', fileobj=tar_file,
2536
                mode='r|bz2')
3638.3.2 by Vincent Ladeuil
Fix all calls to tempfile.mkdtemp to osutils.mkdtemp.
2537
            tmpdir = osutils.mkdtemp()
2018.18.25 by Martin Pool
Repository.tarball fixes for python2.4
2538
            try:
2539
                _extract_tar(tar, tmpdir)
5712.3.13 by Jelmer Vernooij
Add Prober.known_formats().
2540
                tmp_bzrdir = _mod_bzrdir.BzrDir.open(tmpdir)
2018.18.25 by Martin Pool
Repository.tarball fixes for python2.4
2541
                tmp_repo = tmp_bzrdir.open_repository()
2542
                tmp_repo.copy_content_into(destination, revision_id)
2543
            finally:
2544
                osutils.rmtree(tmpdir)
2018.18.10 by Martin Pool
copy_content_into from Remote repositories by using temporary directories on both ends.
2545
        finally:
2018.18.25 by Martin Pool
Repository.tarball fixes for python2.4
2546
            tar_file.close()
2814.10.2 by Andrew Bennetts
Make the fallback a little tidier.
2547
        return destination
2018.18.23 by Martin Pool
review cleanups
2548
        # TODO: Suggestion from john: using external tar is much faster than
2549
        # python's tarfile library, but it may not work on windows.
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
2550
3842.3.20 by Andrew Bennetts
Re-revert changes from another thread that accidentally got reinstated here.
2551
    @property
2552
    def inventories(self):
2553
        """Decorate the real repository for now.
2554
2555
        In the long term a full blown network facility is needed to
2556
        avoid creating a real repository object locally.
2557
        """
2558
        self._ensure_real()
2559
        return self._real_repository.inventories
2560
2604.2.1 by Robert Collins
(robertc) Introduce a pack command.
2561
    @needs_write_lock
5108.1.1 by Parth Malwankar
initial support for 'pack --clean-obsolete-packs'. tested only manually.
2562
    def pack(self, hint=None, clean_obsolete_packs=False):
2604.2.1 by Robert Collins
(robertc) Introduce a pack command.
2563
        """Compress the data within the repository.
2564
        """
6305.2.3 by Jelmer Vernooij
Store hint in body.
2565
        if hint is None:
2566
            body = ""
2567
        else:
2568
            body = "".join([l+"\n" for l in hint])
6305.2.1 by Jelmer Vernooij
add remote call for Repository.pack.
2569
        path = self.bzrdir._path_for_remote_call(self._client)
2570
        try:
6305.2.3 by Jelmer Vernooij
Store hint in body.
2571
            response, handler = self._call_with_body_bytes_expecting_body(
2572
                'Repository.pack', (path, self._lock_token,
6305.2.4 by Jelmer Vernooij
Fix tests.
2573
                    str(clean_obsolete_packs)), body)
6305.2.1 by Jelmer Vernooij
add remote call for Repository.pack.
2574
        except errors.UnknownSmartMethod:
2575
            self._ensure_real()
2576
            return self._real_repository.pack(hint=hint,
2577
                clean_obsolete_packs=clean_obsolete_packs)
6305.2.3 by Jelmer Vernooij
Store hint in body.
2578
        handler.cancel_read_body()
6305.2.1 by Jelmer Vernooij
add remote call for Repository.pack.
2579
        if response != ('ok', ):
2580
            raise errors.UnexpectedSmartServerResponse(response)
2604.2.1 by Robert Collins
(robertc) Introduce a pack command.
2581
3842.3.20 by Andrew Bennetts
Re-revert changes from another thread that accidentally got reinstated here.
2582
    @property
2583
    def revisions(self):
2584
        """Decorate the real repository for now.
2585
2586
        In the long term a full blown network facility is needed.
2587
        """
2588
        self._ensure_real()
2589
        return self._real_repository.revisions
2590
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
2591
    def set_make_working_trees(self, new_value):
4017.3.4 by Robert Collins
Create a verb for Repository.set_make_working_trees.
2592
        if new_value:
2593
            new_value_str = "True"
2594
        else:
2595
            new_value_str = "False"
2596
        path = self.bzrdir._path_for_remote_call(self._client)
2597
        try:
2598
            response = self._call(
2599
                'Repository.set_make_working_trees', path, new_value_str)
2600
        except errors.UnknownSmartMethod:
2601
            self._ensure_real()
2602
            self._real_repository.set_make_working_trees(new_value)
2603
        else:
2604
            if response[0] != 'ok':
2605
                raise errors.UnexpectedSmartServerResponse(response)
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
2606
3842.3.20 by Andrew Bennetts
Re-revert changes from another thread that accidentally got reinstated here.
2607
    @property
2608
    def signatures(self):
2609
        """Decorate the real repository for now.
2610
2611
        In the long term a full blown network facility is needed to avoid
2612
        creating a real repository object locally.
2613
        """
2614
        self._ensure_real()
2615
        return self._real_repository.signatures
2616
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
2617
    @needs_write_lock
2618
    def sign_revision(self, revision_id, gpg_strategy):
6280.8.1 by Jelmer Vernooij
Avoid _ensure_real in RemoteRepository.verify_revision_signature and RemoteRepository.sign_revision.
2619
        testament = _mod_testament.Testament.from_revision(self, revision_id)
2620
        plaintext = testament.as_short_text()
2621
        self.store_revision_signature(gpg_strategy, plaintext, revision_id)
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
2622
3842.3.20 by Andrew Bennetts
Re-revert changes from another thread that accidentally got reinstated here.
2623
    @property
2624
    def texts(self):
2625
        """Decorate the real repository for now.
2626
2627
        In the long term a full blown network facility is needed to avoid
2628
        creating a real repository object locally.
2629
        """
2630
        self._ensure_real()
2631
        return self._real_repository.texts
2632
6280.9.1 by Jelmer Vernooij
Add remote side of Repository.iter_revisions.
2633
    def _iter_revisions_rpc(self, revision_ids):
2634
        body = "\n".join(revision_ids)
2635
        path = self.bzrdir._path_for_remote_call(self._client)
2636
        response_tuple, response_handler = (
2637
            self._call_with_body_bytes_expecting_body(
2638
            "Repository.iter_revisions", (path, ), body))
2639
        if response_tuple[0] != "ok":
2640
            raise errors.UnexpectedSmartServerResponse(response_tuple)
2641
        serializer_format = response_tuple[1]
2642
        serializer = serializer_format_registry.get(serializer_format)
2643
        byte_stream = response_handler.read_streamed_body()
6280.9.4 by Jelmer Vernooij
use zlib instead.
2644
        decompressor = zlib.decompressobj()
6280.9.1 by Jelmer Vernooij
Add remote side of Repository.iter_revisions.
2645
        chunks = []
2646
        for bytes in byte_stream:
6280.9.4 by Jelmer Vernooij
use zlib instead.
2647
            chunks.append(decompressor.decompress(bytes))
6280.9.1 by Jelmer Vernooij
Add remote side of Repository.iter_revisions.
2648
            if decompressor.unused_data != "":
6280.9.4 by Jelmer Vernooij
use zlib instead.
2649
                chunks.append(decompressor.flush())
6280.9.1 by Jelmer Vernooij
Add remote side of Repository.iter_revisions.
2650
                yield serializer.read_revision_from_string("".join(chunks))
6280.9.4 by Jelmer Vernooij
use zlib instead.
2651
                unused = decompressor.unused_data
2652
                decompressor = zlib.decompressobj()
2653
                chunks = [decompressor.decompress(unused)]
2654
        chunks.append(decompressor.flush())
6280.9.1 by Jelmer Vernooij
Add remote side of Repository.iter_revisions.
2655
        text = "".join(chunks)
2656
        if text != "":
2657
            yield serializer.read_revision_from_string("".join(chunks))
2658
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
2659
    @needs_read_lock
2660
    def get_revisions(self, revision_ids):
6280.9.5 by Jelmer Vernooij
Cope with invalid arguments being specified to Repository.get_revisions.
2661
        if revision_ids is None:
2662
            revision_ids = self.all_revision_ids()
2663
        else:
2664
            for rev_id in revision_ids:
2665
                if not rev_id or not isinstance(rev_id, basestring):
2666
                    raise errors.InvalidRevisionId(
2667
                        revision_id=rev_id, branch=self)
6280.9.1 by Jelmer Vernooij
Add remote side of Repository.iter_revisions.
2668
        try:
6280.9.7 by Jelmer Vernooij
Fix compatibility code.
2669
            missing = set(revision_ids)
2670
            revs = {}
2671
            for rev in self._iter_revisions_rpc(revision_ids):
2672
                missing.remove(rev.revision_id)
2673
                revs[rev.revision_id] = rev
6280.9.1 by Jelmer Vernooij
Add remote side of Repository.iter_revisions.
2674
        except errors.UnknownSmartMethod:
2675
            self._ensure_real()
2676
            return self._real_repository.get_revisions(revision_ids)
2677
        for fallback in self._fallback_repositories:
2678
            if not missing:
2679
                break
2680
            for revid in list(missing):
2681
                # XXX JRV 2011-11-20: It would be nice if there was a
2682
                # public method on Repository that could be used to query
2683
                # for revision objects *without* failing completely if one
2684
                # was missing. There is VersionedFileRepository._iter_revisions,
2685
                # but unfortunately that's private and not provided by
2686
                # all repository implementations.
2687
                try:
2688
                    revs[revid] = fallback.get_revision(revid)
2689
                except errors.NoSuchRevision:
2690
                    pass
2691
                else:
2692
                    missing.remove(revid)
2693
        if missing:
2694
            raise errors.NoSuchRevision(self, list(missing)[0])
2695
        return [revs[revid] for revid in revision_ids]
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
2696
2697
    def supports_rich_root(self):
4053.1.4 by Robert Collins
Move the fetch control attributes from Repository to RepositoryFormat.
2698
        return self._format.rich_root_data
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
2699
2018.5.96 by Andrew Bennetts
Merge from bzr.dev, resolving the worst of the semantic conflicts, but there's
2700
    @property
2701
    def _serializer(self):
4053.1.4 by Robert Collins
Move the fetch control attributes from Repository to RepositoryFormat.
2702
        return self._format._serializer
2018.5.96 by Andrew Bennetts
Merge from bzr.dev, resolving the worst of the semantic conflicts, but there's
2703
6267.1.1 by Jelmer Vernooij
Avoid _ensure_real in a couple more places.
2704
    @needs_write_lock
2018.5.97 by Andrew Bennetts
Fix more tests.
2705
    def store_revision_signature(self, gpg_strategy, plaintext, revision_id):
6267.1.1 by Jelmer Vernooij
Avoid _ensure_real in a couple more places.
2706
        signature = gpg_strategy.sign(plaintext)
2707
        self.add_signature_text(revision_id, signature)
2018.5.97 by Andrew Bennetts
Fix more tests.
2708
2996.2.8 by Aaron Bentley
Fix add_signature discrepancies
2709
    def add_signature_text(self, revision_id, signature):
6268.1.10 by Jelmer Vernooij
Use real repository if it is already present.
2710
        if self._real_repository:
2711
            # If there is a real repository the write group will
2712
            # be in the real repository as well, so use that:
6268.1.2 by Jelmer Vernooij
Initial work on Repository.add_signature_text.
2713
            self._ensure_real()
2714
            return self._real_repository.add_signature_text(
2715
                revision_id, signature)
6268.1.10 by Jelmer Vernooij
Use real repository if it is already present.
2716
        path = self.bzrdir._path_for_remote_call(self._client)
6280.10.39 by Jelmer Vernooij
Merge bzr.dev.
2717
        response, handler = self._call_with_body_bytes_expecting_body(
6280.10.32 by Jelmer Vernooij
Merge bzr.dev.
2718
            'Repository.add_signature_text', (path, self._lock_token,
2719
                revision_id) + tuple(self._write_group_tokens), signature)
6280.10.39 by Jelmer Vernooij
Merge bzr.dev.
2720
        handler.cancel_read_body()
6268.1.2 by Jelmer Vernooij
Initial work on Repository.add_signature_text.
2721
        self.refresh_data()
2722
        if response[0] != 'ok':
2723
            raise errors.UnexpectedSmartServerResponse(response)
6280.10.36 by Jelmer Vernooij
Use new write group tokens.
2724
        self._write_group_tokens = response[1:]
2996.2.3 by Aaron Bentley
Add tests for install_revisions and add_signature
2725
2018.5.97 by Andrew Bennetts
Fix more tests.
2726
    def has_signature_for_revision_id(self, revision_id):
6265.1.1 by Jelmer Vernooij
Add new HPSS call ``Repository.has_signature_for_revision_id``.
2727
        path = self.bzrdir._path_for_remote_call(self._client)
2728
        try:
2729
            response = self._call('Repository.has_signature_for_revision_id',
2730
                path, revision_id)
2731
        except errors.UnknownSmartMethod:
2732
            self._ensure_real()
2733
            return self._real_repository.has_signature_for_revision_id(
2734
                revision_id)
2735
        if response[0] not in ('yes', 'no'):
2736
            raise SmartProtocolError('unexpected response code %s' % (response,))
6263.3.7 by Jelmer Vernooij
Fallback for RemoteRepository.has_signature_for_revision_id.
2737
        if response[0] == 'yes':
2738
            return True
2739
        for fallback in self._fallback_repositories:
2740
            if fallback.has_signature_for_revision_id(revision_id):
2741
                return True
2742
        return False
2018.5.97 by Andrew Bennetts
Fix more tests.
2743
6280.8.5 by Jelmer Vernooij
Add needs_read_lock for verify_revision_signature.
2744
    @needs_read_lock
6257.3.1 by Jelmer Vernooij
Support verifying remote signatures.
2745
    def verify_revision_signature(self, revision_id, gpg_strategy):
6280.8.1 by Jelmer Vernooij
Avoid _ensure_real in RemoteRepository.verify_revision_signature and RemoteRepository.sign_revision.
2746
        if not self.has_signature_for_revision_id(revision_id):
2747
            return gpg.SIGNATURE_NOT_SIGNED, None
2748
        signature = self.get_signature_text(revision_id)
2749
2750
        testament = _mod_testament.Testament.from_revision(self, revision_id)
2751
        plaintext = testament.as_short_text()
2752
2753
        return gpg_strategy.verify(signature, plaintext)
6257.3.1 by Jelmer Vernooij
Support verifying remote signatures.
2754
2535.3.45 by Andrew Bennetts
Add item_keys_introduced_by to RemoteRepository.
2755
    def item_keys_introduced_by(self, revision_ids, _files_pb=None):
2756
        self._ensure_real()
2757
        return self._real_repository.item_keys_introduced_by(revision_ids,
2758
            _files_pb=_files_pb)
2759
4332.3.34 by Robert Collins
Delete obsolete pack tuned find_inconsistent_revisions as the generic code path permits the same optimisation.
2760
    def _find_inconsistent_revision_parents(self, revisions_iterator=None):
2819.2.5 by Andrew Bennetts
Make reconcile abort gracefully if the revision index has bad parents.
2761
        self._ensure_real()
4332.3.34 by Robert Collins
Delete obsolete pack tuned find_inconsistent_revisions as the generic code path permits the same optimisation.
2762
        return self._real_repository._find_inconsistent_revision_parents(
2763
            revisions_iterator)
2819.2.5 by Andrew Bennetts
Make reconcile abort gracefully if the revision index has bad parents.
2764
2765
    def _check_for_inconsistent_revision_parents(self):
2766
        self._ensure_real()
2767
        return self._real_repository._check_for_inconsistent_revision_parents()
2768
3835.1.17 by Aaron Bentley
Fix stacking bug
2769
    def _make_parents_provider(self, other=None):
3835.1.8 by Aaron Bentley
Make UnstackedParentsProvider manage the cache
2770
        providers = [self._unstacked_provider]
3835.1.17 by Aaron Bentley
Fix stacking bug
2771
        if other is not None:
2772
            providers.insert(0, other)
5816.8.3 by Andrew Bennetts
Add test for calling add_fallback_repository after _make_parents_provider, and make it work.
2773
        return graph.StackedParentsProvider(_LazyListJoin(
2774
            providers, self._fallback_repositories))
3172.5.1 by Robert Collins
Create a RemoteRepository get_graph implementation and delegate get_parents_map to the real repository.
2775
3842.3.20 by Andrew Bennetts
Re-revert changes from another thread that accidentally got reinstated here.
2776
    def _serialise_search_recipe(self, recipe):
2777
        """Serialise a graph search recipe.
2778
2779
        :param recipe: A search recipe (start, stop, count).
2780
        :return: Serialised bytes.
2781
        """
4152.1.2 by Robert Collins
Add streaming from a stacked branch when the sort order is compatible with doing so.
2782
        start_keys = ' '.join(recipe[1])
2783
        stop_keys = ' '.join(recipe[2])
2784
        count = str(recipe[3])
3842.3.20 by Andrew Bennetts
Re-revert changes from another thread that accidentally got reinstated here.
2785
        return '\n'.join((start_keys, stop_keys, count))
2786
4070.9.5 by Andrew Bennetts
Better wire protocol: don't shoehorn MiniSearchResult serialisation into previous serialisation format.
2787
    def _serialise_search_result(self, search_result):
5539.2.2 by Andrew Bennetts
Add support for 'everything' fetch spec to RemoteStreamSource.
2788
        parts = search_result.get_network_struct()
4070.9.5 by Andrew Bennetts
Better wire protocol: don't shoehorn MiniSearchResult serialisation into previous serialisation format.
2789
        return '\n'.join(parts)
2790
3842.3.2 by Andrew Bennetts
Revert the RemoteVersionedFiles.get_parent_map implementation, leaving just the skeleton of RemoteVersionedFiles.
2791
    def autopack(self):
2792
        path = self.bzrdir._path_for_remote_call(self._client)
2793
        try:
2794
            response = self._call('PackRepository.autopack', path)
2795
        except errors.UnknownSmartMethod:
2796
            self._ensure_real()
2797
            self._real_repository._pack_collection.autopack()
2798
            return
4145.1.2 by Robert Collins
Add a refresh_data method on Repository allowing cleaner handling of insertions into RemoteRepository objects with _real_repository instances.
2799
        self.refresh_data()
3842.3.2 by Andrew Bennetts
Revert the RemoteVersionedFiles.get_parent_map implementation, leaving just the skeleton of RemoteVersionedFiles.
2800
        if response[0] != 'ok':
2801
            raise errors.UnexpectedSmartServerResponse(response)
2802
2803
5815.4.1 by Jelmer Vernooij
Split versionedfile-specific stuff out into VersionedFileRepository.
2804
class RemoteStreamSink(vf_repository.StreamSink):
4022.1.6 by Robert Collins
Cherrypick and polish the RemoteSink for streaming push.
2805
4032.3.7 by Robert Collins
Move write locking and write group responsibilities into the Sink objects themselves, allowing complete avoidance of unnecessary calls when the sink is a RemoteSink.
2806
    def _insert_real(self, stream, src_format, resume_tokens):
4022.1.6 by Robert Collins
Cherrypick and polish the RemoteSink for streaming push.
2807
        self.target_repo._ensure_real()
2808
        sink = self.target_repo._real_repository._get_sink()
4032.3.7 by Robert Collins
Move write locking and write group responsibilities into the Sink objects themselves, allowing complete avoidance of unnecessary calls when the sink is a RemoteSink.
2809
        result = sink.insert_stream(stream, src_format, resume_tokens)
4029.2.1 by Robert Collins
Support streaming push to stacked branches.
2810
        if not result:
2811
            self.target_repo.autopack()
2812
        return result
4022.1.6 by Robert Collins
Cherrypick and polish the RemoteSink for streaming push.
2813
4032.3.7 by Robert Collins
Move write locking and write group responsibilities into the Sink objects themselves, allowing complete avoidance of unnecessary calls when the sink is a RemoteSink.
2814
    def insert_stream(self, stream, src_format, resume_tokens):
4144.3.2 by Andrew Bennetts
Use Repository.insert_stream_locked if there is a lock_token for the remote repo.
2815
        target = self.target_repo
4307.2.4 by Robert Collins
Enable caching of negative revision lookups in RemoteRepository write locks when no _real_repository has been constructed.
2816
        target._unstacked_provider.missing_keys.clear()
4476.3.82 by Andrew Bennetts
Mention another bug fix in NEWS, and update verb name, comments, and NEWS additions for landing on 1.19 rather than 1.18.
2817
        candidate_calls = [('Repository.insert_stream_1.19', (1, 19))]
4144.3.2 by Andrew Bennetts
Use Repository.insert_stream_locked if there is a lock_token for the remote repo.
2818
        if target._lock_token:
4476.3.15 by Andrew Bennetts
Partially working fallback for pre-1.17 servers.
2819
            candidate_calls.append(('Repository.insert_stream_locked', (1, 14)))
2820
            lock_args = (target._lock_token or '',)
4144.3.2 by Andrew Bennetts
Use Repository.insert_stream_locked if there is a lock_token for the remote repo.
2821
        else:
4476.3.15 by Andrew Bennetts
Partially working fallback for pre-1.17 servers.
2822
            candidate_calls.append(('Repository.insert_stream', (1, 13)))
2823
            lock_args = ()
4144.3.2 by Andrew Bennetts
Use Repository.insert_stream_locked if there is a lock_token for the remote repo.
2824
        client = target._client
4022.1.9 by Robert Collins
Fix critical issue in bzr.dev - pushing to an old bzr:// server fails because the stream being consumed before the fallback code occurs, which makes it fail to do the fetch. (Robert Collins, Andrew Bennetts, #332314)
2825
        medium = client._medium
4144.3.2 by Andrew Bennetts
Use Repository.insert_stream_locked if there is a lock_token for the remote repo.
2826
        path = target.bzrdir._path_for_remote_call(client)
4476.3.70 by Andrew Bennetts
Review tweaks.
2827
        # Probe for the verb to use with an empty stream before sending the
2828
        # real stream to it.  We do this both to avoid the risk of sending a
2829
        # large request that is then rejected, and because we don't want to
2830
        # implement a way to buffer, rewind, or restart the stream.
4476.3.15 by Andrew Bennetts
Partially working fallback for pre-1.17 servers.
2831
        found_verb = False
2832
        for verb, required_version in candidate_calls:
2833
            if medium._is_remote_before(required_version):
2834
                continue
4476.3.25 by Andrew Bennetts
Reinstate don't-reprobe-with-resume-tokens optimisation, fixing acceptance test.
2835
            if resume_tokens:
2836
                # We've already done the probing (and set _is_remote_before) on
2837
                # a previous insert.
2838
                found_verb = True
2839
                break
4060.1.4 by Robert Collins
Streaming fetch from remote servers.
2840
            byte_stream = smart_repo._stream_to_byte_stream([], src_format)
4029.2.1 by Robert Collins
Support streaming push to stacked branches.
2841
            try:
2842
                response = client.call_with_body_stream(
4476.3.15 by Andrew Bennetts
Partially working fallback for pre-1.17 servers.
2843
                    (verb, path, '') + lock_args, byte_stream)
4029.2.1 by Robert Collins
Support streaming push to stacked branches.
2844
            except errors.UnknownSmartMethod:
4144.3.2 by Andrew Bennetts
Use Repository.insert_stream_locked if there is a lock_token for the remote repo.
2845
                medium._remember_remote_is_before(required_version)
4476.3.15 by Andrew Bennetts
Partially working fallback for pre-1.17 servers.
2846
            else:
2847
                found_verb = True
2848
                break
2849
        if not found_verb:
2850
            # Have to use VFS.
2851
            return self._insert_real(stream, src_format, resume_tokens)
2852
        self._last_inv_record = None
2853
        self._last_substream = None
4476.3.82 by Andrew Bennetts
Mention another bug fix in NEWS, and update verb name, comments, and NEWS additions for landing on 1.19 rather than 1.18.
2854
        if required_version < (1, 19):
4476.3.35 by Andrew Bennetts
Expand comment.
2855
            # Remote side doesn't support inventory deltas.  Wrap the stream to
2856
            # make sure we don't send any.  If the stream contains inventory
2857
            # deltas we'll interrupt the smart insert_stream request and
2858
            # fallback to VFS.
4476.3.15 by Andrew Bennetts
Partially working fallback for pre-1.17 servers.
2859
            stream = self._stop_stream_if_inventory_delta(stream)
4060.1.4 by Robert Collins
Streaming fetch from remote servers.
2860
        byte_stream = smart_repo._stream_to_byte_stream(
2861
            stream, src_format)
4032.3.7 by Robert Collins
Move write locking and write group responsibilities into the Sink objects themselves, allowing complete avoidance of unnecessary calls when the sink is a RemoteSink.
2862
        resume_tokens = ' '.join(resume_tokens)
4022.1.9 by Robert Collins
Fix critical issue in bzr.dev - pushing to an old bzr:// server fails because the stream being consumed before the fallback code occurs, which makes it fail to do the fetch. (Robert Collins, Andrew Bennetts, #332314)
2863
        response = client.call_with_body_stream(
4476.3.15 by Andrew Bennetts
Partially working fallback for pre-1.17 servers.
2864
            (verb, path, resume_tokens) + lock_args, byte_stream)
4029.2.1 by Robert Collins
Support streaming push to stacked branches.
2865
        if response[0][0] not in ('ok', 'missing-basis'):
4022.1.9 by Robert Collins
Fix critical issue in bzr.dev - pushing to an old bzr:// server fails because the stream being consumed before the fallback code occurs, which makes it fail to do the fetch. (Robert Collins, Andrew Bennetts, #332314)
2866
            raise errors.UnexpectedSmartServerResponse(response)
4476.3.54 by Andrew Bennetts
Update fallback-to-VFS in remote.py for the inventory-deltas substream.
2867
        if self._last_substream is not None:
4476.3.21 by Andrew Bennetts
Clarify some code and comments, and s/1.17/1.18/ in a few places.
2868
            # The stream included an inventory-delta record, but the remote
2869
            # side isn't new enough to support them.  So we need to send the
2870
            # rest of the stream via VFS.
4634.35.15 by Andrew Bennetts
Fix 'fallback to vfs if RPC does not support inventory-deltas' case to refresh the vfs pack names before starting the fallback.
2871
            self.target_repo.refresh_data()
4476.3.21 by Andrew Bennetts
Clarify some code and comments, and s/1.17/1.18/ in a few places.
2872
            return self._resume_stream_with_vfs(response, src_format)
4029.2.1 by Robert Collins
Support streaming push to stacked branches.
2873
        if response[0][0] == 'missing-basis':
2874
            tokens, missing_keys = bencode.bdecode_as_tuple(response[0][1])
4032.3.7 by Robert Collins
Move write locking and write group responsibilities into the Sink objects themselves, allowing complete avoidance of unnecessary calls when the sink is a RemoteSink.
2875
            resume_tokens = tokens
4257.3.3 by Andrew Bennetts
missing_keys from sink.insert_stream should be a set, not a tuple.
2876
            return resume_tokens, set(missing_keys)
4029.2.1 by Robert Collins
Support streaming push to stacked branches.
2877
        else:
4145.1.2 by Robert Collins
Add a refresh_data method on Repository allowing cleaner handling of insertions into RemoteRepository objects with _real_repository instances.
2878
            self.target_repo.refresh_data()
4032.3.7 by Robert Collins
Move write locking and write group responsibilities into the Sink objects themselves, allowing complete avoidance of unnecessary calls when the sink is a RemoteSink.
2879
            return [], set()
4032.1.1 by John Arbash Meinel
Merge the removal of all trailing whitespace, and resolve conflicts.
2880
4476.3.21 by Andrew Bennetts
Clarify some code and comments, and s/1.17/1.18/ in a few places.
2881
    def _resume_stream_with_vfs(self, response, src_format):
2882
        """Resume sending a stream via VFS, first resending the record and
2883
        substream that couldn't be sent via an insert_stream verb.
2884
        """
4476.3.15 by Andrew Bennetts
Partially working fallback for pre-1.17 servers.
2885
        if response[0][0] == 'missing-basis':
2886
            tokens, missing_keys = bencode.bdecode_as_tuple(response[0][1])
2887
            # Ignore missing_keys, we haven't finished inserting yet
2888
        else:
2889
            tokens = []
4476.3.21 by Andrew Bennetts
Clarify some code and comments, and s/1.17/1.18/ in a few places.
2890
        def resume_substream():
4476.3.54 by Andrew Bennetts
Update fallback-to-VFS in remote.py for the inventory-deltas substream.
2891
            # Yield the substream that was interrupted.
4476.3.21 by Andrew Bennetts
Clarify some code and comments, and s/1.17/1.18/ in a few places.
2892
            for record in self._last_substream:
2893
                yield record
2894
            self._last_substream = None
4476.3.15 by Andrew Bennetts
Partially working fallback for pre-1.17 servers.
2895
        def resume_stream():
4476.3.21 by Andrew Bennetts
Clarify some code and comments, and s/1.17/1.18/ in a few places.
2896
            # Finish sending the interrupted substream
4476.3.54 by Andrew Bennetts
Update fallback-to-VFS in remote.py for the inventory-deltas substream.
2897
            yield ('inventory-deltas', resume_substream())
4476.3.21 by Andrew Bennetts
Clarify some code and comments, and s/1.17/1.18/ in a few places.
2898
            # Then simply continue sending the rest of the stream.
4476.3.15 by Andrew Bennetts
Partially working fallback for pre-1.17 servers.
2899
            for substream_kind, substream in self._last_stream:
2900
                yield substream_kind, substream
2901
        return self._insert_real(resume_stream(), src_format, tokens)
2902
2903
    def _stop_stream_if_inventory_delta(self, stream):
4476.3.21 by Andrew Bennetts
Clarify some code and comments, and s/1.17/1.18/ in a few places.
2904
        """Normally this just lets the original stream pass-through unchanged.
2905
4476.3.54 by Andrew Bennetts
Update fallback-to-VFS in remote.py for the inventory-deltas substream.
2906
        However if any 'inventory-deltas' substream occurs it will stop
2907
        streaming, and store the interrupted substream and stream in
2908
        self._last_substream and self._last_stream so that the stream can be
2909
        resumed by _resume_stream_with_vfs.
4476.3.21 by Andrew Bennetts
Clarify some code and comments, and s/1.17/1.18/ in a few places.
2910
        """
5712.3.13 by Jelmer Vernooij
Add Prober.known_formats().
2911
4476.3.15 by Andrew Bennetts
Partially working fallback for pre-1.17 servers.
2912
        stream_iter = iter(stream)
2913
        for substream_kind, substream in stream_iter:
4476.3.54 by Andrew Bennetts
Update fallback-to-VFS in remote.py for the inventory-deltas substream.
2914
            if substream_kind == 'inventory-deltas':
2915
                self._last_substream = substream
2916
                self._last_stream = stream_iter
2917
                return
4476.3.15 by Andrew Bennetts
Partially working fallback for pre-1.17 servers.
2918
            else:
2919
                yield substream_kind, substream
5712.3.13 by Jelmer Vernooij
Add Prober.known_formats().
2920
2921
5815.4.1 by Jelmer Vernooij
Split versionedfile-specific stuff out into VersionedFileRepository.
2922
class RemoteStreamSource(vf_repository.StreamSource):
4060.1.3 by Robert Collins
Implement the separate source component for fetch - repository.StreamSource.
2923
    """Stream data from a remote server."""
2924
4060.1.4 by Robert Collins
Streaming fetch from remote servers.
2925
    def get_stream(self, search):
4152.1.2 by Robert Collins
Add streaming from a stacked branch when the sort order is compatible with doing so.
2926
        if (self.from_repository._fallback_repositories and
2927
            self.to_format._fetch_order == 'topological'):
2928
            return self._real_stream(self.from_repository, search)
4577.1.1 by Robert Collins
Fix fetching from smart servers where there is a chain of stacked repositories rather than a single stacking point. (Robert Collins, bug #406597)
2929
        sources = []
2930
        seen = set()
2931
        repos = [self.from_repository]
2932
        while repos:
2933
            repo = repos.pop(0)
2934
            if repo in seen:
2935
                continue
2936
            seen.add(repo)
2937
            repos.extend(repo._fallback_repositories)
2938
            sources.append(repo)
2939
        return self.missing_parents_chain(search, sources)
4152.1.2 by Robert Collins
Add streaming from a stacked branch when the sort order is compatible with doing so.
2940
4476.3.16 by Andrew Bennetts
Only make inv deltas against bases we've already sent, and other tweaks.
2941
    def get_stream_for_missing_keys(self, missing_keys):
2942
        self.from_repository._ensure_real()
2943
        real_repo = self.from_repository._real_repository
2944
        real_source = real_repo._get_source(self.to_format)
2945
        return real_source.get_stream_for_missing_keys(missing_keys)
2946
4152.1.2 by Robert Collins
Add streaming from a stacked branch when the sort order is compatible with doing so.
2947
    def _real_stream(self, repo, search):
2948
        """Get a stream for search from repo.
6263.3.1 by Jelmer Vernooij
Some formatting fixes.
2949
2950
        This never called RemoteStreamSource.get_stream, and is a helper
2951
        for RemoteStreamSource._get_stream to allow getting a stream
4152.1.2 by Robert Collins
Add streaming from a stacked branch when the sort order is compatible with doing so.
2952
        reliably whether fallback back because of old servers or trying
2953
        to stream from a non-RemoteRepository (which the stacked support
2954
        code will do).
2955
        """
2956
        source = repo._get_source(self.to_format)
2957
        if isinstance(source, RemoteStreamSource):
4600.1.1 by Robert Collins
Fix fetching from 2a branches over bzr-v2.
2958
            repo._ensure_real()
2959
            source = repo._real_repository._get_source(self.to_format)
4152.1.2 by Robert Collins
Add streaming from a stacked branch when the sort order is compatible with doing so.
2960
        return source.get_stream(search)
2961
2962
    def _get_stream(self, repo, search):
2963
        """Core worker to get a stream from repo for search.
2964
2965
        This is used by both get_stream and the stacking support logic. It
2966
        deliberately gets a stream for repo which does not need to be
2967
        self.from_repository. In the event that repo is not Remote, or
2968
        cannot do a smart stream, a fallback is made to the generic
2969
        repository._get_stream() interface, via self._real_stream.
2970
2971
        In the event of stacking, streams from _get_stream will not
2972
        contain all the data for search - this is normal (see get_stream).
2973
2974
        :param repo: A repository.
2975
        :param search: A search.
2976
        """
2977
        # Fallbacks may be non-smart
2978
        if not isinstance(repo, RemoteRepository):
2979
            return self._real_stream(repo, search)
4060.1.4 by Robert Collins
Streaming fetch from remote servers.
2980
        client = repo._client
2981
        medium = client._medium
2982
        path = repo.bzrdir._path_for_remote_call(client)
4476.3.29 by Andrew Bennetts
Add Repository.get_stream_1.18 verb.
2983
        search_bytes = repo._serialise_search_result(search)
2984
        args = (path, self.to_format.network_name())
2985
        candidate_verbs = [
4476.3.82 by Andrew Bennetts
Mention another bug fix in NEWS, and update verb name, comments, and NEWS additions for landing on 1.19 rather than 1.18.
2986
            ('Repository.get_stream_1.19', (1, 19)),
4476.3.29 by Andrew Bennetts
Add Repository.get_stream_1.18 verb.
2987
            ('Repository.get_stream', (1, 13))]
5539.2.2 by Andrew Bennetts
Add support for 'everything' fetch spec to RemoteStreamSource.
2988
4476.3.29 by Andrew Bennetts
Add Repository.get_stream_1.18 verb.
2989
        found_verb = False
2990
        for verb, version in candidate_verbs:
2991
            if medium._is_remote_before(version):
2992
                continue
2993
            try:
2994
                response = repo._call_with_body_bytes_expecting_body(
2995
                    verb, args, search_bytes)
2996
            except errors.UnknownSmartMethod:
2997
                medium._remember_remote_is_before(version)
6619.3.2 by Jelmer Vernooij
Apply 2to3 except fix.
2998
            except errors.UnknownErrorFromSmartServer as e:
6341.1.4 by Jelmer Vernooij
Move more functionality to vf_search.
2999
                if isinstance(search, vf_search.EverythingResult):
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.
3000
                    error_verb = e.error_from_smart_server.error_verb
3001
                    if error_verb == 'BadSearch':
5536.3.3 by Andrew Bennetts
Merge lp:bzr.
3002
                        # Pre-2.4 servers don't support this sort of search.
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.
3003
                        # XXX: perhaps falling back to VFS on BadSearch is a
3004
                        # good idea in general?  It might provide a little bit
3005
                        # of protection against client-side bugs.
5536.3.3 by Andrew Bennetts
Merge lp:bzr.
3006
                        medium._remember_remote_is_before((2, 4))
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.
3007
                        break
3008
                raise
4476.3.29 by Andrew Bennetts
Add Repository.get_stream_1.18 verb.
3009
            else:
3010
                response_tuple, response_handler = response
3011
                found_verb = True
3012
                break
3013
        if not found_verb:
4152.1.2 by Robert Collins
Add streaming from a stacked branch when the sort order is compatible with doing so.
3014
            return self._real_stream(repo, search)
4060.1.4 by Robert Collins
Streaming fetch from remote servers.
3015
        if response_tuple[0] != 'ok':
3016
            raise errors.UnexpectedSmartServerResponse(response_tuple)
3017
        byte_stream = response_handler.read_streamed_body()
5195.3.23 by Parth Malwankar
moved progress bar logic to SourceStream.
3018
        src_format, stream = smart_repo._byte_stream_to_stream(byte_stream,
3019
            self._record_counter)
4060.1.4 by Robert Collins
Streaming fetch from remote servers.
3020
        if src_format.network_name() != repo._format.network_name():
3021
            raise AssertionError(
3022
                "Mismatched RemoteRepository and stream src %r, %r" % (
3023
                src_format.network_name(), repo._format.network_name()))
3024
        return stream
3025
4152.1.2 by Robert Collins
Add streaming from a stacked branch when the sort order is compatible with doing so.
3026
    def missing_parents_chain(self, search, sources):
3027
        """Chain multiple streams together to handle stacking.
3028
3029
        :param search: The overall search to satisfy with streams.
3030
        :param sources: A list of Repository objects to query.
3031
        """
4634.61.2 by Andrew Bennetts
Variable rename suggested by Robert.
3032
        self.from_serialiser = self.from_repository._format._serializer
4152.1.2 by Robert Collins
Add streaming from a stacked branch when the sort order is compatible with doing so.
3033
        self.seen_revs = set()
3034
        self.referenced_revs = set()
3035
        # If there are heads in the search, or the key count is > 0, we are not
3036
        # done.
3037
        while not search.is_empty() and len(sources) > 1:
3038
            source = sources.pop(0)
3039
            stream = self._get_stream(source, search)
3040
            for kind, substream in stream:
3041
                if kind != 'revisions':
3042
                    yield kind, substream
3043
                else:
3044
                    yield kind, self.missing_parents_rev_handler(substream)
3045
            search = search.refine(self.seen_revs, self.referenced_revs)
3046
            self.seen_revs = set()
3047
            self.referenced_revs = set()
3048
        if not search.is_empty():
3049
            for kind, stream in self._get_stream(sources[0], search):
3050
                yield kind, stream
3051
3052
    def missing_parents_rev_handler(self, substream):
3053
        for content in substream:
3054
            revision_bytes = content.get_bytes_as('fulltext')
4634.61.2 by Andrew Bennetts
Variable rename suggested by Robert.
3055
            revision = self.from_serialiser.read_revision_from_string(
3056
                revision_bytes)
4152.1.2 by Robert Collins
Add streaming from a stacked branch when the sort order is compatible with doing so.
3057
            self.seen_revs.add(content.key[-1])
3058
            self.referenced_revs.update(revision.parent_ids)
3059
            yield content
3060
4060.1.3 by Robert Collins
Implement the separate source component for fetch - repository.StreamSource.
3061
2018.5.127 by Andrew Bennetts
Fix most of the lockable_files tests for RemoteBranchLockableFiles.
3062
class RemoteBranchLockableFiles(LockableFiles):
2018.5.59 by Robert Collins
Get BranchConfig working somewhat on RemoteBranches (Robert Collins, Vincent Ladeuil).
3063
    """A 'LockableFiles' implementation that talks to a smart server.
3943.8.1 by Marius Kruger
remove all trailing whitespace from bzr source
3064
2018.5.59 by Robert Collins
Get BranchConfig working somewhat on RemoteBranches (Robert Collins, Vincent Ladeuil).
3065
    This is not a public interface class.
3066
    """
3067
3068
    def __init__(self, bzrdir, _client):
3069
        self.bzrdir = bzrdir
3070
        self._client = _client
2018.5.135 by Andrew Bennetts
Prevent remote branch clients from determining the 'right' mode for control files, because we don't want clients setting the mode anyway.
3071
        self._need_find_modes = True
2018.5.133 by Andrew Bennetts
All TestLockableFiles_RemoteLockDir tests passing.
3072
        LockableFiles.__init__(
2018.5.163 by Andrew Bennetts
Deal with various review comments from Robert.
3073
            self, bzrdir.get_branch_transport(None),
2018.5.133 by Andrew Bennetts
All TestLockableFiles_RemoteLockDir tests passing.
3074
            'lock', lockdir.LockDir)
2018.5.59 by Robert Collins
Get BranchConfig working somewhat on RemoteBranches (Robert Collins, Vincent Ladeuil).
3075
2018.5.135 by Andrew Bennetts
Prevent remote branch clients from determining the 'right' mode for control files, because we don't want clients setting the mode anyway.
3076
    def _find_modes(self):
3077
        # RemoteBranches don't let the client set the mode of control files.
3078
        self._dir_mode = None
3079
        self._file_mode = None
3080
2018.5.59 by Robert Collins
Get BranchConfig working somewhat on RemoteBranches (Robert Collins, Vincent Ladeuil).
3081
1752.2.31 by Martin Pool
[broken] some support for write operations over hpss
3082
class RemoteBranchFormat(branch.BranchFormat):
3083
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.
3084
    def __init__(self, network_name=None):
3834.5.2 by John Arbash Meinel
Track down the various BranchFormats that weren't setting the branch format as part of the _matchingbzrdir format.
3085
        super(RemoteBranchFormat, self).__init__()
3086
        self._matchingbzrdir = RemoteBzrDirFormat()
3087
        self._matchingbzrdir.set_branch_format(self)
4032.3.2 by Robert Collins
Create and use a RPC call to create branches on bzr servers rather than using VFS calls.
3088
        self._custom_format = None
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.
3089
        self._network_name = network_name
3834.5.2 by John Arbash Meinel
Track down the various BranchFormats that weren't setting the branch format as part of the _matchingbzrdir format.
3090
2018.5.124 by Robert Collins
Fix test_format_initialize_find_open by delegating Branch formt lookup to the BzrDir, where it should have stayed from the start.
3091
    def __eq__(self, other):
3943.8.1 by Marius Kruger
remove all trailing whitespace from bzr source
3092
        return (isinstance(other, RemoteBranchFormat) and
2018.5.124 by Robert Collins
Fix test_format_initialize_find_open by delegating Branch formt lookup to the BzrDir, where it should have stayed from the start.
3093
            self.__dict__ == other.__dict__)
3094
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.
3095
    def _ensure_real(self):
3096
        if self._custom_format is None:
6305.4.1 by Jelmer Vernooij
Print sensible error message when remote format is unknown.
3097
            try:
3098
                self._custom_format = branch.network_format_registry.get(
3099
                    self._network_name)
3100
            except KeyError:
3101
                raise errors.UnknownFormatError(kind='branch',
3102
                    format=self._network_name)
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.
3103
2018.5.60 by Robert Collins
More missing methods from RemoteBranch and RemoteRepository to let 'info' get further.
3104
    def get_format_description(self):
4792.1.1 by Andrew Bennetts
Show real branch/repo format description in 'info -v' over HPSS.
3105
        self._ensure_real()
3106
        return 'Remote: ' + self._custom_format.get_format_description()
2018.5.60 by Robert Collins
More missing methods from RemoteBranch and RemoteRepository to let 'info' get further.
3107
4032.3.1 by Robert Collins
Add a BranchFormat.network_name() method as preparation for creating branches via RPC calls.
3108
    def network_name(self):
3109
        return self._network_name
3110
5051.3.10 by Jelmer Vernooij
Pass colocated branch name around in more places.
3111
    def open(self, a_bzrdir, name=None, ignore_fallbacks=False):
3112
        return a_bzrdir.open_branch(name=name, 
3113
            ignore_fallbacks=ignore_fallbacks)
1752.2.52 by Andrew Bennetts
Flesh out more Remote* methods needed to open and initialise remote branches/trees/repositories.
3114
6437.71.1 by John Arbash Meinel
One of the discoveries from fixing bug #1046697.
3115
    def _vfs_initialize(self, a_bzrdir, name, append_revisions_only,
3116
                        repository=None):
4032.3.2 by Robert Collins
Create and use a RPC call to create branches on bzr servers rather than using VFS calls.
3117
        # Initialisation when using a local bzrdir object, or a non-vfs init
3118
        # method is not available on the server.
3119
        # self._custom_format is always set - the start of initialize ensures
3120
        # that.
3121
        if isinstance(a_bzrdir, RemoteBzrDir):
3122
            a_bzrdir._ensure_real()
5051.3.10 by Jelmer Vernooij
Pass colocated branch name around in more places.
3123
            result = self._custom_format.initialize(a_bzrdir._real_bzrdir,
6437.71.1 by John Arbash Meinel
One of the discoveries from fixing bug #1046697.
3124
                name=name, append_revisions_only=append_revisions_only,
3125
                repository=repository)
4032.3.2 by Robert Collins
Create and use a RPC call to create branches on bzr servers rather than using VFS calls.
3126
        else:
3127
            # We assume the bzrdir is parameterised; it may not be.
6437.21.7 by Jelmer Vernooij
Fix remaining tests.
3128
            result = self._custom_format.initialize(a_bzrdir, name=name,
6437.71.1 by John Arbash Meinel
One of the discoveries from fixing bug #1046697.
3129
                append_revisions_only=append_revisions_only,
3130
                repository=repository)
4032.3.2 by Robert Collins
Create and use a RPC call to create branches on bzr servers rather than using VFS calls.
3131
        if (isinstance(a_bzrdir, RemoteBzrDir) and
3132
            not isinstance(result, RemoteBranch)):
5051.3.10 by Jelmer Vernooij
Pass colocated branch name around in more places.
3133
            result = RemoteBranch(a_bzrdir, a_bzrdir.find_repository(), result,
3134
                                  name=name)
4032.3.2 by Robert Collins
Create and use a RPC call to create branches on bzr servers rather than using VFS calls.
3135
        return result
3136
6123.9.12 by Jelmer Vernooij
Add append_revisions_only argument to BranchFormat.initialize.
3137
    def initialize(self, a_bzrdir, name=None, repository=None,
3138
                   append_revisions_only=None):
6436.1.2 by Jelmer Vernooij
Fix some tests.
3139
        if name is None:
3140
            name = a_bzrdir._get_selected_branch()
4032.3.2 by Robert Collins
Create and use a RPC call to create branches on bzr servers rather than using VFS calls.
3141
        # 1) get the network name to use.
3142
        if self._custom_format:
3143
            network_name = self._custom_format.network_name()
3144
        else:
6622.1.34 by Jelmer Vernooij
Rename brzlib => breezy.
3145
            # Select the current breezy default and ask for that.
6472.2.1 by Jelmer Vernooij
Use bzrdir.controldir for generic access to control directories.
3146
            reference_bzrdir_format = controldir.format_registry.get('default')()
4032.3.2 by Robert Collins
Create and use a RPC call to create branches on bzr servers rather than using VFS calls.
3147
            reference_format = reference_bzrdir_format.get_branch_format()
3148
            self._custom_format = reference_format
3149
            network_name = reference_format.network_name()
3150
        # Being asked to create on a non RemoteBzrDir:
4005.2.1 by Robert Collins
Fix RemoteBranch to be used correctly in tests using bzr+ssh, to fire off Branch hooks correctly, and improve the branch_implementations tests to check that making a branch gets the right format under test.
3151
        if not isinstance(a_bzrdir, RemoteBzrDir):
6123.9.12 by Jelmer Vernooij
Add append_revisions_only argument to BranchFormat.initialize.
3152
            return self._vfs_initialize(a_bzrdir, name=name,
6437.71.1 by John Arbash Meinel
One of the discoveries from fixing bug #1046697.
3153
                append_revisions_only=append_revisions_only,
3154
                repository=repository)
4032.3.2 by Robert Collins
Create and use a RPC call to create branches on bzr servers rather than using VFS calls.
3155
        medium = a_bzrdir._client._medium
3156
        if medium._is_remote_before((1, 13)):
6123.9.12 by Jelmer Vernooij
Add append_revisions_only argument to BranchFormat.initialize.
3157
            return self._vfs_initialize(a_bzrdir, name=name,
6437.71.1 by John Arbash Meinel
One of the discoveries from fixing bug #1046697.
3158
                append_revisions_only=append_revisions_only,
3159
                repository=repository)
4032.3.2 by Robert Collins
Create and use a RPC call to create branches on bzr servers rather than using VFS calls.
3160
        # Creating on a remote bzr dir.
3161
        # 2) try direct creation via RPC
3162
        path = a_bzrdir._path_for_remote_call(a_bzrdir._client)
6436.1.2 by Jelmer Vernooij
Fix some tests.
3163
        if name != "":
5051.3.11 by Jelmer Vernooij
add XXX for creating remote colocated branches.
3164
            # XXX JRV20100304: Support creating colocated branches
5051.3.10 by Jelmer Vernooij
Pass colocated branch name around in more places.
3165
            raise errors.NoColocatedBranchSupport(self)
4032.3.2 by Robert Collins
Create and use a RPC call to create branches on bzr servers rather than using VFS calls.
3166
        verb = 'BzrDir.create_branch'
3167
        try:
3168
            response = a_bzrdir._call(verb, path, network_name)
3169
        except errors.UnknownSmartMethod:
3170
            # Fallback - use vfs methods
4094.1.1 by Andrew Bennetts
Add some medium._remember_is_before((1, 13)) calls.
3171
            medium._remember_remote_is_before((1, 13))
6123.9.12 by Jelmer Vernooij
Add append_revisions_only argument to BranchFormat.initialize.
3172
            return self._vfs_initialize(a_bzrdir, name=name,
6437.71.1 by John Arbash Meinel
One of the discoveries from fixing bug #1046697.
3173
                    append_revisions_only=append_revisions_only,
3174
                    repository=repository)
4032.3.2 by Robert Collins
Create and use a RPC call to create branches on bzr servers rather than using VFS calls.
3175
        if response[0] != 'ok':
3176
            raise errors.UnexpectedSmartServerResponse(response)
3177
        # Turn the response into a RemoteRepository object.
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.
3178
        format = RemoteBranchFormat(network_name=response[1])
4032.3.2 by Robert Collins
Create and use a RPC call to create branches on bzr servers rather than using VFS calls.
3179
        repo_format = response_tuple_to_repo_format(response[3:])
5536.1.1 by Andrew Bennetts
Avoid reopening (and relocking) the same branches/repositories in ControlDir.sprout. Still a few rough edges, but the tests I've run are passing.
3180
        repo_path = response[2]
3181
        if repository is not None:
5609.21.1 by Andrew Bennetts
Possible fix for #726584, plus drive-by docstring fix.
3182
            remote_repo_url = urlutils.join(a_bzrdir.user_url, repo_path)
5535.3.7 by Andrew Bennetts
Allow for trailing-slash differences between local url path vs. remote url path for remote branch's repository.
3183
            url_diff = urlutils.relative_url(repository.user_url,
3184
                    remote_repo_url)
3185
            if url_diff != '.':
5536.1.1 by Andrew Bennetts
Avoid reopening (and relocking) the same branches/repositories in ControlDir.sprout. Still a few rough edges, but the tests I've run are passing.
3186
                raise AssertionError(
5536.1.10 by Andrew Bennetts
Give more helpful message in AssertionErrors, just in case.
3187
                    'repository.user_url %r does not match URL from server '
3188
                    'response (%r + %r)'
5609.21.1 by Andrew Bennetts
Possible fix for #726584, plus drive-by docstring fix.
3189
                    % (repository.user_url, a_bzrdir.user_url, repo_path))
5536.1.1 by Andrew Bennetts
Avoid reopening (and relocking) the same branches/repositories in ControlDir.sprout. Still a few rough edges, but the tests I've run are passing.
3190
            remote_repo = repository
4005.2.1 by Robert Collins
Fix RemoteBranch to be used correctly in tests using bzr+ssh, to fire off Branch hooks correctly, and improve the branch_implementations tests to check that making a branch gets the right format under test.
3191
        else:
5536.1.1 by Andrew Bennetts
Avoid reopening (and relocking) the same branches/repositories in ControlDir.sprout. Still a few rough edges, but the tests I've run are passing.
3192
            if repo_path == '':
3193
                repo_bzrdir = a_bzrdir
3194
            else:
3195
                repo_bzrdir = RemoteBzrDir(
3196
                    a_bzrdir.root_transport.clone(repo_path), a_bzrdir._format,
3197
                    a_bzrdir._client)
3198
            remote_repo = RemoteRepository(repo_bzrdir, repo_format)
4032.3.2 by Robert Collins
Create and use a RPC call to create branches on bzr servers rather than using VFS calls.
3199
        remote_branch = RemoteBranch(a_bzrdir, remote_repo,
5051.3.10 by Jelmer Vernooij
Pass colocated branch name around in more places.
3200
            format=format, setup_stacking=False, name=name)
6123.9.12 by Jelmer Vernooij
Add append_revisions_only argument to BranchFormat.initialize.
3201
        if append_revisions_only:
3202
            remote_branch.set_append_revisions_only(append_revisions_only)
4044.1.4 by Robert Collins
Remove a wasted round trip determining the revno and revid of a newly created branch.
3203
        # XXX: We know this is a new branch, so it must have revno 0, revid
3204
        # NULL_REVISION. Creating the branch locked would make this be unable
3205
        # to be wrong; here its simply very unlikely to be wrong. RBC 20090225
3206
        remote_branch._last_revision_info_cache = 0, NULL_REVISION
4032.3.2 by Robert Collins
Create and use a RPC call to create branches on bzr servers rather than using VFS calls.
3207
        return remote_branch
1752.2.31 by Martin Pool
[broken] some support for write operations over hpss
3208
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.
3209
    def make_tags(self, branch):
3210
        self._ensure_real()
3211
        return self._custom_format.make_tags(branch)
3212
2696.3.6 by Martin Pool
Mark RemoteBranch as (possibly) supporting tags
3213
    def supports_tags(self):
3214
        # Remote branches might support tags, but we won't know until we
3215
        # access the real remote branch.
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.
3216
        self._ensure_real()
3217
        return self._custom_format.supports_tags()
2696.3.6 by Martin Pool
Mark RemoteBranch as (possibly) supporting tags
3218
4103.2.2 by Andrew Bennetts
Fix RemoteBranchFormat.supports_stacking()
3219
    def supports_stacking(self):
3220
        self._ensure_real()
3221
        return self._custom_format.supports_stacking()
3222
4301.3.3 by Andrew Bennetts
Move check onto base Branch class, and add a supports_set_append_revisions_only method to BranchFormat, as suggested by Robert.
3223
    def supports_set_append_revisions_only(self):
3224
        self._ensure_real()
3225
        return self._custom_format.supports_set_append_revisions_only()
3226
5672.1.7 by Andrew Bennetts
Use a more explicit method name.
3227
    def _use_default_local_heads_to_fetch(self):
5672.1.4 by Andrew Bennetts
Fix final bzr-loom test by adding RemoteBranch.heads_to_fetch that can ask the remote branch for the heads to fetch (but uses the cheaper default logic if it knows the remote format has an identical heads_to_fetch as Branch.heads_to_fetch).
3228
        # If the branch format is a metadir format *and* its heads_to_fetch
3229
        # implementation is not overridden vs the base class, we can use the
3230
        # base class logic rather than use the heads_to_fetch RPC.  This is
5672.1.5 by Andrew Bennetts
Add some tests for RemoteBranch.heads_to_fetch, and add release-note.
3231
        # usually cheaper in terms of net round trips, as the last-revision and
5672.1.4 by Andrew Bennetts
Fix final bzr-loom test by adding RemoteBranch.heads_to_fetch that can ask the remote branch for the heads to fetch (but uses the cheaper default logic if it knows the remote format has an identical heads_to_fetch as Branch.heads_to_fetch).
3232
        # tags info fetched is cached and would be fetched anyway.
3233
        self._ensure_real()
6653.1.1 by Jelmer Vernooij
Split bzr branch code out into breezy.bzrbranch.
3234
        if isinstance(self._custom_format, bzrbranch.BranchFormatMetadir):
5672.1.4 by Andrew Bennetts
Fix final bzr-loom test by adding RemoteBranch.heads_to_fetch that can ask the remote branch for the heads to fetch (but uses the cheaper default logic if it knows the remote format has an identical heads_to_fetch as Branch.heads_to_fetch).
3235
            branch_class = self._custom_format._branch_class()
6619.3.24 by Jelmer Vernooij
Run 2to3 methodattrs fixer.
3236
            heads_to_fetch_impl = branch_class.heads_to_fetch.__func__
3237
            if heads_to_fetch_impl is branch.Branch.heads_to_fetch.__func__:
5672.1.4 by Andrew Bennetts
Fix final bzr-loom test by adding RemoteBranch.heads_to_fetch that can ask the remote branch for the heads to fetch (but uses the cheaper default logic if it knows the remote format has an identical heads_to_fetch as Branch.heads_to_fetch).
3238
                return True
3239
        return False
1752.2.31 by Martin Pool
[broken] some support for write operations over hpss
3240
6263.3.1 by Jelmer Vernooij
Some formatting fixes.
3241
6362.6.3 by Jelmer Vernooij
Fix compatibility after config stack changes.
3242
class RemoteBranchStore(_mod_config.IniFileStore):
6270.1.6 by Jelmer Vernooij
Provide RemoteControlStore and RemoteBranchStore.
3243
    """Branch store which attempts to use HPSS calls to retrieve branch store.
3244
3245
    Note that this is specific to bzr-based formats.
3246
    """
3247
3248
    def __init__(self, branch):
3249
        super(RemoteBranchStore, self).__init__()
3250
        self.branch = branch
6270.1.14 by Jelmer Vernooij
Set RemoteBranchStore.id.
3251
        self.id = "branch"
6270.1.7 by Jelmer Vernooij
Use _ensure_real.
3252
        self._real_store = None
6270.1.6 by Jelmer Vernooij
Provide RemoteControlStore and RemoteBranchStore.
3253
3254
    def external_url(self):
6499.3.2 by Vincent Ladeuil
Use a proper unique url for remote config files.
3255
        return urlutils.join(self.branch.user_url, 'branch.conf')
6270.1.6 by Jelmer Vernooij
Provide RemoteControlStore and RemoteBranchStore.
3256
3257
    def _load_content(self):
3258
        path = self.branch._remote_path()
3259
        try:
6270.1.10 by Jelmer Vernooij
Fix testing Branch.set_config_file.
3260
            response, handler = self.branch._call_expecting_body(
6270.1.6 by Jelmer Vernooij
Provide RemoteControlStore and RemoteBranchStore.
3261
                'Branch.get_config_file', path)
3262
        except errors.UnknownSmartMethod:
6270.1.7 by Jelmer Vernooij
Use _ensure_real.
3263
            self._ensure_real()
3264
            return self._real_store._load_content()
6270.1.6 by Jelmer Vernooij
Provide RemoteControlStore and RemoteBranchStore.
3265
        if len(response) and response[0] != 'ok':
3266
            raise errors.UnexpectedSmartServerResponse(response)
3267
        return handler.read_body_bytes()
3268
3269
    def _save_content(self, content):
6270.1.7 by Jelmer Vernooij
Use _ensure_real.
3270
        path = self.branch._remote_path()
3271
        try:
6270.1.18 by Jelmer Vernooij
Fix a test.
3272
            response, handler = self.branch._call_with_body_bytes_expecting_body(
6270.1.17 by Jelmer Vernooij
s/set_config_file/put_config_file.
3273
                'Branch.put_config_file', (path,
6270.1.10 by Jelmer Vernooij
Fix testing Branch.set_config_file.
3274
                    self.branch._lock_token, self.branch._repo_lock_token),
3275
                content)
6270.1.7 by Jelmer Vernooij
Use _ensure_real.
3276
        except errors.UnknownSmartMethod:
3277
            self._ensure_real()
3278
            return self._real_store._save_content(content)
6270.1.18 by Jelmer Vernooij
Fix a test.
3279
        handler.cancel_read_body()
6270.1.16 by Jelmer Vernooij
Expect 'ok' response from set_config_file.
3280
        if response != ('ok', ):
6270.1.7 by Jelmer Vernooij
Use _ensure_real.
3281
            raise errors.UnexpectedSmartServerResponse(response)
3282
3283
    def _ensure_real(self):
3284
        self.branch._ensure_real()
6270.1.8 by Jelmer Vernooij
Fix RemoteControlStore.
3285
        if self._real_store is None:
6362.6.3 by Jelmer Vernooij
Fix compatibility after config stack changes.
3286
            self._real_store = _mod_config.BranchStore(self.branch)
6270.1.6 by Jelmer Vernooij
Provide RemoteControlStore and RemoteBranchStore.
3287
3288
4731.1.2 by Andrew Bennetts
Refactor to reduce duplication.
3289
class RemoteBranch(branch.Branch, _RpcHelper, lock._RelockDebugMixin):
1752.2.31 by Martin Pool
[broken] some support for write operations over hpss
3290
    """Branch stored on a server accessed by HPSS RPC.
3291
3292
    At the moment most operations are mapped down to simple file operations.
3293
    """
1752.2.30 by Martin Pool
Start adding a RemoteBzrDir, etc
3294
2018.5.51 by Wouter van Heyst
Test and implement RemoteBranch.last_revision_info()
3295
    def __init__(self, remote_bzrdir, remote_repository, real_branch=None,
6305.3.6 by Jelmer Vernooij
Pass possible_transports along for remote branches.
3296
        _client=None, format=None, setup_stacking=True, name=None,
3297
        possible_transports=None):
2018.5.34 by Robert Collins
Get test_remote.BasicRemoteObjectTests.test_open_remote_branch passing by implementing a remote method BzrDir.find_repository.
3298
        """Create a RemoteBranch instance.
3299
3300
        :param real_branch: An optional local implementation of the branch
3301
            format, usually accessing the data via the VFS.
2018.5.51 by Wouter van Heyst
Test and implement RemoteBranch.last_revision_info()
3302
        :param _client: Private parameter for testing.
4032.3.2 by Robert Collins
Create and use a RPC call to create branches on bzr servers rather than using VFS calls.
3303
        :param format: A RemoteBranchFormat object, None to create one
3304
            automatically. If supplied it should have a network_name already
3305
            supplied.
3306
        :param setup_stacking: If True make an RPC call to determine the
3307
            stacked (or not) status of the branch. If False assume the branch
3308
            is not stacked.
5051.3.10 by Jelmer Vernooij
Pass colocated branch name around in more places.
3309
        :param name: Colocated branch name
2018.5.34 by Robert Collins
Get test_remote.BasicRemoteObjectTests.test_open_remote_branch passing by implementing a remote method BzrDir.find_repository.
3310
        """
2018.5.163 by Andrew Bennetts
Deal with various review comments from Robert.
3311
        # We intentionally don't call the parent class's __init__, because it
3312
        # will try to assign to self.tags, which is a property in this subclass.
3313
        # And the parent's __init__ doesn't do much anyway.
1752.2.64 by Andrew Bennetts
Improve how RemoteBzrDir.open_branch works to handle references and not double-open repositories.
3314
        self.bzrdir = remote_bzrdir
6437.21.7 by Jelmer Vernooij
Fix remaining tests.
3315
        self.name = name
2018.5.51 by Wouter van Heyst
Test and implement RemoteBranch.last_revision_info()
3316
        if _client is not None:
3317
            self._client = _client
3318
        else:
3313.2.1 by Andrew Bennetts
Change _SmartClient's API to accept a medium and a base, rather than a _SharedConnection.
3319
            self._client = remote_bzrdir._client
1752.2.64 by Andrew Bennetts
Improve how RemoteBzrDir.open_branch works to handle references and not double-open repositories.
3320
        self.repository = remote_repository
2018.5.34 by Robert Collins
Get test_remote.BasicRemoteObjectTests.test_open_remote_branch passing by implementing a remote method BzrDir.find_repository.
3321
        if real_branch is not None:
3322
            self._real_branch = real_branch
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
3323
            # Give the remote repository the matching real repo.
2018.5.97 by Andrew Bennetts
Fix more tests.
3324
            real_repo = self._real_branch.repository
3325
            if isinstance(real_repo, RemoteRepository):
3326
                real_repo._ensure_real()
3327
                real_repo = real_repo._real_repository
3328
            self.repository._set_real_repository(real_repo)
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
3329
            # Give the branch the remote repository to let fast-pathing happen.
3330
            self._real_branch.repository = self.repository
2018.5.70 by Robert Collins
Only try to get real repositories when an operation requires them.
3331
        else:
3332
            self._real_branch = None
6622.1.34 by Jelmer Vernooij
Rename brzlib => breezy.
3333
        # Fill out expected attributes of branch for breezy API users.
4419.2.2 by Andrew Bennetts
Read lock branch_from in cmd_pull, avoids refetching last_revision_info and so reduces test_pull acceptance ratchet.
3334
        self._clear_cached_state()
5158.6.9 by Martin Pool
Simplify various code to use user_url
3335
        # TODO: deprecate self.base in favor of user_url
3336
        self.base = self.bzrdir.user_url
5051.3.10 by Jelmer Vernooij
Pass colocated branch name around in more places.
3337
        self._name = name
2018.5.169 by Andrew Bennetts
Add a _server_formats flag to BzrDir.open_from_transport and BzrDirFormat.find_format, make RemoteBranch.control_files into a property.
3338
        self._control_files = None
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
3339
        self._lock_mode = None
3340
        self._lock_token = None
2892.2.1 by Andrew Bennetts
Add Branch.set_last_revision_info smart method, and make the RemoteBranch client use it.
3341
        self._repo_lock_token = None
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
3342
        self._lock_count = 0
3343
        self._leave_lock = False
6404.6.1 by Vincent Ladeuil
Tests passing for a first rough version of a cached branch config store. The changes here are too invasive and several parallel proposals have been made.
3344
        self.conf_store = None
4032.3.2 by Robert Collins
Create and use a RPC call to create branches on bzr servers rather than using VFS calls.
3345
        # Setup a format: note that we cannot call _ensure_real until all the
3346
        # attributes above are set: This code cannot be moved higher up in this
3347
        # function.
3348
        if format is None:
3349
            self._format = RemoteBranchFormat()
3350
            if real_branch is not None:
3351
                self._format._network_name = \
3352
                    self._real_branch._format.network_name()
4032.3.1 by Robert Collins
Add a BranchFormat.network_name() method as preparation for creating branches via RPC calls.
3353
        else:
4032.3.2 by Robert Collins
Create and use a RPC call to create branches on bzr servers rather than using VFS calls.
3354
            self._format = format
4600.2.1 by Robert Collins
Make RemoteBranch honour ignore_fallbacks when _ensure_real is triggered.
3355
        # when we do _ensure_real we may need to pass ignore_fallbacks to the
3356
        # branch.open_branch method.
3357
        self._real_ignore_fallbacks = not setup_stacking
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.
3358
        if not self._format._network_name:
3359
            # Did not get from open_branchV2 - old server.
3360
            self._ensure_real()
3361
            self._format._network_name = \
3362
                self._real_branch._format.network_name()
3363
        self.tags = self._format.make_tags(self)
3681.1.2 by Robert Collins
Adjust for trunk.
3364
        # The base class init is not called, so we duplicate this:
3681.1.1 by Robert Collins
Create a new hook Branch.open. (Robert Collins)
3365
        hooks = branch.Branch.hooks['open']
3366
        for hook in hooks:
3367
            hook(self)
4419.1.3 by Andrew Bennetts
Quick fix by using self._ensure_real.
3368
        self._is_stacked = False
4032.3.2 by Robert Collins
Create and use a RPC call to create branches on bzr servers rather than using VFS calls.
3369
        if setup_stacking:
6305.3.6 by Jelmer Vernooij
Pass possible_transports along for remote branches.
3370
            self._setup_stacking(possible_transports)
3691.2.1 by Martin Pool
RemoteBranch must configure stacking into the repository
3371
6305.3.6 by Jelmer Vernooij
Pass possible_transports along for remote branches.
3372
    def _setup_stacking(self, possible_transports):
3691.2.1 by Martin Pool
RemoteBranch must configure stacking into the repository
3373
        # configure stacking into the remote repository, by reading it from
3691.2.3 by Martin Pool
Factor out RemoteBranch._remote_path() and disable RemoteBranch stacking
3374
        # the vfs branch.
3691.2.1 by Martin Pool
RemoteBranch must configure stacking into the repository
3375
        try:
3376
            fallback_url = self.get_stacked_on_url()
3377
        except (errors.NotStacked, errors.UnstackableBranchFormat,
6619.3.2 by Jelmer Vernooij
Apply 2to3 except fix.
3378
            errors.UnstackableRepositoryFormat) as e:
3691.2.7 by Martin Pool
FakeClient can know what calls to expect
3379
            return
4419.1.3 by Andrew Bennetts
Quick fix by using self._ensure_real.
3380
        self._is_stacked = True
6305.3.6 by Jelmer Vernooij
Pass possible_transports along for remote branches.
3381
        if possible_transports is None:
3382
            possible_transports = []
3383
        else:
3384
            possible_transports = list(possible_transports)
3385
        possible_transports.append(self.bzrdir.root_transport)
6305.3.3 by Jelmer Vernooij
Fix use of possible_transports.
3386
        self._activate_fallback_location(fallback_url,
6305.3.6 by Jelmer Vernooij
Pass possible_transports along for remote branches.
3387
            possible_transports=possible_transports)
1752.2.64 by Andrew Bennetts
Improve how RemoteBzrDir.open_branch works to handle references and not double-open repositories.
3388
4226.1.5 by Robert Collins
Reinstate the use of the Branch.get_config_file verb.
3389
    def _get_config(self):
3390
        return RemoteBranchConfig(self)
3391
6270.1.19 by Jelmer Vernooij
Some changes discussed with vila on IRC.
3392
    def _get_config_store(self):
6404.6.1 by Vincent Ladeuil
Tests passing for a first rough version of a cached branch config store. The changes here are too invasive and several parallel proposals have been made.
3393
        if self.conf_store is None:
3394
            self.conf_store =  RemoteBranchStore(self)
3395
        return self.conf_store
6270.1.4 by Jelmer Vernooij
Add Branch.get_config_stack / BzrDir.get_config_stack.
3396
6538.1.29 by Aaron Bentley
Remove unused 'message'
3397
    def store_uncommitted(self, creator):
6538.1.23 by Aaron Bentley
Move uncommitted API to BzrBranch/RemoteBranch.
3398
        self._ensure_real()
6538.1.29 by Aaron Bentley
Remove unused 'message'
3399
        return self._real_branch.store_uncommitted(creator)
6538.1.23 by Aaron Bentley
Move uncommitted API to BzrBranch/RemoteBranch.
3400
3401
    def get_unshelver(self, tree):
3402
        self._ensure_real()
3403
        return self._real_branch.get_unshelver(tree)
3404
3407.2.17 by Martin Pool
better name: _get_real_transport
3405
    def _get_real_transport(self):
3407.2.16 by Martin Pool
Remove RemoteBranch reliance on control_files._transport
3406
        # if we try vfs access, return the real branch's vfs transport
3407
        self._ensure_real()
3408
        return self._real_branch._transport
3409
3407.2.17 by Martin Pool
better name: _get_real_transport
3410
    _transport = property(_get_real_transport)
3407.2.16 by Martin Pool
Remove RemoteBranch reliance on control_files._transport
3411
2477.1.1 by Martin Pool
Add RemoteBranch repr
3412
    def __str__(self):
3413
        return "%s(%s)" % (self.__class__.__name__, self.base)
3414
3415
    __repr__ = __str__
3416
2018.5.70 by Robert Collins
Only try to get real repositories when an operation requires them.
3417
    def _ensure_real(self):
3418
        """Ensure that there is a _real_branch set.
3419
2018.5.163 by Andrew Bennetts
Deal with various review comments from Robert.
3420
        Used before calls to self._real_branch.
2018.5.70 by Robert Collins
Only try to get real repositories when an operation requires them.
3421
        """
3407.2.16 by Martin Pool
Remove RemoteBranch reliance on control_files._transport
3422
        if self._real_branch is None:
3376.2.4 by Martin Pool
Remove every assert statement from bzrlib!
3423
            if not vfs.vfs_enabled():
3424
                raise AssertionError('smart server vfs must be enabled '
3425
                    'to use vfs implementation')
2018.5.70 by Robert Collins
Only try to get real repositories when an operation requires them.
3426
            self.bzrdir._ensure_real()
4600.2.1 by Robert Collins
Make RemoteBranch honour ignore_fallbacks when _ensure_real is triggered.
3427
            self._real_branch = self.bzrdir._real_bzrdir.open_branch(
5051.3.10 by Jelmer Vernooij
Pass colocated branch name around in more places.
3428
                ignore_fallbacks=self._real_ignore_fallbacks, name=self._name)
6404.6.1 by Vincent Ladeuil
Tests passing for a first rough version of a cached branch config store. The changes here are too invasive and several parallel proposals have been made.
3429
            # The remote branch and the real branch shares the same store. If
3430
            # we don't, there will always be cases where one of the stores
3431
            # doesn't see an update made on the other.
3432
            self._real_branch.conf_store = self.conf_store
3692.1.3 by Andrew Bennetts
Delete some cruft (like the _ensure_real call in RemoteBranch.lock_write), improve some comments, and wrap some long lines.
3433
            if self.repository._real_repository is None:
3434
                # Give the remote repository the matching real repo.
3435
                real_repo = self._real_branch.repository
3436
                if isinstance(real_repo, RemoteRepository):
3437
                    real_repo._ensure_real()
3438
                    real_repo = real_repo._real_repository
3439
                self.repository._set_real_repository(real_repo)
3440
            # Give the real branch the remote repository to let fast-pathing
3441
            # happen.
2018.5.70 by Robert Collins
Only try to get real repositories when an operation requires them.
3442
            self._real_branch.repository = self.repository
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
3443
            if self._lock_mode == 'r':
3444
                self._real_branch.lock_read()
3692.1.3 by Andrew Bennetts
Delete some cruft (like the _ensure_real call in RemoteBranch.lock_write), improve some comments, and wrap some long lines.
3445
            elif self._lock_mode == 'w':
3446
                self._real_branch.lock_write(token=self._lock_token)
2018.5.70 by Robert Collins
Only try to get real repositories when an operation requires them.
3447
3533.3.1 by Andrew Bennetts
Remove duplication of error translation in bzrlib/remote.py.
3448
    def _translate_error(self, err, **context):
3449
        self.repository._translate_error(err, branch=self, **context)
3450
3441.5.1 by Andrew Bennetts
Avoid necessarily calling get_parent_map when pushing.
3451
    def _clear_cached_state(self):
3452
        super(RemoteBranch, self)._clear_cached_state()
3441.5.5 by Andrew Bennetts
Some small tweaks and comments.
3453
        if self._real_branch is not None:
3454
            self._real_branch._clear_cached_state()
3441.5.29 by Andrew Bennetts
More review tweaks: whitespace nits in test_smart, add (and use) ._clear_cached_state_of_remote_branch_only method in bzrlib/remote.py.
3455
3456
    def _clear_cached_state_of_remote_branch_only(self):
3457
        """Like _clear_cached_state, but doesn't clear the cache of
3458
        self._real_branch.
3459
3460
        This is useful when falling back to calling a method of
3461
        self._real_branch that changes state.  In that case the underlying
3462
        branch changes, so we need to invalidate this RemoteBranch's cache of
3463
        it.  However, there's no need to invalidate the _real_branch's cache
3464
        too, in fact doing so might harm performance.
3465
        """
3466
        super(RemoteBranch, self)._clear_cached_state()
3943.8.1 by Marius Kruger
remove all trailing whitespace from bzr source
3467
2018.5.169 by Andrew Bennetts
Add a _server_formats flag to BzrDir.open_from_transport and BzrDirFormat.find_format, make RemoteBranch.control_files into a property.
3468
    @property
3469
    def control_files(self):
3470
        # Defer actually creating RemoteBranchLockableFiles until its needed,
3471
        # because it triggers an _ensure_real that we otherwise might not need.
3472
        if self._control_files is None:
3473
            self._control_files = RemoteBranchLockableFiles(
3474
                self.bzrdir, self._client)
3475
        return self._control_files
3476
2018.5.60 by Robert Collins
More missing methods from RemoteBranch and RemoteRepository to let 'info' get further.
3477
    def get_physical_lock_status(self):
3478
        """See Branch.get_physical_lock_status()."""
6280.6.1 by Jelmer Vernooij
Implement remote side of {Branch,Repository}.get_physical_lock_status.
3479
        try:
3480
            response = self._client.call('Branch.get_physical_lock_status',
3481
                self._remote_path())
3482
        except errors.UnknownSmartMethod:
3483
            self._ensure_real()
3484
            return self._real_branch.get_physical_lock_status()
3485
        if response[0] not in ('yes', 'no'):
3486
            raise errors.UnexpectedSmartServerResponse(response)
3487
        return (response[0] == 'yes')
2018.5.60 by Robert Collins
More missing methods from RemoteBranch and RemoteRepository to let 'info' get further.
3488
3537.3.1 by Martin Pool
Rename branch.get_stacked_on to get_stacked_on_url
3489
    def get_stacked_on_url(self):
3221.11.2 by Robert Collins
Create basic stackable branch facility.
3490
        """Get the URL this branch is stacked against.
3491
3492
        :raises NotStacked: If the branch is not stacked.
3493
        :raises UnstackableBranchFormat: If the branch does not support
3494
            stacking.
3495
        :raises UnstackableRepositoryFormat: If the repository does not support
3496
            stacking.
3497
        """
3691.2.12 by Martin Pool
Add test for coping without Branch.get_stacked_on_url
3498
        try:
3786.2.3 by Andrew Bennetts
Remove duplicated 'call & translate errors' code in bzrlib.remote.
3499
            # there may not be a repository yet, so we can't use
3500
            # self._translate_error, so we can't use self._call either.
3691.2.12 by Martin Pool
Add test for coping without Branch.get_stacked_on_url
3501
            response = self._client.call('Branch.get_stacked_on_url',
3502
                self._remote_path())
6619.3.2 by Jelmer Vernooij
Apply 2to3 except fix.
3503
        except errors.ErrorFromSmartServer as err:
3691.2.12 by Martin Pool
Add test for coping without Branch.get_stacked_on_url
3504
            # there may not be a repository yet, so we can't call through
3505
            # its _translate_error
3506
            _translate_error(err, branch=self)
6619.3.2 by Jelmer Vernooij
Apply 2to3 except fix.
3507
        except errors.UnknownSmartMethod as err:
3691.2.12 by Martin Pool
Add test for coping without Branch.get_stacked_on_url
3508
            self._ensure_real()
3509
            return self._real_branch.get_stacked_on_url()
3786.2.3 by Andrew Bennetts
Remove duplicated 'call & translate errors' code in bzrlib.remote.
3510
        if response[0] != 'ok':
3511
            raise errors.UnexpectedSmartServerResponse(response)
3512
        return response[1]
3221.11.2 by Robert Collins
Create basic stackable branch facility.
3513
4419.1.3 by Andrew Bennetts
Quick fix by using self._ensure_real.
3514
    def set_stacked_on_url(self, url):
3515
        branch.Branch.set_stacked_on_url(self, url)
6404.6.1 by Vincent Ladeuil
Tests passing for a first rough version of a cached branch config store. The changes here are too invasive and several parallel proposals have been made.
3516
        # We need the stacked_on_url to be visible both locally (to not query
3517
        # it repeatedly) and remotely (so smart verbs can get it server side)
3518
        # Without the following line,
6622.1.34 by Jelmer Vernooij
Rename brzlib => breezy.
3519
        # breezy.tests.per_branch.test_create_clone.TestCreateClone
6404.6.1 by Vincent Ladeuil
Tests passing for a first rough version of a cached branch config store. The changes here are too invasive and several parallel proposals have been made.
3520
        # .test_create_clone_on_transport_stacked_hooks_get_stacked_branch
3521
        # fails for remote branches -- vila 2012-01-04
3522
        self.conf_store.save_changes()
4419.1.3 by Andrew Bennetts
Quick fix by using self._ensure_real.
3523
        if not url:
3524
            self._is_stacked = False
3525
        else:
3526
            self._is_stacked = True
5712.3.13 by Jelmer Vernooij
Add Prober.known_formats().
3527
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.
3528
    def _vfs_get_tags_bytes(self):
3529
        self._ensure_real()
3530
        return self._real_branch._get_tags_bytes()
3531
5535.2.1 by Andrew Bennetts
Cache a branch's tags during a read-lock.
3532
    @needs_read_lock
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.
3533
    def _get_tags_bytes(self):
5535.2.1 by Andrew Bennetts
Cache a branch's tags during a read-lock.
3534
        if self._tags_bytes is None:
3535
            self._tags_bytes = self._get_tags_bytes_via_hpss()
3536
        return self._tags_bytes
3537
3538
    def _get_tags_bytes_via_hpss(self):
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.
3539
        medium = self._client._medium
3540
        if medium._is_remote_before((1, 13)):
3541
            return self._vfs_get_tags_bytes()
3542
        try:
3543
            response = self._call('Branch.get_tags_bytes', self._remote_path())
3544
        except errors.UnknownSmartMethod:
4094.1.1 by Andrew Bennetts
Add some medium._remember_is_before((1, 13)) calls.
3545
            medium._remember_remote_is_before((1, 13))
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.
3546
            return self._vfs_get_tags_bytes()
3547
        return response[0]
3548
4556.2.10 by Andrew Bennetts
Fix trivial bug in _vfs_set_tags_bytes.
3549
    def _vfs_set_tags_bytes(self, bytes):
4556.2.1 by Andrew Bennetts
Add Branch.set_tags_bytes RPC, with HPSS call count acceptance test. Also fixes serialisation of LockDir, and uses external_url() in LockDir's repr and contention message.
3550
        self._ensure_real()
4556.2.10 by Andrew Bennetts
Fix trivial bug in _vfs_set_tags_bytes.
3551
        return self._real_branch._set_tags_bytes(bytes)
4556.2.1 by Andrew Bennetts
Add Branch.set_tags_bytes RPC, with HPSS call count acceptance test. Also fixes serialisation of LockDir, and uses external_url() in LockDir's repr and contention message.
3552
3553
    def _set_tags_bytes(self, bytes):
5535.2.3 by Andrew Bennetts
Reset cached tags when mutating tags.
3554
        if self.is_locked():
3555
            self._tags_bytes = bytes
4556.2.1 by Andrew Bennetts
Add Branch.set_tags_bytes RPC, with HPSS call count acceptance test. Also fixes serialisation of LockDir, and uses external_url() in LockDir's repr and contention message.
3556
        medium = self._client._medium
3557
        if medium._is_remote_before((1, 18)):
3558
            self._vfs_set_tags_bytes(bytes)
4634.36.1 by Andrew Bennetts
Fix trivial bug in RemoteBranch._set_tags_bytes, and add some unit tests for it.
3559
            return
4556.2.1 by Andrew Bennetts
Add Branch.set_tags_bytes RPC, with HPSS call count acceptance test. Also fixes serialisation of LockDir, and uses external_url() in LockDir's repr and contention message.
3560
        try:
3561
            args = (
3562
                self._remote_path(), self._lock_token, self._repo_lock_token)
3563
            response = self._call_with_body_bytes(
3564
                'Branch.set_tags_bytes', args, bytes)
3565
        except errors.UnknownSmartMethod:
3566
            medium._remember_remote_is_before((1, 18))
3567
            self._vfs_set_tags_bytes(bytes)
3568
1752.2.31 by Martin Pool
[broken] some support for write operations over hpss
3569
    def lock_read(self):
5200.3.3 by Robert Collins
Lock methods on ``Tree``, ``Branch`` and ``Repository`` are now
3570
        """Lock the branch for read operations.
3571
6622.1.34 by Jelmer Vernooij
Rename brzlib => breezy.
3572
        :return: A breezy.lock.LogicalLockResult.
5200.3.3 by Robert Collins
Lock methods on ``Tree``, ``Branch`` and ``Repository`` are now
3573
        """
3692.1.1 by Andrew Bennetts
Make RemoteBranch.lock_write lock the repository too.
3574
        self.repository.lock_read()
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
3575
        if not self._lock_mode:
4731.1.2 by Andrew Bennetts
Refactor to reduce duplication.
3576
            self._note_lock('r')
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
3577
            self._lock_mode = 'r'
3578
            self._lock_count = 1
3579
            if self._real_branch is not None:
3580
                self._real_branch.lock_read()
3581
        else:
3582
            self._lock_count += 1
5200.3.6 by Robert Collins
Make all lock methods return Result objects, rather than lock_read returning self, as per John's review.
3583
        return lock.LogicalLockResult(self.unlock)
1752.2.52 by Andrew Bennetts
Flesh out more Remote* methods needed to open and initialise remote branches/trees/repositories.
3584
2018.5.142 by Andrew Bennetts
Change Branch.lock_token to only accept and receive the branch lock token (rather than the branch and repo lock tokens).
3585
    def _remote_lock_write(self, token):
3586
        if token is None:
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
3587
            branch_token = repo_token = ''
3588
        else:
2018.5.142 by Andrew Bennetts
Change Branch.lock_token to only accept and receive the branch lock token (rather than the branch and repo lock tokens).
3589
            branch_token = token
5200.3.3 by Robert Collins
Lock methods on ``Tree``, ``Branch`` and ``Repository`` are now
3590
            repo_token = self.repository.lock_write().repository_token
2018.5.142 by Andrew Bennetts
Change Branch.lock_token to only accept and receive the branch lock token (rather than the branch and repo lock tokens).
3591
            self.repository.unlock()
3786.2.3 by Andrew Bennetts
Remove duplicated 'call & translate errors' code in bzrlib.remote.
3592
        err_context = {'token': token}
5284.6.1 by Parth Malwankar
initial implementation for better LockContention message.
3593
        try:
3594
            response = self._call(
3595
                'Branch.lock_write', self._remote_path(), branch_token,
3596
                repo_token or '', **err_context)
6619.3.2 by Jelmer Vernooij
Apply 2to3 except fix.
3597
        except errors.LockContention as e:
5284.6.3 by Parth Malwankar
fixed tests. closed review comments by mgz.
3598
            # The LockContention from the server doesn't have any
3599
            # information about the lock_url. We re-raise LockContention
3600
            # with valid lock_url.
3601
            raise errors.LockContention('(remote lock)',
3602
                self.repository.base.split('.bzr/')[0])
3245.4.24 by Andrew Bennetts
Consistently raise errors from the server as ErrorFromSmartServer exceptions.
3603
        if response[0] != 'ok':
2555.1.1 by Martin Pool
Remove use of 'assert False' to raise an exception unconditionally
3604
            raise errors.UnexpectedSmartServerResponse(response)
3245.4.24 by Andrew Bennetts
Consistently raise errors from the server as ErrorFromSmartServer exceptions.
3605
        ok, branch_token, repo_token = response
3606
        return branch_token, repo_token
3943.8.1 by Marius Kruger
remove all trailing whitespace from bzr source
3607
2018.5.142 by Andrew Bennetts
Change Branch.lock_token to only accept and receive the branch lock token (rather than the branch and repo lock tokens).
3608
    def lock_write(self, token=None):
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
3609
        if not self._lock_mode:
4731.1.2 by Andrew Bennetts
Refactor to reduce duplication.
3610
            self._note_lock('w')
3692.1.3 by Andrew Bennetts
Delete some cruft (like the _ensure_real call in RemoteBranch.lock_write), improve some comments, and wrap some long lines.
3611
            # Lock the branch and repo in one remote call.
2018.5.142 by Andrew Bennetts
Change Branch.lock_token to only accept and receive the branch lock token (rather than the branch and repo lock tokens).
3612
            remote_tokens = self._remote_lock_write(token)
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
3613
            self._lock_token, self._repo_lock_token = remote_tokens
3376.2.4 by Martin Pool
Remove every assert statement from bzrlib!
3614
            if not self._lock_token:
3615
                raise SmartProtocolError('Remote server did not return a token!')
3692.1.3 by Andrew Bennetts
Delete some cruft (like the _ensure_real call in RemoteBranch.lock_write), improve some comments, and wrap some long lines.
3616
            # Tell the self.repository object that it is locked.
3692.1.2 by Andrew Bennetts
Fix regression introduced by fix, and add a test for that regression.
3617
            self.repository.lock_write(
3618
                self._repo_lock_token, _skip_rpc=True)
3692.1.1 by Andrew Bennetts
Make RemoteBranch.lock_write lock the repository too.
3619
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
3620
            if self._real_branch is not None:
3692.1.5 by Andrew Bennetts
Fix bug revealed by removing _ensure_real call from RemoteBranch.lock_write.
3621
                self._real_branch.lock_write(token=self._lock_token)
2018.5.142 by Andrew Bennetts
Change Branch.lock_token to only accept and receive the branch lock token (rather than the branch and repo lock tokens).
3622
            if token is not None:
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
3623
                self._leave_lock = True
3624
            else:
3625
                self._leave_lock = False
3626
            self._lock_mode = 'w'
3627
            self._lock_count = 1
3628
        elif self._lock_mode == 'r':
5241.1.1 by Andrew Bennetts
Fix AttributeError in RemoteBranch.lock_write after lock_read.
3629
            raise errors.ReadOnlyError(self)
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
3630
        else:
2018.5.142 by Andrew Bennetts
Change Branch.lock_token to only accept and receive the branch lock token (rather than the branch and repo lock tokens).
3631
            if token is not None:
3692.1.3 by Andrew Bennetts
Delete some cruft (like the _ensure_real call in RemoteBranch.lock_write), improve some comments, and wrap some long lines.
3632
                # A token was given to lock_write, and we're relocking, so
3633
                # check that the given token actually matches the one we
3634
                # already have.
2018.5.142 by Andrew Bennetts
Change Branch.lock_token to only accept and receive the branch lock token (rather than the branch and repo lock tokens).
3635
                if token != self._lock_token:
3636
                    raise errors.TokenMismatch(token, self._lock_token)
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
3637
            self._lock_count += 1
3692.1.3 by Andrew Bennetts
Delete some cruft (like the _ensure_real call in RemoteBranch.lock_write), improve some comments, and wrap some long lines.
3638
            # Re-lock the repository too.
3692.1.2 by Andrew Bennetts
Fix regression introduced by fix, and add a test for that regression.
3639
            self.repository.lock_write(self._repo_lock_token)
5200.3.3 by Robert Collins
Lock methods on ``Tree``, ``Branch`` and ``Repository`` are now
3640
        return BranchWriteLockResult(self.unlock, self._lock_token or None)
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
3641
3642
    def _unlock(self, branch_token, repo_token):
3786.2.3 by Andrew Bennetts
Remove duplicated 'call & translate errors' code in bzrlib.remote.
3643
        err_context = {'token': str((branch_token, repo_token))}
3644
        response = self._call(
3645
            'Branch.unlock', self._remote_path(), branch_token,
3646
            repo_token or '', **err_context)
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
3647
        if response == ('ok',):
3648
            return
3245.4.24 by Andrew Bennetts
Consistently raise errors from the server as ErrorFromSmartServer exceptions.
3649
        raise errors.UnexpectedSmartServerResponse(response)
1752.2.31 by Martin Pool
[broken] some support for write operations over hpss
3650
4634.85.9 by Andrew Bennetts
Add some experimental decorators: @only_raises(..) and @cleanup_method.
3651
    @only_raises(errors.LockNotHeld, errors.LockBroken)
1752.2.31 by Martin Pool
[broken] some support for write operations over hpss
3652
    def unlock(self):
3692.1.1 by Andrew Bennetts
Make RemoteBranch.lock_write lock the repository too.
3653
        try:
3654
            self._lock_count -= 1
3655
            if not self._lock_count:
6404.6.1 by Vincent Ladeuil
Tests passing for a first rough version of a cached branch config store. The changes here are too invasive and several parallel proposals have been made.
3656
                if self.conf_store is not None:
3657
                    self.conf_store.save_changes()
3692.1.1 by Andrew Bennetts
Make RemoteBranch.lock_write lock the repository too.
3658
                self._clear_cached_state()
3659
                mode = self._lock_mode
3660
                self._lock_mode = None
3661
                if self._real_branch is not None:
3662
                    if (not self._leave_lock and mode == 'w' and
3663
                        self._repo_lock_token):
3664
                        # If this RemoteBranch will remove the physical lock
3665
                        # for the repository, make sure the _real_branch
3666
                        # doesn't do it first.  (Because the _real_branch's
3667
                        # repository is set to be the RemoteRepository.)
3668
                        self._real_branch.repository.leave_lock_in_place()
3669
                    self._real_branch.unlock()
3670
                if mode != 'w':
3671
                    # Only write-locked branched need to make a remote method
4031.3.1 by Frank Aspell
Fixing various typos
3672
                    # call to perform the unlock.
3692.1.1 by Andrew Bennetts
Make RemoteBranch.lock_write lock the repository too.
3673
                    return
3674
                if not self._lock_token:
3675
                    raise AssertionError('Locked, but no token!')
3676
                branch_token = self._lock_token
3677
                repo_token = self._repo_lock_token
3678
                self._lock_token = None
3679
                self._repo_lock_token = None
3680
                if not self._leave_lock:
3681
                    self._unlock(branch_token, repo_token)
3682
        finally:
3683
            self.repository.unlock()
1752.2.52 by Andrew Bennetts
Flesh out more Remote* methods needed to open and initialise remote branches/trees/repositories.
3684
3685
    def break_lock(self):
6280.4.3 by Jelmer Vernooij
add Branch.break_lock.
3686
        try:
3687
            response = self._call(
3688
                'Branch.break_lock', self._remote_path())
3689
        except errors.UnknownSmartMethod:
3690
            self._ensure_real()
3691
            return self._real_branch.break_lock()
3692
        if response != ('ok',):
3693
            raise errors.UnexpectedSmartServerResponse(response)
1752.2.31 by Martin Pool
[broken] some support for write operations over hpss
3694
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
3695
    def leave_lock_in_place(self):
3015.2.9 by Robert Collins
Handle repositories that do not allow remote locking, like pack repositories, in the client side remote server proxy objects.
3696
        if not self._lock_token:
3697
            raise NotImplementedError(self.leave_lock_in_place)
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
3698
        self._leave_lock = True
3699
3700
    def dont_leave_lock_in_place(self):
3015.2.9 by Robert Collins
Handle repositories that do not allow remote locking, like pack repositories, in the client side remote server proxy objects.
3701
        if not self._lock_token:
3015.2.15 by Robert Collins
Review feedback.
3702
            raise NotImplementedError(self.dont_leave_lock_in_place)
2018.5.79 by Andrew Bennetts
Implement RemoteBranch.lock_write/unlock as smart operations.
3703
        self._leave_lock = False
3704
4634.69.1 by Andrew Bennetts
Apply @needs_read_lock to RemoteBranch.get_rev_id.
3705
    @needs_read_lock
4419.2.4 by Andrew Bennetts
Add Repository.get_rev_id_for_revno RPC, removes VFS calls from 'pull -r 123' case.
3706
    def get_rev_id(self, revno, history=None):
4419.2.17 by Andrew Bennetts
Fix test failures in test_lookup_revision_id_by_dotted.
3707
        if revno == 0:
3708
            return _mod_revision.NULL_REVISION
4419.2.4 by Andrew Bennetts
Add Repository.get_rev_id_for_revno RPC, removes VFS calls from 'pull -r 123' case.
3709
        last_revision_info = self.last_revision_info()
4419.2.15 by Andrew Bennetts
Simplify RemoteBranch.get_rev_id a little; get_rev_id_for_revno handles stacking for us.
3710
        ok, result = self.repository.get_rev_id_for_revno(
3711
            revno, last_revision_info)
3712
        if ok:
3713
            return result
3714
        missing_parent = result[1]
4419.2.17 by Andrew Bennetts
Fix test failures in test_lookup_revision_id_by_dotted.
3715
        # Either the revision named by the server is missing, or its parent
3716
        # is.  Call get_parent_map to determine which, so that we report a
3717
        # useful error.
3718
        parent_map = self.repository.get_parent_map([missing_parent])
3719
        if missing_parent in parent_map:
3720
            missing_parent = parent_map[missing_parent]
4419.2.4 by Andrew Bennetts
Add Repository.get_rev_id_for_revno RPC, removes VFS calls from 'pull -r 123' case.
3721
        raise errors.RevisionNotPresent(missing_parent, self.repository)
3722
5718.8.3 by Jelmer Vernooij
More branch restructuring.
3723
    def _read_last_revision_info(self):
3786.2.3 by Andrew Bennetts
Remove duplicated 'call & translate errors' code in bzrlib.remote.
3724
        response = self._call('Branch.last_revision_info', self._remote_path())
3376.2.4 by Martin Pool
Remove every assert statement from bzrlib!
3725
        if response[0] != 'ok':
3726
            raise SmartProtocolError('unexpected response code %s' % (response,))
2018.5.51 by Wouter van Heyst
Test and implement RemoteBranch.last_revision_info()
3727
        revno = int(response[1])
2018.5.83 by Andrew Bennetts
Fix some test failures caused by the switch from unicode to UTF-8-encoded strs for revision IDs.
3728
        last_revision = response[2]
2018.5.51 by Wouter van Heyst
Test and implement RemoteBranch.last_revision_info()
3729
        return (revno, last_revision)
3730
2018.5.105 by Andrew Bennetts
Implement revision_history caching for RemoteBranch.
3731
    def _gen_revision_history(self):
3732
        """See Branch._gen_revision_history()."""
4419.1.3 by Andrew Bennetts
Quick fix by using self._ensure_real.
3733
        if self._is_stacked:
3734
            self._ensure_real()
3735
            return self._real_branch._gen_revision_history()
3786.2.3 by Andrew Bennetts
Remove duplicated 'call & translate errors' code in bzrlib.remote.
3736
        response_tuple, response_handler = self._call_expecting_body(
3691.2.3 by Martin Pool
Factor out RemoteBranch._remote_path() and disable RemoteBranch stacking
3737
            'Branch.revision_history', self._remote_path())
3245.4.58 by Andrew Bennetts
Unpack call_expecting_body's return value into variables, to avoid lots of ugly subscripting.
3738
        if response_tuple[0] != 'ok':
3452.2.2 by Andrew Bennetts
Experimental PackRepository.{check_references,autopack} RPCs.
3739
            raise errors.UnexpectedSmartServerResponse(response_tuple)
3245.4.58 by Andrew Bennetts
Unpack call_expecting_body's return value into variables, to avoid lots of ugly subscripting.
3740
        result = response_handler.read_body_bytes().split('\x00')
2018.5.38 by Robert Collins
Implement RemoteBranch.revision_history().
3741
        if result == ['']:
3742
            return []
3743
        return result
1752.2.30 by Martin Pool
Start adding a RemoteBzrDir, etc
3744
3691.2.3 by Martin Pool
Factor out RemoteBranch._remote_path() and disable RemoteBranch stacking
3745
    def _remote_path(self):
3746
        return self.bzrdir._path_for_remote_call(self._client)
3747
3441.5.18 by Andrew Bennetts
Fix some test failures.
3748
    def _set_last_revision_descendant(self, revision_id, other_branch,
3441.5.28 by Andrew Bennetts
Another review tweak: rename do_not_overwrite_descendant to allow_overwrite_descendant.
3749
            allow_diverged=False, allow_overwrite_descendant=False):
4005.2.1 by Robert Collins
Fix RemoteBranch to be used correctly in tests using bzr+ssh, to fire off Branch hooks correctly, and improve the branch_implementations tests to check that making a branch gets the right format under test.
3750
        # This performs additional work to meet the hook contract; while its
3751
        # undesirable, we have to synthesise the revno to call the hook, and
3752
        # not calling the hook is worse as it means changes can't be prevented.
3753
        # Having calculated this though, we can't just call into
3754
        # set_last_revision_info as a simple call, because there is a set_rh
3755
        # hook that some folk may still be using.
3756
        old_revno, old_revid = self.last_revision_info()
3757
        history = self._lefthand_history(revision_id)
3758
        self._run_pre_change_branch_tip_hooks(len(history), revision_id)
3786.2.3 by Andrew Bennetts
Remove duplicated 'call & translate errors' code in bzrlib.remote.
3759
        err_context = {'other_branch': other_branch}
3760
        response = self._call('Branch.set_last_revision_ex',
3761
            self._remote_path(), self._lock_token, self._repo_lock_token,
3762
            revision_id, int(allow_diverged), int(allow_overwrite_descendant),
3763
            **err_context)
3441.5.6 by Andrew Bennetts
Greatly simplify RemoteBranch.update_revisions. Still needs more tests.
3764
        self._clear_cached_state()
3441.5.18 by Andrew Bennetts
Fix some test failures.
3765
        if len(response) != 3 and response[0] != 'ok':
3441.5.6 by Andrew Bennetts
Greatly simplify RemoteBranch.update_revisions. Still needs more tests.
3766
            raise errors.UnexpectedSmartServerResponse(response)
3441.5.18 by Andrew Bennetts
Fix some test failures.
3767
        new_revno, new_revision_id = response[1:]
3768
        self._last_revision_info_cache = new_revno, new_revision_id
4005.2.1 by Robert Collins
Fix RemoteBranch to be used correctly in tests using bzr+ssh, to fire off Branch hooks correctly, and improve the branch_implementations tests to check that making a branch gets the right format under test.
3769
        self._run_post_change_branch_tip_hooks(old_revno, old_revid)
3692.1.5 by Andrew Bennetts
Fix bug revealed by removing _ensure_real call from RemoteBranch.lock_write.
3770
        if self._real_branch is not None:
3771
            cache = new_revno, new_revision_id
3772
            self._real_branch._last_revision_info_cache = cache
3441.5.6 by Andrew Bennetts
Greatly simplify RemoteBranch.update_revisions. Still needs more tests.
3773
3441.5.1 by Andrew Bennetts
Avoid necessarily calling get_parent_map when pushing.
3774
    def _set_last_revision(self, revision_id):
4005.2.1 by Robert Collins
Fix RemoteBranch to be used correctly in tests using bzr+ssh, to fire off Branch hooks correctly, and improve the branch_implementations tests to check that making a branch gets the right format under test.
3775
        old_revno, old_revid = self.last_revision_info()
3776
        # This performs additional work to meet the hook contract; while its
3777
        # undesirable, we have to synthesise the revno to call the hook, and
3778
        # not calling the hook is worse as it means changes can't be prevented.
3779
        # Having calculated this though, we can't just call into
3780
        # set_last_revision_info as a simple call, because there is a set_rh
3781
        # hook that some folk may still be using.
3782
        history = self._lefthand_history(revision_id)
3783
        self._run_pre_change_branch_tip_hooks(len(history), revision_id)
3441.5.1 by Andrew Bennetts
Avoid necessarily calling get_parent_map when pushing.
3784
        self._clear_cached_state()
3786.2.3 by Andrew Bennetts
Remove duplicated 'call & translate errors' code in bzrlib.remote.
3785
        response = self._call('Branch.set_last_revision',
3786
            self._remote_path(), self._lock_token, self._repo_lock_token,
3787
            revision_id)
3441.5.1 by Andrew Bennetts
Avoid necessarily calling get_parent_map when pushing.
3788
        if response != ('ok',):
3789
            raise errors.UnexpectedSmartServerResponse(response)
4005.2.1 by Robert Collins
Fix RemoteBranch to be used correctly in tests using bzr+ssh, to fire off Branch hooks correctly, and improve the branch_implementations tests to check that making a branch gets the right format under test.
3790
        self._run_post_change_branch_tip_hooks(old_revno, old_revid)
3441.5.1 by Andrew Bennetts
Avoid necessarily calling get_parent_map when pushing.
3791
4078.2.1 by Robert Collins
Add a Branch.get_parent remote call for RemoteBranch.
3792
    def _get_parent_location(self):
3793
        medium = self._client._medium
3794
        if medium._is_remote_before((1, 13)):
3795
            return self._vfs_get_parent_location()
3796
        try:
4083.1.4 by Andrew Bennetts
Fix trivial bug in get_parent RPC.
3797
            response = self._call('Branch.get_parent', self._remote_path())
4078.2.1 by Robert Collins
Add a Branch.get_parent remote call for RemoteBranch.
3798
        except errors.UnknownSmartMethod:
4094.1.1 by Andrew Bennetts
Add some medium._remember_is_before((1, 13)) calls.
3799
            medium._remember_remote_is_before((1, 13))
4078.2.1 by Robert Collins
Add a Branch.get_parent remote call for RemoteBranch.
3800
            return self._vfs_get_parent_location()
4083.1.4 by Andrew Bennetts
Fix trivial bug in get_parent RPC.
3801
        if len(response) != 1:
4083.1.6 by Andrew Bennetts
Fix trivial bug in my trivial bug fix :)
3802
            raise errors.UnexpectedSmartServerResponse(response)
4083.1.4 by Andrew Bennetts
Fix trivial bug in get_parent RPC.
3803
        parent_location = response[0]
3804
        if parent_location == '':
4078.2.1 by Robert Collins
Add a Branch.get_parent remote call for RemoteBranch.
3805
            return None
4083.1.4 by Andrew Bennetts
Fix trivial bug in get_parent RPC.
3806
        return parent_location
4078.2.1 by Robert Collins
Add a Branch.get_parent remote call for RemoteBranch.
3807
3808
    def _vfs_get_parent_location(self):
4005.2.1 by Robert Collins
Fix RemoteBranch to be used correctly in tests using bzr+ssh, to fire off Branch hooks correctly, and improve the branch_implementations tests to check that making a branch gets the right format under test.
3809
        self._ensure_real()
4083.1.5 by Andrew Bennetts
Fix trivial bug in get_parent RPC.
3810
        return self._real_branch._get_parent_location()
4032.1.1 by John Arbash Meinel
Merge the removal of all trailing whitespace, and resolve conflicts.
3811
4005.2.1 by Robert Collins
Fix RemoteBranch to be used correctly in tests using bzr+ssh, to fire off Branch hooks correctly, and improve the branch_implementations tests to check that making a branch gets the right format under test.
3812
    def _set_parent_location(self, url):
4288.1.7 by Robert Collins
Add new remote server verb Branch.set_parent_location, dropping roundtrips further on push operations.
3813
        medium = self._client._medium
3814
        if medium._is_remote_before((1, 15)):
3815
            return self._vfs_set_parent_location(url)
3816
        try:
3817
            call_url = url or ''
6619.3.18 by Jelmer Vernooij
Run 2to3 idioms fixer.
3818
            if not isinstance(call_url, str):
4288.1.7 by Robert Collins
Add new remote server verb Branch.set_parent_location, dropping roundtrips further on push operations.
3819
                raise AssertionError('url must be a str or None (%s)' % url)
3820
            response = self._call('Branch.set_parent_location',
3821
                self._remote_path(), self._lock_token, self._repo_lock_token,
3822
                call_url)
3823
        except errors.UnknownSmartMethod:
3824
            medium._remember_remote_is_before((1, 15))
3825
            return self._vfs_set_parent_location(url)
3826
        if response != ():
3827
            raise errors.UnexpectedSmartServerResponse(response)
3828
3829
    def _vfs_set_parent_location(self, url):
4288.1.4 by Robert Collins
Remove the explicit set_parent method on RemoteBranch in favour of inheriting from Branch.
3830
        self._ensure_real()
3831
        return self._real_branch._set_parent_location(url)
4032.1.1 by John Arbash Meinel
Merge the removal of all trailing whitespace, and resolve conflicts.
3832
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
3833
    @needs_write_lock
2477.1.2 by Martin Pool
Rename push/pull back to 'run_hooks' (jameinel)
3834
    def pull(self, source, overwrite=False, stop_revision=None,
2477.1.9 by Martin Pool
Review cleanups from John, mostly docs
3835
             **kwargs):
3441.5.29 by Andrew Bennetts
More review tweaks: whitespace nits in test_smart, add (and use) ._clear_cached_state_of_remote_branch_only method in bzrlib/remote.py.
3836
        self._clear_cached_state_of_remote_branch_only()
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
3837
        self._ensure_real()
3482.1.1 by John Arbash Meinel
Fix bug #238149, RemoteBranch.pull needs to return the _real_branch's pull result.
3838
        return self._real_branch.pull(
2477.1.2 by Martin Pool
Rename push/pull back to 'run_hooks' (jameinel)
3839
            source, overwrite=overwrite, stop_revision=stop_revision,
3489.2.4 by Andrew Bennetts
Fix all tests broken by fixing make_branch_and_tree.
3840
            _override_hook_target=self, **kwargs)
2018.14.1 by Andrew Bennetts
Update to current hpss branch? Fix lots of test failures.
3841
2018.14.3 by Andrew Bennetts
Make a couple more branch_implementations tests pass.
3842
    @needs_read_lock
5853.2.3 by Jelmer Vernooij
Fix lossy tests.
3843
    def push(self, target, overwrite=False, stop_revision=None, lossy=False):
2018.14.3 by Andrew Bennetts
Make a couple more branch_implementations tests pass.
3844
        self._ensure_real()
2018.5.97 by Andrew Bennetts
Fix more tests.
3845
        return self._real_branch.push(
5853.2.3 by Jelmer Vernooij
Fix lossy tests.
3846
            target, overwrite=overwrite, stop_revision=stop_revision, lossy=lossy,
2477.1.5 by Martin Pool
More cleanups of Branch.push to get the right behaviour with RemoteBranches
3847
            _override_hook_source_branch=self)
2018.14.3 by Andrew Bennetts
Make a couple more branch_implementations tests pass.
3848
6437.70.8 by John Arbash Meinel
trivially implement peek_lock_mode.
3849
    def peek_lock_mode(self):
3850
        return self._lock_mode
3851
2018.14.3 by Andrew Bennetts
Make a couple more branch_implementations tests pass.
3852
    def is_locked(self):
3853
        return self._lock_count >= 1
3854
3634.2.1 by John Arbash Meinel
Thunk over to the real branch's revision_id_to_revno.
3855
    @needs_read_lock
6263.1.2 by Jelmer Vernooij
Add ``Branch.revision_id_to_revno`` smart verb.
3856
    def revision_id_to_dotted_revno(self, revision_id):
3857
        """Given a revision id, return its dotted revno.
3858
3859
        :return: a tuple like (1,) or (400,1,3).
3860
        """
3861
        try:
3862
            response = self._call('Branch.revision_id_to_revno',
3863
                self._remote_path(), revision_id)
3864
        except errors.UnknownSmartMethod:
3865
            self._ensure_real()
6305.1.1 by Jelmer Vernooij
Add test for Branch.revision_id_to_dotted_revno fallback.
3866
            return self._real_branch.revision_id_to_dotted_revno(revision_id)
6263.1.2 by Jelmer Vernooij
Add ``Branch.revision_id_to_revno`` smart verb.
3867
        if response[0] == 'ok':
3868
            return tuple([int(x) for x in response[1:]])
3869
        else:
3870
            raise errors.UnexpectedSmartServerResponse(response)
3871
3872
    @needs_read_lock
3634.2.1 by John Arbash Meinel
Thunk over to the real branch's revision_id_to_revno.
3873
    def revision_id_to_revno(self, revision_id):
6263.1.2 by Jelmer Vernooij
Add ``Branch.revision_id_to_revno`` smart verb.
3874
        """Given a revision id on the branch mainline, return its revno.
3875
3876
        :return: an integer
3877
        """
3878
        try:
3879
            response = self._call('Branch.revision_id_to_revno',
3880
                self._remote_path(), revision_id)
3881
        except errors.UnknownSmartMethod:
3882
            self._ensure_real()
3883
            return self._real_branch.revision_id_to_revno(revision_id)
3884
        if response[0] == 'ok':
3885
            if len(response) == 2:
3886
                return int(response[1])
6263.1.6 by Jelmer Vernooij
Fix another test.
3887
            raise NoSuchRevision(self, revision_id)
6263.1.2 by Jelmer Vernooij
Add ``Branch.revision_id_to_revno`` smart verb.
3888
        else:
3889
            raise errors.UnexpectedSmartServerResponse(response)
3634.2.1 by John Arbash Meinel
Thunk over to the real branch's revision_id_to_revno.
3890
2892.2.1 by Andrew Bennetts
Add Branch.set_last_revision_info smart method, and make the RemoteBranch client use it.
3891
    @needs_write_lock
2018.5.83 by Andrew Bennetts
Fix some test failures caused by the switch from unicode to UTF-8-encoded strs for revision IDs.
3892
    def set_last_revision_info(self, revno, revision_id):
4005.2.1 by Robert Collins
Fix RemoteBranch to be used correctly in tests using bzr+ssh, to fire off Branch hooks correctly, and improve the branch_implementations tests to check that making a branch gets the right format under test.
3893
        # XXX: These should be returned by the set_last_revision_info verb
3894
        old_revno, old_revid = self.last_revision_info()
3895
        self._run_pre_change_branch_tip_hooks(revno, revision_id)
5803.1.1 by Jelmer Vernooij
Raise InvalidRevisionId on Branch.set_last_revision_info.
3896
        if not revision_id or not isinstance(revision_id, basestring):
3897
            raise errors.InvalidRevisionId(revision_id=revision_id, branch=self)
3297.4.2 by Andrew Bennetts
Add backwards compatibility for servers older than 1.4.
3898
        try:
3786.2.3 by Andrew Bennetts
Remove duplicated 'call & translate errors' code in bzrlib.remote.
3899
            response = self._call('Branch.set_last_revision_info',
3900
                self._remote_path(), self._lock_token, self._repo_lock_token,
3901
                str(revno), revision_id)
3297.4.2 by Andrew Bennetts
Add backwards compatibility for servers older than 1.4.
3902
        except errors.UnknownSmartMethod:
3903
            self._ensure_real()
3441.5.29 by Andrew Bennetts
More review tweaks: whitespace nits in test_smart, add (and use) ._clear_cached_state_of_remote_branch_only method in bzrlib/remote.py.
3904
            self._clear_cached_state_of_remote_branch_only()
3441.5.1 by Andrew Bennetts
Avoid necessarily calling get_parent_map when pushing.
3905
            self._real_branch.set_last_revision_info(revno, revision_id)
3906
            self._last_revision_info_cache = revno, revision_id
3907
            return
2892.2.1 by Andrew Bennetts
Add Branch.set_last_revision_info smart method, and make the RemoteBranch client use it.
3908
        if response == ('ok',):
3909
            self._clear_cached_state()
3441.5.1 by Andrew Bennetts
Avoid necessarily calling get_parent_map when pushing.
3910
            self._last_revision_info_cache = revno, revision_id
4005.2.1 by Robert Collins
Fix RemoteBranch to be used correctly in tests using bzr+ssh, to fire off Branch hooks correctly, and improve the branch_implementations tests to check that making a branch gets the right format under test.
3911
            self._run_post_change_branch_tip_hooks(old_revno, old_revid)
3441.5.29 by Andrew Bennetts
More review tweaks: whitespace nits in test_smart, add (and use) ._clear_cached_state_of_remote_branch_only method in bzrlib/remote.py.
3912
            # Update the _real_branch's cache too.
3913
            if self._real_branch is not None:
3914
                cache = self._last_revision_info_cache
3915
                self._real_branch._last_revision_info_cache = cache
2892.2.1 by Andrew Bennetts
Add Branch.set_last_revision_info smart method, and make the RemoteBranch client use it.
3916
        else:
3917
            raise errors.UnexpectedSmartServerResponse(response)
2018.5.83 by Andrew Bennetts
Fix some test failures caused by the switch from unicode to UTF-8-encoded strs for revision IDs.
3918
3441.5.27 by Andrew Bennetts
Tweaks suggested by John's review: rename _check_if_descendant_or_diverged, move caching last_revision_info into base Branch, better use of lock decorators.
3919
    @needs_write_lock
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.
3920
    def generate_revision_history(self, revision_id, last_rev=None,
3921
                                  other_branch=None):
3441.5.6 by Andrew Bennetts
Greatly simplify RemoteBranch.update_revisions. Still needs more tests.
3922
        medium = self._client._medium
3441.5.23 by Andrew Bennetts
Fix test failures.
3923
        if not medium._is_remote_before((1, 6)):
4005.2.1 by Robert Collins
Fix RemoteBranch to be used correctly in tests using bzr+ssh, to fire off Branch hooks correctly, and improve the branch_implementations tests to check that making a branch gets the right format under test.
3924
            # Use a smart method for 1.6 and above servers
3441.5.6 by Andrew Bennetts
Greatly simplify RemoteBranch.update_revisions. Still needs more tests.
3925
            try:
3441.5.18 by Andrew Bennetts
Fix some test failures.
3926
                self._set_last_revision_descendant(revision_id, other_branch,
3441.5.28 by Andrew Bennetts
Another review tweak: rename do_not_overwrite_descendant to allow_overwrite_descendant.
3927
                    allow_diverged=True, allow_overwrite_descendant=True)
3441.5.6 by Andrew Bennetts
Greatly simplify RemoteBranch.update_revisions. Still needs more tests.
3928
                return
3441.5.18 by Andrew Bennetts
Fix some test failures.
3929
            except errors.UnknownSmartMethod:
3441.5.23 by Andrew Bennetts
Fix test failures.
3930
                medium._remember_remote_is_before((1, 6))
3441.5.29 by Andrew Bennetts
More review tweaks: whitespace nits in test_smart, add (and use) ._clear_cached_state_of_remote_branch_only method in bzrlib/remote.py.
3931
        self._clear_cached_state_of_remote_branch_only()
6498.3.5 by Jelmer Vernooij
Fix some more tests.
3932
        graph = self.repository.get_graph()
3933
        (last_revno, last_revid) = self.last_revision_info()
3934
        known_revision_ids = [
3935
            (last_revid, last_revno),
3936
            (_mod_revision.NULL_REVISION, 0),
3937
            ]
3938
        if last_rev is not None:
3939
            if not graph.is_ancestor(last_rev, revision_id):
3940
                # our previous tip is not merged into stop_revision
3941
                raise errors.DivergedBranches(self, other_branch)
3942
        revno = graph.find_distance_to_null(revision_id, known_revision_ids)
3943
        self.set_last_revision_info(revno, revision_id)
2018.5.96 by Andrew Bennetts
Merge from bzr.dev, resolving the worst of the semantic conflicts, but there's
3944
2018.5.97 by Andrew Bennetts
Fix more tests.
3945
    def set_push_location(self, location):
6404.6.1 by Vincent Ladeuil
Tests passing for a first rough version of a cached branch config store. The changes here are too invasive and several parallel proposals have been made.
3946
        self._set_config_location('push_location', location)
2018.5.97 by Andrew Bennetts
Fix more tests.
3947
5741.1.11 by Jelmer Vernooij
Don't make heads_to_fetch() take a stop_revision.
3948
    def heads_to_fetch(self):
5672.1.7 by Andrew Bennetts
Use a more explicit method name.
3949
        if self._format._use_default_local_heads_to_fetch():
5672.1.5 by Andrew Bennetts
Add some tests for RemoteBranch.heads_to_fetch, and add release-note.
3950
            # We recognise this format, and its heads-to-fetch implementation
3951
            # is the default one (tip + tags).  In this case it's cheaper to
3952
            # just use the default implementation rather than a special RPC as
3953
            # the tip and tags data is cached.
5741.1.11 by Jelmer Vernooij
Don't make heads_to_fetch() take a stop_revision.
3954
            return branch.Branch.heads_to_fetch(self)
5672.1.4 by Andrew Bennetts
Fix final bzr-loom test by adding RemoteBranch.heads_to_fetch that can ask the remote branch for the heads to fetch (but uses the cheaper default logic if it knows the remote format has an identical heads_to_fetch as Branch.heads_to_fetch).
3955
        medium = self._client._medium
3956
        if medium._is_remote_before((2, 4)):
5741.1.11 by Jelmer Vernooij
Don't make heads_to_fetch() take a stop_revision.
3957
            return self._vfs_heads_to_fetch()
5672.1.4 by Andrew Bennetts
Fix final bzr-loom test by adding RemoteBranch.heads_to_fetch that can ask the remote branch for the heads to fetch (but uses the cheaper default logic if it knows the remote format has an identical heads_to_fetch as Branch.heads_to_fetch).
3958
        try:
5741.1.11 by Jelmer Vernooij
Don't make heads_to_fetch() take a stop_revision.
3959
            return self._rpc_heads_to_fetch()
5672.1.4 by Andrew Bennetts
Fix final bzr-loom test by adding RemoteBranch.heads_to_fetch that can ask the remote branch for the heads to fetch (but uses the cheaper default logic if it knows the remote format has an identical heads_to_fetch as Branch.heads_to_fetch).
3960
        except errors.UnknownSmartMethod:
3961
            medium._remember_remote_is_before((2, 4))
5741.1.11 by Jelmer Vernooij
Don't make heads_to_fetch() take a stop_revision.
3962
            return self._vfs_heads_to_fetch()
5672.1.4 by Andrew Bennetts
Fix final bzr-loom test by adding RemoteBranch.heads_to_fetch that can ask the remote branch for the heads to fetch (but uses the cheaper default logic if it knows the remote format has an identical heads_to_fetch as Branch.heads_to_fetch).
3963
5741.1.11 by Jelmer Vernooij
Don't make heads_to_fetch() take a stop_revision.
3964
    def _rpc_heads_to_fetch(self):
3965
        response = self._call('Branch.heads_to_fetch', self._remote_path())
5672.1.4 by Andrew Bennetts
Fix final bzr-loom test by adding RemoteBranch.heads_to_fetch that can ask the remote branch for the heads to fetch (but uses the cheaper default logic if it knows the remote format has an identical heads_to_fetch as Branch.heads_to_fetch).
3966
        if len(response) != 2:
3967
            raise errors.UnexpectedSmartServerResponse(response)
3968
        must_fetch, if_present_fetch = response
3969
        return set(must_fetch), set(if_present_fetch)
3970
5741.1.11 by Jelmer Vernooij
Don't make heads_to_fetch() take a stop_revision.
3971
    def _vfs_heads_to_fetch(self):
5672.1.4 by Andrew Bennetts
Fix final bzr-loom test by adding RemoteBranch.heads_to_fetch that can ask the remote branch for the heads to fetch (but uses the cheaper default logic if it knows the remote format has an identical heads_to_fetch as Branch.heads_to_fetch).
3972
        self._ensure_real()
5741.1.11 by Jelmer Vernooij
Don't make heads_to_fetch() take a stop_revision.
3973
        return self._real_branch.heads_to_fetch()
5672.1.4 by Andrew Bennetts
Fix final bzr-loom test by adding RemoteBranch.heads_to_fetch that can ask the remote branch for the heads to fetch (but uses the cheaper default logic if it knows the remote format has an identical heads_to_fetch as Branch.heads_to_fetch).
3974
2018.18.25 by Martin Pool
Repository.tarball fixes for python2.4
3975
4288.1.1 by Robert Collins
Add support for a RemoteBzrDirConfig to support optimising push operations which need to look for default stacking locations.
3976
class RemoteConfig(object):
3977
    """A Config that reads and writes from smart verbs.
4226.1.5 by Robert Collins
Reinstate the use of the Branch.get_config_file verb.
3978
3979
    It is a low-level object that considers config data to be name/value pairs
3980
    that may be associated with a section. Assigning meaning to the these
6622.1.34 by Jelmer Vernooij
Rename brzlib => breezy.
3981
    values is done at higher levels like breezy.config.TreeConfig.
4226.1.5 by Robert Collins
Reinstate the use of the Branch.get_config_file verb.
3982
    """
3983
3984
    def get_option(self, name, section=None, default=None):
3985
        """Return the value associated with a named option.
3986
3987
        :param name: The name of the value
3988
        :param section: The section the option is in (if any)
3989
        :param default: The value to return if the value is not set
3990
        :return: The value or default value
3991
        """
4288.1.1 by Robert Collins
Add support for a RemoteBzrDirConfig to support optimising push operations which need to look for default stacking locations.
3992
        try:
3993
            configobj = self._get_configobj()
5743.8.17 by Vincent Ladeuil
Add config old_get hook for remote config.
3994
            section_obj = None
4288.1.1 by Robert Collins
Add support for a RemoteBzrDirConfig to support optimising push operations which need to look for default stacking locations.
3995
            if section is None:
3996
                section_obj = configobj
3997
            else:
3998
                try:
3999
                    section_obj = configobj[section]
4000
                except KeyError:
5743.8.17 by Vincent Ladeuil
Add config old_get hook for remote config.
4001
                    pass
4002
            if section_obj is None:
4003
                value = default
4004
            else:
4005
                value = section_obj.get(name, default)
4288.1.1 by Robert Collins
Add support for a RemoteBzrDirConfig to support optimising push operations which need to look for default stacking locations.
4006
        except errors.UnknownSmartMethod:
5743.8.17 by Vincent Ladeuil
Add config old_get hook for remote config.
4007
            value = self._vfs_get_option(name, section, default)
6362.6.3 by Jelmer Vernooij
Fix compatibility after config stack changes.
4008
        for hook in _mod_config.OldConfigHooks['get']:
5743.8.17 by Vincent Ladeuil
Add config old_get hook for remote config.
4009
            hook(self, name, value)
4010
        return value
4226.1.5 by Robert Collins
Reinstate the use of the Branch.get_config_file verb.
4011
4288.1.1 by Robert Collins
Add support for a RemoteBzrDirConfig to support optimising push operations which need to look for default stacking locations.
4012
    def _response_to_configobj(self, response):
4288.1.2 by Robert Collins
Create a server verb for doing BzrDir.get_config()
4013
        if len(response[0]) and response[0][0] != 'ok':
4288.1.4 by Robert Collins
Remove the explicit set_parent method on RemoteBranch in favour of inheriting from Branch.
4014
            raise errors.UnexpectedSmartServerResponse(response)
4241.5.1 by Matt Nordhoff
Fix Branch.get_config_file smart verb on multi-line config files. (Bug #354075)
4015
        lines = response[1].read_body_bytes().splitlines()
6362.6.3 by Jelmer Vernooij
Fix compatibility after config stack changes.
4016
        conf = _mod_config.ConfigObj(lines, encoding='utf-8')
4017
        for hook in _mod_config.OldConfigHooks['load']:
5743.8.21 by Vincent Ladeuil
Add test for config load hook for remote configs.
4018
            hook(self)
4019
        return conf
4226.1.5 by Robert Collins
Reinstate the use of the Branch.get_config_file verb.
4020
4288.1.1 by Robert Collins
Add support for a RemoteBzrDirConfig to support optimising push operations which need to look for default stacking locations.
4021
4022
class RemoteBranchConfig(RemoteConfig):
4023
    """A RemoteConfig for Branches."""
4024
4025
    def __init__(self, branch):
4026
        self._branch = branch
4027
4028
    def _get_configobj(self):
4029
        path = self._branch._remote_path()
4030
        response = self._branch._client.call_expecting_body(
4031
            'Branch.get_config_file', path)
4032
        return self._response_to_configobj(response)
4033
4226.1.5 by Robert Collins
Reinstate the use of the Branch.get_config_file verb.
4034
    def set_option(self, value, name, section=None):
4035
        """Set the value associated with a named option.
4036
4037
        :param value: The value to set
4038
        :param name: The name of the value to set
4039
        :param section: The section the option is in (if any)
4040
        """
4226.2.1 by Robert Collins
Set branch config options via a smart method.
4041
        medium = self._branch._client._medium
4042
        if medium._is_remote_before((1, 14)):
4043
            return self._vfs_set_option(value, name, section)
5227.1.2 by Andrew Bennetts
Add Branch.set_config_option_dict RPC (and VFS fallback), fixes #430382.
4044
        if isinstance(value, dict):
4045
            if medium._is_remote_before((2, 2)):
4046
                return self._vfs_set_option(value, name, section)
4047
            return self._set_config_option_dict(value, name, section)
4048
        else:
4049
            return self._set_config_option(value, name, section)
4050
4051
    def _set_config_option(self, value, name, section):
4226.2.1 by Robert Collins
Set branch config options via a smart method.
4052
        try:
4053
            path = self._branch._remote_path()
4054
            response = self._branch._client.call('Branch.set_config_option',
4055
                path, self._branch._lock_token, self._branch._repo_lock_token,
4226.2.2 by Robert Collins
Fix setting config options to support unicode values and don't attempt to reset repositories _fallback_repositories as the simple approach fails to work.
4056
                value.encode('utf8'), name, section or '')
4226.2.1 by Robert Collins
Set branch config options via a smart method.
4057
        except errors.UnknownSmartMethod:
5227.1.2 by Andrew Bennetts
Add Branch.set_config_option_dict RPC (and VFS fallback), fixes #430382.
4058
            medium = self._branch._client._medium
4226.2.1 by Robert Collins
Set branch config options via a smart method.
4059
            medium._remember_remote_is_before((1, 14))
4060
            return self._vfs_set_option(value, name, section)
4061
        if response != ():
4062
            raise errors.UnexpectedSmartServerResponse(response)
4226.1.5 by Robert Collins
Reinstate the use of the Branch.get_config_file verb.
4063
5227.1.2 by Andrew Bennetts
Add Branch.set_config_option_dict RPC (and VFS fallback), fixes #430382.
4064
    def _serialize_option_dict(self, option_dict):
4065
        utf8_dict = {}
4066
        for key, value in option_dict.items():
4067
            if isinstance(key, unicode):
4068
                key = key.encode('utf8')
4069
            if isinstance(value, unicode):
4070
                value = value.encode('utf8')
4071
            utf8_dict[key] = value
4072
        return bencode.bencode(utf8_dict)
4073
4074
    def _set_config_option_dict(self, value, name, section):
4075
        try:
4076
            path = self._branch._remote_path()
4077
            serialised_dict = self._serialize_option_dict(value)
4078
            response = self._branch._client.call(
4079
                'Branch.set_config_option_dict',
4080
                path, self._branch._lock_token, self._branch._repo_lock_token,
4081
                serialised_dict, name, section or '')
4082
        except errors.UnknownSmartMethod:
4083
            medium = self._branch._client._medium
4084
            medium._remember_remote_is_before((2, 2))
4085
            return self._vfs_set_option(value, name, section)
4086
        if response != ():
4087
            raise errors.UnexpectedSmartServerResponse(response)
4088
4288.1.1 by Robert Collins
Add support for a RemoteBzrDirConfig to support optimising push operations which need to look for default stacking locations.
4089
    def _real_object(self):
4090
        self._branch._ensure_real()
4091
        return self._branch._real_branch
4092
4226.1.5 by Robert Collins
Reinstate the use of the Branch.get_config_file verb.
4093
    def _vfs_set_option(self, value, name, section=None):
4288.1.1 by Robert Collins
Add support for a RemoteBzrDirConfig to support optimising push operations which need to look for default stacking locations.
4094
        return self._real_object()._get_config().set_option(
4095
            value, name, section)
4096
4097
4098
class RemoteBzrDirConfig(RemoteConfig):
4099
    """A RemoteConfig for BzrDirs."""
4100
4101
    def __init__(self, bzrdir):
4102
        self._bzrdir = bzrdir
4103
4104
    def _get_configobj(self):
4288.1.4 by Robert Collins
Remove the explicit set_parent method on RemoteBranch in favour of inheriting from Branch.
4105
        medium = self._bzrdir._client._medium
4106
        verb = 'BzrDir.get_config_file'
4107
        if medium._is_remote_before((1, 15)):
4108
            raise errors.UnknownSmartMethod(verb)
4288.1.1 by Robert Collins
Add support for a RemoteBzrDirConfig to support optimising push operations which need to look for default stacking locations.
4109
        path = self._bzrdir._path_for_remote_call(self._bzrdir._client)
4110
        response = self._bzrdir._call_expecting_body(
4288.1.4 by Robert Collins
Remove the explicit set_parent method on RemoteBranch in favour of inheriting from Branch.
4111
            verb, path)
4288.1.1 by Robert Collins
Add support for a RemoteBzrDirConfig to support optimising push operations which need to look for default stacking locations.
4112
        return self._response_to_configobj(response)
4113
4114
    def _vfs_get_option(self, name, section, default):
4115
        return self._real_object()._get_config().get_option(
4116
            name, section, default)
4117
4118
    def set_option(self, value, name, section=None):
4119
        """Set the value associated with a named option.
4120
4121
        :param value: The value to set
4122
        :param name: The name of the value to set
4123
        :param section: The section the option is in (if any)
4124
        """
4125
        return self._real_object()._get_config().set_option(
4126
            value, name, section)
4127
4128
    def _real_object(self):
4129
        self._bzrdir._ensure_real()
4130
        return self._bzrdir._real_bzrdir
4131
4226.1.5 by Robert Collins
Reinstate the use of the Branch.get_config_file verb.
4132
2018.18.25 by Martin Pool
Repository.tarball fixes for python2.4
4133
def _extract_tar(tar, to_dir):
4134
    """Extract all the contents of a tarfile object.
4135
4136
    A replacement for extractall, which is not present in python2.4
4137
    """
4138
    for tarinfo in tar:
4139
        tar.extract(tarinfo, to_dir)
3533.3.1 by Andrew Bennetts
Remove duplication of error translation in bzrlib/remote.py.
4140
4141
6284.1.1 by Jelmer Vernooij
Allow registering custom error handlers in the HPSS client.
4142
error_translators = registry.Registry()
4143
no_context_error_translators = registry.Registry()
4144
4145
3533.3.1 by Andrew Bennetts
Remove duplication of error translation in bzrlib/remote.py.
4146
def _translate_error(err, **context):
4147
    """Translate an ErrorFromSmartServer into a more useful error.
4148
4149
    Possible context keys:
4150
      - branch
4151
      - repository
4152
      - bzrdir
4153
      - token
4154
      - other_branch
3779.3.2 by Andrew Bennetts
Unify error translation done in bzrlib.remote and bzrlib.transport.remote.
4155
      - path
3690.1.1 by Andrew Bennetts
Unexpected error responses from a smart server no longer cause the client to traceback.
4156
4157
    If the error from the server doesn't match a known pattern, then
3690.1.2 by Andrew Bennetts
Rename UntranslateableErrorFromSmartServer -> UnknownErrorFromSmartServer.
4158
    UnknownErrorFromSmartServer is raised.
3533.3.1 by Andrew Bennetts
Remove duplication of error translation in bzrlib/remote.py.
4159
    """
4160
    def find(name):
3533.3.4 by Andrew Bennetts
Add tests for _translate_error's robustness.
4161
        try:
4162
            return context[name]
6619.3.2 by Jelmer Vernooij
Apply 2to3 except fix.
4163
        except KeyError as key_err:
3779.3.2 by Andrew Bennetts
Unify error translation done in bzrlib.remote and bzrlib.transport.remote.
4164
            mutter('Missing key %r in context %r', key_err.args[0], context)
3533.3.4 by Andrew Bennetts
Add tests for _translate_error's robustness.
4165
            raise err
3779.3.2 by Andrew Bennetts
Unify error translation done in bzrlib.remote and bzrlib.transport.remote.
4166
    def get_path():
3779.3.3 by Andrew Bennetts
Add a docstring.
4167
        """Get the path from the context if present, otherwise use first error
4168
        arg.
4169
        """
3779.3.2 by Andrew Bennetts
Unify error translation done in bzrlib.remote and bzrlib.transport.remote.
4170
        try:
4171
            return context['path']
6619.3.2 by Jelmer Vernooij
Apply 2to3 except fix.
4172
        except KeyError as key_err:
3779.3.2 by Andrew Bennetts
Unify error translation done in bzrlib.remote and bzrlib.transport.remote.
4173
            try:
4174
                return err.error_args[0]
6619.3.2 by Jelmer Vernooij
Apply 2to3 except fix.
4175
            except IndexError as idx_err:
3779.3.2 by Andrew Bennetts
Unify error translation done in bzrlib.remote and bzrlib.transport.remote.
4176
                mutter(
4177
                    'Missing key %r in context %r', key_err.args[0], context)
4178
                raise err
4179
6284.1.1 by Jelmer Vernooij
Allow registering custom error handlers in the HPSS client.
4180
    try:
4181
        translator = error_translators.get(err.error_verb)
4182
    except KeyError:
4183
        pass
4184
    else:
4185
        raise translator(err, find, get_path)
4186
    try:
4187
        translator = no_context_error_translators.get(err.error_verb)
4188
    except KeyError:
4189
        raise errors.UnknownErrorFromSmartServer(err)
4190
    else:
4191
        raise translator(err)
4192
4193
4194
error_translators.register('NoSuchRevision',
4195
    lambda err, find, get_path: NoSuchRevision(
4196
        find('branch'), err.error_args[0]))
4197
error_translators.register('nosuchrevision',
4198
    lambda err, find, get_path: NoSuchRevision(
4199
        find('repository'), err.error_args[0]))
4200
4201
def _translate_nobranch_error(err, find, get_path):
4202
    if len(err.error_args) >= 1:
4203
        extra = err.error_args[0]
4204
    else:
4205
        extra = None
4206
    return errors.NotBranchError(path=find('bzrdir').root_transport.base,
4207
        detail=extra)
4208
4209
error_translators.register('nobranch', _translate_nobranch_error)
4210
error_translators.register('norepository',
4211
    lambda err, find, get_path: errors.NoRepositoryPresent(
4212
        find('bzrdir')))
4213
error_translators.register('UnlockableTransport',
4214
    lambda err, find, get_path: errors.UnlockableTransport(
4215
        find('bzrdir').root_transport))
4216
error_translators.register('TokenMismatch',
4217
    lambda err, find, get_path: errors.TokenMismatch(
4218
        find('token'), '(remote token)'))
4219
error_translators.register('Diverged',
4220
    lambda err, find, get_path: errors.DivergedBranches(
4221
        find('branch'), find('other_branch')))
4222
error_translators.register('NotStacked',
4223
    lambda err, find, get_path: errors.NotStacked(branch=find('branch')))
4224
4225
def _translate_PermissionDenied(err, find, get_path):
4226
    path = get_path()
4227
    if len(err.error_args) >= 2:
4228
        extra = err.error_args[1]
4229
    else:
4230
        extra = None
4231
    return errors.PermissionDenied(path, extra=extra)
4232
4233
error_translators.register('PermissionDenied', _translate_PermissionDenied)
4234
error_translators.register('ReadError',
4235
    lambda err, find, get_path: errors.ReadError(get_path()))
4236
error_translators.register('NoSuchFile',
4237
    lambda err, find, get_path: errors.NoSuchFile(get_path()))
6300.1.7 by Jelmer Vernooij
Fix test.
4238
error_translators.register('TokenLockingNotSupported',
4239
    lambda err, find, get_path: errors.TokenLockingNotSupported(
4240
        find('repository')))
6280.10.31 by Jelmer Vernooij
Merge bzr.dev.
4241
error_translators.register('UnsuspendableWriteGroup',
4242
    lambda err, find, get_path: errors.UnsuspendableWriteGroup(
4243
        repository=find('repository')))
4244
error_translators.register('UnresumableWriteGroup',
4245
    lambda err, find, get_path: errors.UnresumableWriteGroup(
4246
        repository=find('repository'), write_groups=err.error_args[0],
4247
        reason=err.error_args[1]))
6284.1.1 by Jelmer Vernooij
Allow registering custom error handlers in the HPSS client.
4248
no_context_error_translators.register('IncompatibleRepositories',
4249
    lambda err: errors.IncompatibleRepositories(
4250
        err.error_args[0], err.error_args[1], err.error_args[2]))
4251
no_context_error_translators.register('LockContention',
4252
    lambda err: errors.LockContention('(remote lock)'))
4253
no_context_error_translators.register('LockFailed',
4254
    lambda err: errors.LockFailed(err.error_args[0], err.error_args[1]))
4255
no_context_error_translators.register('TipChangeRejected',
4256
    lambda err: errors.TipChangeRejected(err.error_args[0].decode('utf8')))
4257
no_context_error_translators.register('UnstackableBranchFormat',
4258
    lambda err: errors.UnstackableBranchFormat(*err.error_args))
4259
no_context_error_translators.register('UnstackableRepositoryFormat',
4260
    lambda err: errors.UnstackableRepositoryFormat(*err.error_args))
4261
no_context_error_translators.register('FileExists',
4262
    lambda err: errors.FileExists(err.error_args[0]))
4263
no_context_error_translators.register('DirectoryNotEmpty',
4264
    lambda err: errors.DirectoryNotEmpty(err.error_args[0]))
4265
4266
def _translate_short_readv_error(err):
4267
    args = err.error_args
4268
    return errors.ShortReadvError(args[0], int(args[1]), int(args[2]),
4269
        int(args[3]))
4270
4271
no_context_error_translators.register('ShortReadvError',
4272
    _translate_short_readv_error)
4273
4274
def _translate_unicode_error(err):
3779.3.2 by Andrew Bennetts
Unify error translation done in bzrlib.remote and bzrlib.transport.remote.
4275
        encoding = str(err.error_args[0]) # encoding must always be a string
4276
        val = err.error_args[1]
4277
        start = int(err.error_args[2])
4278
        end = int(err.error_args[3])
4279
        reason = str(err.error_args[4]) # reason must always be a string
4280
        if val.startswith('u:'):
4281
            val = val[2:].decode('utf-8')
4282
        elif val.startswith('s:'):
4283
            val = val[2:].decode('base64')
3786.2.3 by Andrew Bennetts
Remove duplicated 'call & translate errors' code in bzrlib.remote.
4284
        if err.error_verb == 'UnicodeDecodeError':
3779.3.2 by Andrew Bennetts
Unify error translation done in bzrlib.remote and bzrlib.transport.remote.
4285
            raise UnicodeDecodeError(encoding, val, start, end, reason)
3786.2.3 by Andrew Bennetts
Remove duplicated 'call & translate errors' code in bzrlib.remote.
4286
        elif err.error_verb == 'UnicodeEncodeError':
3779.3.2 by Andrew Bennetts
Unify error translation done in bzrlib.remote and bzrlib.transport.remote.
4287
            raise UnicodeEncodeError(encoding, val, start, end, reason)
6284.1.1 by Jelmer Vernooij
Allow registering custom error handlers in the HPSS client.
4288
4289
no_context_error_translators.register('UnicodeEncodeError',
4290
    _translate_unicode_error)
4291
no_context_error_translators.register('UnicodeDecodeError',
4292
    _translate_unicode_error)
4293
no_context_error_translators.register('ReadOnlyError',
4294
    lambda err: errors.TransportNotPossible('readonly transport'))
4295
no_context_error_translators.register('MemoryError',
4296
    lambda err: errors.BzrError("remote server out of memory\n"
4297
        "Retry non-remotely, or contact the server admin for details."))
6280.10.28 by Jelmer Vernooij
merge bzr.dev.
4298
no_context_error_translators.register('RevisionNotPresent',
4299
    lambda err: errors.RevisionNotPresent(err.error_args[0], err.error_args[1]))
4300
6280.7.13 by Jelmer Vernooij
Merge bzr.dev.
4301
no_context_error_translators.register('BzrCheckError',
4302
    lambda err: errors.BzrCheckError(msg=err.error_args[0]))
4303