/brz/remove-bazaar

To get this branch, use:
bzr branch http://gegoxaren.bato24.eu/bzr/brz/remove-bazaar

« back to all changes in this revision

Viewing changes to bzrlib/bzrdir.py

  • Committer: Robert Collins
  • Date: 2010-05-11 08:36:16 UTC
  • mto: This revision was merged to the branch mainline in revision 5223.
  • Revision ID: robertc@robertcollins.net-20100511083616-b8fjb19zomwupid0
Make all lock methods return Result objects, rather than lock_read returning self, as per John's review.

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
 
# Copyright (C) 2005, 2006, 2007, 2008 Canonical Ltd
 
1
# Copyright (C) 2006-2010 Canonical Ltd
2
2
#
3
3
# This program is free software; you can redistribute it and/or modify
4
4
# it under the terms of the GNU General Public License as published by
12
12
#
13
13
# You should have received a copy of the GNU General Public License
14
14
# along with this program; if not, write to the Free Software
15
 
# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
 
15
# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
16
16
 
17
17
"""BzrDir logic. The BzrDir is the basic control directory used by bzr.
18
18
 
29
29
 
30
30
import os
31
31
import sys
 
32
import warnings
32
33
 
33
34
from bzrlib.lazy_import import lazy_import
34
35
lazy_import(globals(), """
37
38
 
38
39
import bzrlib
39
40
from bzrlib import (
 
41
    branch,
40
42
    config,
41
43
    errors,
42
44
    graph,
44
46
    lockdir,
45
47
    osutils,
46
48
    remote,
 
49
    repository,
47
50
    revision as _mod_revision,
48
51
    ui,
49
52
    urlutils,
57
60
from bzrlib.osutils import (
58
61
    sha_string,
59
62
    )
 
63
from bzrlib.push import (
 
64
    PushResult,
 
65
    )
 
66
from bzrlib.repofmt import pack_repo
60
67
from bzrlib.smart.client import _SmartClient
61
68
from bzrlib.store.versioned import WeaveStore
62
69
from bzrlib.transactions import WriteTransaction
71
78
from bzrlib.trace import (
72
79
    mutter,
73
80
    note,
 
81
    warning,
74
82
    )
75
83
 
76
84
from bzrlib import (
 
85
    hooks,
77
86
    registry,
78
87
    symbol_versioning,
79
88
    )
80
 
 
81
 
 
82
 
class BzrDir(object):
 
89
    
 
90
    
 
91
class ControlComponent(object):
 
92
    """Abstract base class for control directory components.
 
93
    
 
94
    This provides interfaces that are common across bzrdirs, 
 
95
    repositories, branches, and workingtree control directories.
 
96
    
 
97
    They all expose two urls and transports: the *user* URL is the 
 
98
    one that stops above the control directory (eg .bzr) and that 
 
99
    should normally be used in messages, and the *control* URL is
 
100
    under that in eg .bzr/checkout and is used to read the control
 
101
    files.
 
102
    
 
103
    This can be used as a mixin and is intended to fit with 
 
104
    foreign formats.
 
105
    """
 
106
    
 
107
    @property
 
108
    def control_transport(self):
 
109
        raise NotImplementedError
 
110
   
 
111
    @property
 
112
    def control_url(self):
 
113
        return self.control_transport.base
 
114
    
 
115
    @property
 
116
    def user_transport(self):
 
117
        raise NotImplementedError
 
118
        
 
119
    @property
 
120
    def user_url(self):
 
121
        return self.user_transport.base
 
122
    
 
123
 
 
124
class BzrDir(ControlComponent):
83
125
    """A .bzr control diretory.
84
 
    
 
126
 
85
127
    BzrDir instances let you create or open any of the things that can be
86
128
    found within .bzr - checkouts, branches and repositories.
87
 
    
 
129
 
88
130
    :ivar transport:
89
131
        the transport which this bzr dir is rooted at (i.e. file:///.../.bzr/)
90
132
    :ivar root_transport:
92
134
        (i.e. the parent directory holding the .bzr directory).
93
135
 
94
136
    Everything in the bzrdir should have the same file permissions.
 
137
 
 
138
    :cvar hooks: An instance of BzrDirHooks.
95
139
    """
96
140
 
97
141
    def break_lock(self):
119
163
        return True
120
164
 
121
165
    def check_conversion_target(self, target_format):
 
166
        """Check that a bzrdir as a whole can be converted to a new format."""
 
167
        # The only current restriction is that the repository content can be 
 
168
        # fetched compatibly with the target.
122
169
        target_repo_format = target_format.repository_format
123
 
        source_repo_format = self._format.repository_format
124
 
        source_repo_format.check_conversion_target(target_repo_format)
 
170
        try:
 
171
            self.open_repository()._format.check_conversion_target(
 
172
                target_repo_format)
 
173
        except errors.NoRepositoryPresent:
 
174
            # No repo, no problem.
 
175
            pass
125
176
 
126
177
    @staticmethod
127
178
    def _check_supported(format, allow_unsupported,
129
180
        basedir=None):
130
181
        """Give an error or warning on old formats.
131
182
 
132
 
        :param format: may be any kind of format - workingtree, branch, 
 
183
        :param format: may be any kind of format - workingtree, branch,
133
184
        or repository.
134
185
 
135
 
        :param allow_unsupported: If true, allow opening 
136
 
        formats that are strongly deprecated, and which may 
 
186
        :param allow_unsupported: If true, allow opening
 
187
        formats that are strongly deprecated, and which may
137
188
        have limited functionality.
138
189
 
139
190
        :param recommend_upgrade: If true (default), warn
171
222
                                       preserve_stacking=preserve_stacking)
172
223
 
173
224
    def clone_on_transport(self, transport, revision_id=None,
174
 
                           force_new_repo=False, preserve_stacking=False,
175
 
                           stacked_on=None):
 
225
        force_new_repo=False, preserve_stacking=False, stacked_on=None,
 
226
        create_prefix=False, use_existing_dir=True):
176
227
        """Clone this bzrdir and its contents to transport verbatim.
177
228
 
178
229
        :param transport: The transport for the location to produce the clone
184
235
                               even if one is available.
185
236
        :param preserve_stacking: When cloning a stacked branch, stack the
186
237
            new branch on top of the other branch's stacked-on branch.
 
238
        :param create_prefix: Create any missing directories leading up to
 
239
            to_transport.
 
240
        :param use_existing_dir: Use an existing directory if one exists.
187
241
        """
188
 
        transport.ensure_base()
 
242
        # Overview: put together a broad description of what we want to end up
 
243
        # with; then make as few api calls as possible to do it.
 
244
        
 
245
        # We may want to create a repo/branch/tree, if we do so what format
 
246
        # would we want for each:
189
247
        require_stacking = (stacked_on is not None)
190
 
        metadir = self.cloning_metadir(require_stacking)
191
 
        result = metadir.initialize_on_transport(transport)
192
 
        repository_policy = None
 
248
        format = self.cloning_metadir(require_stacking)
 
249
        
 
250
        # Figure out what objects we want:
193
251
        try:
194
252
            local_repo = self.find_repository()
195
253
        except errors.NoRepositoryPresent:
209
267
                        errors.UnstackableRepositoryFormat,
210
268
                        errors.NotStacked):
211
269
                    pass
212
 
 
 
270
        # Bug: We create a metadir without knowing if it can support stacking,
 
271
        # we should look up the policy needs first, or just use it as a hint,
 
272
        # or something.
213
273
        if local_repo:
214
 
            # may need to copy content in
215
 
            repository_policy = result.determine_repository_policy(
216
 
                force_new_repo, stacked_on, self.root_transport.base,
217
 
                require_stacking=require_stacking)
218
274
            make_working_trees = local_repo.make_working_trees()
219
 
            result_repo = repository_policy.acquire_repository(
220
 
                make_working_trees, local_repo.is_shared())
221
 
            result_repo.fetch(local_repo, revision_id=revision_id)
222
 
        else:
223
 
            result_repo = None
 
275
            want_shared = local_repo.is_shared()
 
276
            repo_format_name = format.repository_format.network_name()
 
277
        else:
 
278
            make_working_trees = False
 
279
            want_shared = False
 
280
            repo_format_name = None
 
281
 
 
282
        result_repo, result, require_stacking, repository_policy = \
 
283
            format.initialize_on_transport_ex(transport,
 
284
            use_existing_dir=use_existing_dir, create_prefix=create_prefix,
 
285
            force_new_repo=force_new_repo, stacked_on=stacked_on,
 
286
            stack_on_pwd=self.root_transport.base,
 
287
            repo_format_name=repo_format_name,
 
288
            make_working_trees=make_working_trees, shared_repo=want_shared)
 
289
        if repo_format_name:
 
290
            try:
 
291
                # If the result repository is in the same place as the
 
292
                # resulting bzr dir, it will have no content, further if the
 
293
                # result is not stacked then we know all content should be
 
294
                # copied, and finally if we are copying up to a specific
 
295
                # revision_id then we can use the pending-ancestry-result which
 
296
                # does not require traversing all of history to describe it.
 
297
                if (result_repo.user_url == result.user_url
 
298
                    and not require_stacking and
 
299
                    revision_id is not None):
 
300
                    fetch_spec = graph.PendingAncestryResult(
 
301
                        [revision_id], local_repo)
 
302
                    result_repo.fetch(local_repo, fetch_spec=fetch_spec)
 
303
                else:
 
304
                    result_repo.fetch(local_repo, revision_id=revision_id)
 
305
            finally:
 
306
                result_repo.unlock()
 
307
        else:
 
308
            if result_repo is not None:
 
309
                raise AssertionError('result_repo not None(%r)' % result_repo)
224
310
        # 1 if there is a branch present
225
311
        #   make sure its content is available in the target repository
226
312
        #   clone it.
227
313
        if local_branch is not None:
228
 
            result_branch = local_branch.clone(result, revision_id=revision_id)
229
 
            if repository_policy is not None:
230
 
                repository_policy.configure_branch(result_branch)
231
 
        if result_repo is None or result_repo.make_working_trees():
232
 
            try:
 
314
            result_branch = local_branch.clone(result, revision_id=revision_id,
 
315
                repository_policy=repository_policy)
 
316
        try:
 
317
            # Cheaper to check if the target is not local, than to try making
 
318
            # the tree and fail.
 
319
            result.root_transport.local_abspath('.')
 
320
            if result_repo is None or result_repo.make_working_trees():
233
321
                self.open_workingtree().clone(result)
234
 
            except (errors.NoWorkingTree, errors.NotLocalUrl):
235
 
                pass
 
322
        except (errors.NoWorkingTree, errors.NotLocalUrl):
 
323
            pass
236
324
        return result
237
325
 
238
326
    # TODO: This should be given a Transport, and should chdir up; otherwise
244
332
    @classmethod
245
333
    def create(cls, base, format=None, possible_transports=None):
246
334
        """Create a new BzrDir at the url 'base'.
247
 
        
 
335
 
248
336
        :param format: If supplied, the format of branch to create.  If not
249
337
            supplied, the default is used.
250
 
        :param possible_transports: If supplied, a list of transports that 
 
338
        :param possible_transports: If supplied, a list of transports that
251
339
            can be reused to share a remote connection.
252
340
        """
253
341
        if cls is not BzrDir:
300
388
                for subdir in sorted(subdirs, reverse=True):
301
389
                    pending.append(current_transport.clone(subdir))
302
390
 
 
391
    def list_branches(self):
 
392
        """Return a sequence of all branches local to this control directory.
 
393
 
 
394
        """
 
395
        try:
 
396
            return [self.open_branch()]
 
397
        except errors.NotBranchError:
 
398
            return []
 
399
 
303
400
    @staticmethod
304
401
    def find_branches(transport):
305
402
        """Find all branches under a transport.
317
414
            except errors.NoRepositoryPresent:
318
415
                pass
319
416
            else:
320
 
                return False, (None, repository)
321
 
            try:
322
 
                branch = bzrdir.open_branch()
323
 
            except errors.NotBranchError:
324
 
                return True, (None, None)
325
 
            else:
326
 
                return True, (branch, None)
327
 
        branches = []
328
 
        for branch, repo in BzrDir.find_bzrdirs(transport, evaluate=evaluate):
 
417
                return False, ([], repository)
 
418
            return True, (bzrdir.list_branches(), None)
 
419
        ret = []
 
420
        for branches, repo in BzrDir.find_bzrdirs(transport,
 
421
                                                  evaluate=evaluate):
329
422
            if repo is not None:
330
 
                branches.extend(repo.find_branches())
331
 
            if branch is not None:
332
 
                branches.append(branch)
333
 
        return branches
 
423
                ret.extend(repo.find_branches())
 
424
            if branches is not None:
 
425
                ret.extend(branches)
 
426
        return ret
334
427
 
335
428
    def destroy_repository(self):
336
429
        """Destroy the repository in this BzrDir"""
337
430
        raise NotImplementedError(self.destroy_repository)
338
431
 
339
 
    def create_branch(self):
 
432
    def create_branch(self, name=None):
340
433
        """Create a branch in this BzrDir.
341
434
 
 
435
        :param name: Name of the colocated branch to create, None for
 
436
            the default branch.
 
437
 
342
438
        The bzrdir's format will control what branch format is created.
343
439
        For more control see BranchFormatXX.create(a_bzrdir).
344
440
        """
345
441
        raise NotImplementedError(self.create_branch)
346
442
 
347
 
    def destroy_branch(self):
348
 
        """Destroy the branch in this BzrDir"""
 
443
    def destroy_branch(self, name=None):
 
444
        """Destroy a branch in this BzrDir.
 
445
        
 
446
        :param name: Name of the branch to destroy, None for the default 
 
447
            branch.
 
448
        """
349
449
        raise NotImplementedError(self.destroy_branch)
350
450
 
351
451
    @staticmethod
353
453
        """Create a new BzrDir, Branch and Repository at the url 'base'.
354
454
 
355
455
        This will use the current default BzrDirFormat unless one is
356
 
        specified, and use whatever 
 
456
        specified, and use whatever
357
457
        repository format that that uses via bzrdir.create_branch and
358
458
        create_repository. If a shared repository is available that is used
359
459
        preferentially.
373
473
                                    stack_on_pwd=None, require_stacking=False):
374
474
        """Return an object representing a policy to use.
375
475
 
376
 
        This controls whether a new repository is created, or a shared
377
 
        repository used instead.
 
476
        This controls whether a new repository is created, and the format of
 
477
        that repository, or some existing shared repository used instead.
378
478
 
379
479
        If stack_on is supplied, will not seek a containing shared repo.
380
480
 
389
489
            stack_on_pwd = None
390
490
            config = found_bzrdir.get_config()
391
491
            stop = False
392
 
            if config is not None:
393
 
                stack_on = config.get_default_stack_on()
394
 
                if stack_on is not None:
395
 
                    stack_on_pwd = found_bzrdir.root_transport.base
396
 
                    stop = True
397
 
                    note('Using default stacking branch %s at %s', stack_on,
398
 
                         stack_on_pwd)
 
492
            stack_on = config.get_default_stack_on()
 
493
            if stack_on is not None:
 
494
                stack_on_pwd = found_bzrdir.user_url
 
495
                stop = True
399
496
            # does it have a repository ?
400
497
            try:
401
498
                repository = found_bzrdir.open_repository()
402
499
            except errors.NoRepositoryPresent:
403
500
                repository = None
404
501
            else:
405
 
                if ((found_bzrdir.root_transport.base !=
406
 
                     self.root_transport.base) and not repository.is_shared()):
 
502
                if (found_bzrdir.user_url != self.user_url 
 
503
                    and not repository.is_shared()):
 
504
                    # Don't look higher, can't use a higher shared repo.
407
505
                    repository = None
 
506
                    stop = True
408
507
                else:
409
508
                    stop = True
410
509
            if not stop:
434
533
    def _find_or_create_repository(self, force_new_repo):
435
534
        """Create a new repository if needed, returning the repository."""
436
535
        policy = self.determine_repository_policy(force_new_repo)
437
 
        return policy.acquire_repository()
 
536
        return policy.acquire_repository()[0]
438
537
 
439
538
    @staticmethod
440
539
    def create_branch_convenience(base, force_new_repo=False,
447
546
        not.
448
547
 
449
548
        This will use the current default BzrDirFormat unless one is
450
 
        specified, and use whatever 
 
549
        specified, and use whatever
451
550
        repository format that that uses via bzrdir.create_branch and
452
551
        create_repository. If a shared repository is available that is used
453
552
        preferentially. Whatever repository is used, its tree creation policy
455
554
 
456
555
        The created Branch object is returned.
457
556
        If a working tree cannot be made due to base not being a file:// url,
458
 
        no error is raised unless force_new_tree is True, in which case no 
 
557
        no error is raised unless force_new_tree is True, in which case no
459
558
        data is created on disk and NotLocalUrl is raised.
460
559
 
461
560
        :param base: The URL to create the branch at.
462
561
        :param force_new_repo: If True a new repository is always created.
463
 
        :param force_new_tree: If True or False force creation of a tree or 
 
562
        :param force_new_tree: If True or False force creation of a tree or
464
563
                               prevent such creation respectively.
465
564
        :param format: Override for the bzrdir format to create.
466
565
        :param possible_transports: An optional reusable transports list.
488
587
        'base' must be a local path or a file:// url.
489
588
 
490
589
        This will use the current default BzrDirFormat unless one is
491
 
        specified, and use whatever 
 
590
        specified, and use whatever
492
591
        repository format that that uses for bzrdirformat.create_workingtree,
493
592
        create_branch and create_repository.
494
593
 
506
605
    def create_workingtree(self, revision_id=None, from_branch=None,
507
606
        accelerator_tree=None, hardlink=False):
508
607
        """Create a working tree at this BzrDir.
509
 
        
 
608
 
510
609
        :param revision_id: create it as of this revision id.
511
610
        :param from_branch: override bzrdir branch (for lightweight checkouts)
512
611
        :param accelerator_tree: A tree which can be used for retrieving file
516
615
        """
517
616
        raise NotImplementedError(self.create_workingtree)
518
617
 
 
618
    def backup_bzrdir(self):
 
619
        """Backup this bzr control directory.
 
620
 
 
621
        :return: Tuple with old path name and new path name
 
622
        """
 
623
        def name_gen(base='backup.bzr'):
 
624
            counter = 1
 
625
            name = "%s.~%d~" % (base, counter)
 
626
            while self.root_transport.has(name):
 
627
                counter += 1
 
628
                name = "%s.~%d~" % (base, counter)
 
629
            return name
 
630
 
 
631
        backup_dir=name_gen()
 
632
        pb = ui.ui_factory.nested_progress_bar()
 
633
        try:
 
634
            # FIXME: bug 300001 -- the backup fails if the backup directory
 
635
            # already exists, but it should instead either remove it or make
 
636
            # a new backup directory.
 
637
            #
 
638
            old_path = self.root_transport.abspath('.bzr')
 
639
            new_path = self.root_transport.abspath(backup_dir)
 
640
            ui.ui_factory.note('making backup of %s\n  to %s' % (old_path, new_path,))
 
641
            self.root_transport.copy_tree('.bzr', backup_dir)
 
642
            return (old_path, new_path)
 
643
        finally:
 
644
            pb.finished()
 
645
 
519
646
    def retire_bzrdir(self, limit=10000):
520
647
        """Permanently disable the bzrdir.
521
648
 
575
702
            if stop:
576
703
                return result
577
704
            next_transport = found_bzrdir.root_transport.clone('..')
578
 
            if (found_bzrdir.root_transport.base == next_transport.base):
 
705
            if (found_bzrdir.user_url == next_transport.base):
579
706
                # top of the file system
580
707
                return None
581
708
            # find the next containing bzrdir
598
725
                repository = found_bzrdir.open_repository()
599
726
            except errors.NoRepositoryPresent:
600
727
                return None, False
601
 
            if found_bzrdir.root_transport.base == self.root_transport.base:
 
728
            if found_bzrdir.user_url == self.user_url:
602
729
                return repository, True
603
730
            elif repository.is_shared():
604
731
                return repository, True
619
746
        """
620
747
        return None
621
748
 
622
 
    def get_branch_transport(self, branch_format):
 
749
    def get_branch_transport(self, branch_format, name=None):
623
750
        """Get the transport for use by branch format in this BzrDir.
624
751
 
625
752
        Note that bzr dirs that do not support format strings will raise
626
753
        IncompatibleFormat if the branch format they are given has
627
754
        a format string, and vice versa.
628
755
 
629
 
        If branch_format is None, the transport is returned with no 
 
756
        If branch_format is None, the transport is returned with no
630
757
        checking. If it is not None, then the returned transport is
631
758
        guaranteed to point to an existing directory ready for use.
632
759
        """
675
802
        if not self._mode_check_done:
676
803
            self._find_creation_modes()
677
804
        return self._dir_mode
678
 
        
 
805
 
679
806
    def get_repository_transport(self, repository_format):
680
807
        """Get the transport for use by repository format in this BzrDir.
681
808
 
683
810
        IncompatibleFormat if the repository format they are given has
684
811
        a format string, and vice versa.
685
812
 
686
 
        If repository_format is None, the transport is returned with no 
 
813
        If repository_format is None, the transport is returned with no
687
814
        checking. If it is not None, then the returned transport is
688
815
        guaranteed to point to an existing directory ready for use.
689
816
        """
690
817
        raise NotImplementedError(self.get_repository_transport)
691
 
        
 
818
 
692
819
    def get_workingtree_transport(self, tree_format):
693
820
        """Get the transport for use by workingtree format in this BzrDir.
694
821
 
696
823
        IncompatibleFormat if the workingtree format they are given has a
697
824
        format string, and vice versa.
698
825
 
699
 
        If workingtree_format is None, the transport is returned with no 
 
826
        If workingtree_format is None, the transport is returned with no
700
827
        checking. If it is not None, then the returned transport is
701
828
        guaranteed to point to an existing directory ready for use.
702
829
        """
703
830
        raise NotImplementedError(self.get_workingtree_transport)
704
831
 
705
832
    def get_config(self):
706
 
        if getattr(self, '_get_config', None) is None:
707
 
            return None
708
 
        return self._get_config()
 
833
        """Get configuration for this BzrDir."""
 
834
        return config.BzrDirConfig(self)
 
835
 
 
836
    def _get_config(self):
 
837
        """By default, no configuration is available."""
 
838
        return None
709
839
 
710
840
    def __init__(self, _transport, _format):
711
841
        """Initialize a Bzr control dir object.
712
 
        
 
842
 
713
843
        Only really common logic should reside here, concrete classes should be
714
844
        made with varying behaviours.
715
845
 
717
847
        :param _transport: the transport this dir is based at.
718
848
        """
719
849
        self._format = _format
 
850
        # these are also under the more standard names of 
 
851
        # control_transport and user_transport
720
852
        self.transport = _transport.clone('.bzr')
721
853
        self.root_transport = _transport
722
854
        self._mode_check_done = False
 
855
        
 
856
    @property 
 
857
    def user_transport(self):
 
858
        return self.root_transport
 
859
        
 
860
    @property
 
861
    def control_transport(self):
 
862
        return self.transport
723
863
 
724
864
    def is_control_filename(self, filename):
725
865
        """True if filename is the name of a path which is reserved for bzrdir's.
726
 
        
 
866
 
727
867
        :param filename: A filename within the root transport of this bzrdir.
728
868
 
729
869
        This is true IF and ONLY IF the filename is part of the namespace reserved
732
872
        this in the future - for instance to make bzr talk with svn working
733
873
        trees.
734
874
        """
735
 
        # this might be better on the BzrDirFormat class because it refers to 
736
 
        # all the possible bzrdir disk formats. 
737
 
        # This method is tested via the workingtree is_control_filename tests- 
 
875
        # this might be better on the BzrDirFormat class because it refers to
 
876
        # all the possible bzrdir disk formats.
 
877
        # This method is tested via the workingtree is_control_filename tests-
738
878
        # it was extracted from WorkingTree.is_control_filename. If the method's
739
879
        # contract is extended beyond the current trivial implementation, please
740
880
        # add new tests for it to the appropriate place.
742
882
 
743
883
    def needs_format_conversion(self, format=None):
744
884
        """Return true if this bzrdir needs convert_format run on it.
745
 
        
746
 
        For instance, if the repository format is out of date but the 
 
885
 
 
886
        For instance, if the repository format is out of date but the
747
887
        branch and working tree are not, this should return True.
748
888
 
749
889
        :param format: Optional parameter indicating a specific desired
755
895
    def open_unsupported(base):
756
896
        """Open a branch which is not supported."""
757
897
        return BzrDir.open(base, _unsupported=True)
758
 
        
 
898
 
759
899
    @staticmethod
760
900
    def open(base, _unsupported=False, possible_transports=None):
761
901
        """Open an existing bzrdir, rooted at 'base' (url).
762
 
        
 
902
 
763
903
        :param _unsupported: a private parameter to the BzrDir class.
764
904
        """
765
905
        t = get_transport(base, possible_transports=possible_transports)
773
913
        :param transport: Transport containing the bzrdir.
774
914
        :param _unsupported: private.
775
915
        """
 
916
        for hook in BzrDir.hooks['pre_open']:
 
917
            hook(transport)
 
918
        # Keep initial base since 'transport' may be modified while following
 
919
        # the redirections.
776
920
        base = transport.base
777
 
 
778
921
        def find_format(transport):
779
922
            return transport, BzrDirFormat.find_format(
780
923
                transport, _server_formats=_server_formats)
781
924
 
782
925
        def redirected(transport, e, redirection_notice):
783
 
            qualified_source = e.get_source_url()
784
 
            relpath = transport.relpath(qualified_source)
785
 
            if not e.target.endswith(relpath):
786
 
                # Not redirected to a branch-format, not a branch
787
 
                raise errors.NotBranchError(path=e.target)
788
 
            target = e.target[:-len(relpath)]
 
926
            redirected_transport = transport._redirected_to(e.source, e.target)
 
927
            if redirected_transport is None:
 
928
                raise errors.NotBranchError(base)
789
929
            note('%s is%s redirected to %s',
790
 
                 transport.base, e.permanently, target)
791
 
            # Let's try with a new transport
792
 
            # FIXME: If 'transport' has a qualifier, this should
793
 
            # be applied again to the new transport *iff* the
794
 
            # schemes used are the same. Uncomment this code
795
 
            # once the function (and tests) exist.
796
 
            # -- vila20070212
797
 
            #target = urlutils.copy_url_qualifiers(original, target)
798
 
            return get_transport(target)
 
930
                 transport.base, e.permanently, redirected_transport.base)
 
931
            return redirected_transport
799
932
 
800
933
        try:
801
934
            transport, format = do_catching_redirections(find_format,
807
940
        BzrDir._check_supported(format, _unsupported)
808
941
        return format.open(transport, _found=True)
809
942
 
810
 
    def open_branch(self, unsupported=False):
 
943
    def open_branch(self, name=None, unsupported=False,
 
944
                    ignore_fallbacks=False):
811
945
        """Open the branch object at this BzrDir if one is present.
812
946
 
813
947
        If unsupported is True, then no longer supported branch formats can
814
948
        still be opened.
815
 
        
 
949
 
816
950
        TODO: static convenience version of this?
817
951
        """
818
952
        raise NotImplementedError(self.open_branch)
820
954
    @staticmethod
821
955
    def open_containing(url, possible_transports=None):
822
956
        """Open an existing branch which contains url.
823
 
        
 
957
 
824
958
        :param url: url to search from.
825
959
        See open_containing_from_transport for more detail.
826
960
        """
827
961
        transport = get_transport(url, possible_transports)
828
962
        return BzrDir.open_containing_from_transport(transport)
829
 
    
 
963
 
830
964
    @staticmethod
831
965
    def open_containing_from_transport(a_transport):
832
966
        """Open an existing branch which contains a_transport.base.
835
969
 
836
970
        Basically we keep looking up until we find the control directory or
837
971
        run into the root.  If there isn't one, raises NotBranchError.
838
 
        If there is one and it is either an unrecognised format or an unsupported 
 
972
        If there is one and it is either an unrecognised format or an unsupported
839
973
        format, UnknownFormatError or UnsupportedFormatError are raised.
840
974
        If there is one, it is returned, along with the unused portion of url.
841
975
 
842
 
        :return: The BzrDir that contains the path, and a Unicode path 
 
976
        :return: The BzrDir that contains the path, and a Unicode path
843
977
                for the rest of the URL.
844
978
        """
845
979
        # this gets the normalised url back. I.e. '.' -> the full path.
951
1085
        """
952
1086
        raise NotImplementedError(self.open_workingtree)
953
1087
 
954
 
    def has_branch(self):
 
1088
    def has_branch(self, name=None):
955
1089
        """Tell if this bzrdir contains a branch.
956
 
        
 
1090
 
957
1091
        Note: if you're going to open the branch, you should just go ahead
958
 
        and try, and not ask permission first.  (This method just opens the 
959
 
        branch and discards it, and that's somewhat expensive.) 
 
1092
        and try, and not ask permission first.  (This method just opens the
 
1093
        branch and discards it, and that's somewhat expensive.)
960
1094
        """
961
1095
        try:
962
 
            self.open_branch()
 
1096
            self.open_branch(name)
963
1097
            return True
964
1098
        except errors.NotBranchError:
965
1099
            return False
969
1103
 
970
1104
        This will still raise an exception if the bzrdir has a workingtree that
971
1105
        is remote & inaccessible.
972
 
        
 
1106
 
973
1107
        Note: if you're going to open the working tree, you should just go ahead
974
 
        and try, and not ask permission first.  (This method just opens the 
975
 
        workingtree and discards it, and that's somewhat expensive.) 
 
1108
        and try, and not ask permission first.  (This method just opens the
 
1109
        workingtree and discards it, and that's somewhat expensive.)
976
1110
        """
977
1111
        try:
978
1112
            self.open_workingtree(recommend_upgrade=False)
982
1116
 
983
1117
    def _cloning_metadir(self):
984
1118
        """Produce a metadir suitable for cloning with.
985
 
        
 
1119
 
986
1120
        :returns: (destination_bzrdir_format, source_repository)
987
1121
        """
988
1122
        result_format = self._format.__class__()
989
1123
        try:
990
1124
            try:
991
 
                branch = self.open_branch()
 
1125
                branch = self.open_branch(ignore_fallbacks=True)
992
1126
                source_repository = branch.repository
993
1127
                result_format._branch_format = branch._format
994
1128
            except errors.NotBranchError:
1031
1165
        """
1032
1166
        format, repository = self._cloning_metadir()
1033
1167
        if format._workingtree_format is None:
 
1168
            # No tree in self.
1034
1169
            if repository is None:
 
1170
                # No repository either
1035
1171
                return format
 
1172
            # We have a repository, so set a working tree? (Why? This seems to
 
1173
            # contradict the stated return value in the docstring).
1036
1174
            tree_format = repository._format._matchingbzrdir.workingtree_format
1037
1175
            format.workingtree_format = tree_format.__class__()
1038
 
        if (require_stacking and not
1039
 
            format.get_branch_format().supports_stacking()):
1040
 
            # We need to make a stacked branch, but the default format for the
1041
 
            # target doesn't support stacking.  So force a branch that *can*
1042
 
            # support stacking.
1043
 
            from bzrlib.branch import BzrBranchFormat7
1044
 
            format._branch_format = BzrBranchFormat7()
1045
 
            mutter("using %r for stacking" % (format._branch_format,))
1046
 
            from bzrlib.repofmt import pack_repo
1047
 
            if format.repository_format.rich_root_data:
1048
 
                bzrdir_format_name = '1.6.1-rich-root'
1049
 
                repo_format = pack_repo.RepositoryFormatKnitPack5RichRoot()
1050
 
            else:
1051
 
                bzrdir_format_name = '1.6'
1052
 
                repo_format = pack_repo.RepositoryFormatKnitPack5()
1053
 
            note('Source format does not support stacking, using format:'
1054
 
                 ' \'%s\'\n  %s\n',
1055
 
                 bzrdir_format_name, repo_format.get_format_description())
1056
 
            format.repository_format = repo_format
 
1176
        if require_stacking:
 
1177
            format.require_stacking()
1057
1178
        return format
1058
1179
 
1059
1180
    def checkout_metadir(self):
1062
1183
    def sprout(self, url, revision_id=None, force_new_repo=False,
1063
1184
               recurse='down', possible_transports=None,
1064
1185
               accelerator_tree=None, hardlink=False, stacked=False,
1065
 
               source_branch=None):
 
1186
               source_branch=None, create_tree_if_local=True):
1066
1187
        """Create a copy of this bzrdir prepared for use as a new line of
1067
1188
        development.
1068
1189
 
1083
1204
            where possible.
1084
1205
        :param stacked: If true, create a stacked branch referring to the
1085
1206
            location of this control directory.
 
1207
        :param create_tree_if_local: If true, a working-tree will be created
 
1208
            when working locally.
1086
1209
        """
1087
1210
        target_transport = get_transport(url, possible_transports)
1088
1211
        target_transport.ensure_base()
1110
1233
                    source_repository = None
1111
1234
        repository_policy = result.determine_repository_policy(
1112
1235
            force_new_repo, stacked_branch_url, require_stacking=stacked)
1113
 
        result_repo = repository_policy.acquire_repository()
 
1236
        result_repo, is_new_repo = repository_policy.acquire_repository()
 
1237
        if is_new_repo and revision_id is not None and not stacked:
 
1238
            fetch_spec = graph.PendingAncestryResult(
 
1239
                [revision_id], source_repository)
 
1240
        else:
 
1241
            fetch_spec = None
1114
1242
        if source_repository is not None:
1115
1243
            # Fetch while stacked to prevent unstacked fetch from
1116
1244
            # Branch.sprout.
1117
 
            result_repo.fetch(source_repository, revision_id=revision_id)
 
1245
            if fetch_spec is None:
 
1246
                result_repo.fetch(source_repository, revision_id=revision_id)
 
1247
            else:
 
1248
                result_repo.fetch(source_repository, fetch_spec=fetch_spec)
1118
1249
 
1119
1250
        if source_branch is None:
1120
1251
            # this is for sprouting a bzrdir without a branch; is that
1122
1253
            # Not especially, but it's part of the contract.
1123
1254
            result_branch = result.create_branch()
1124
1255
        else:
1125
 
            # Force NULL revision to avoid using repository before stacking
1126
 
            # is configured.
1127
 
            result_branch = source_branch.sprout(
1128
 
                result, revision_id=_mod_revision.NULL_REVISION)
1129
 
            parent_location = result_branch.get_parent()
 
1256
            result_branch = source_branch.sprout(result,
 
1257
                revision_id=revision_id, repository_policy=repository_policy)
1130
1258
        mutter("created new branch %r" % (result_branch,))
1131
 
        repository_policy.configure_branch(result_branch)
1132
 
        if source_branch is not None:
1133
 
            source_branch.copy_content_into(result_branch, revision_id)
1134
 
            # Override copy_content_into
1135
 
            result_branch.set_parent(parent_location)
1136
1259
 
1137
1260
        # Create/update the result working tree
1138
 
        if isinstance(target_transport, local.LocalTransport) and (
1139
 
            result_repo is None or result_repo.make_working_trees()):
 
1261
        if (create_tree_if_local and
 
1262
            isinstance(target_transport, local.LocalTransport) and
 
1263
            (result_repo is None or result_repo.make_working_trees())):
1140
1264
            wt = result.create_workingtree(accelerator_tree=accelerator_tree,
1141
1265
                hardlink=hardlink)
1142
1266
            wt.lock_write()
1179
1303
                    basis.unlock()
1180
1304
        return result
1181
1305
 
 
1306
    def push_branch(self, source, revision_id=None, overwrite=False, 
 
1307
        remember=False, create_prefix=False):
 
1308
        """Push the source branch into this BzrDir."""
 
1309
        br_to = None
 
1310
        # If we can open a branch, use its direct repository, otherwise see
 
1311
        # if there is a repository without a branch.
 
1312
        try:
 
1313
            br_to = self.open_branch()
 
1314
        except errors.NotBranchError:
 
1315
            # Didn't find a branch, can we find a repository?
 
1316
            repository_to = self.find_repository()
 
1317
        else:
 
1318
            # Found a branch, so we must have found a repository
 
1319
            repository_to = br_to.repository
 
1320
 
 
1321
        push_result = PushResult()
 
1322
        push_result.source_branch = source
 
1323
        if br_to is None:
 
1324
            # We have a repository but no branch, copy the revisions, and then
 
1325
            # create a branch.
 
1326
            repository_to.fetch(source.repository, revision_id=revision_id)
 
1327
            br_to = source.clone(self, revision_id=revision_id)
 
1328
            if source.get_push_location() is None or remember:
 
1329
                source.set_push_location(br_to.base)
 
1330
            push_result.stacked_on = None
 
1331
            push_result.branch_push_result = None
 
1332
            push_result.old_revno = None
 
1333
            push_result.old_revid = _mod_revision.NULL_REVISION
 
1334
            push_result.target_branch = br_to
 
1335
            push_result.master_branch = None
 
1336
            push_result.workingtree_updated = False
 
1337
        else:
 
1338
            # We have successfully opened the branch, remember if necessary:
 
1339
            if source.get_push_location() is None or remember:
 
1340
                source.set_push_location(br_to.base)
 
1341
            try:
 
1342
                tree_to = self.open_workingtree()
 
1343
            except errors.NotLocalUrl:
 
1344
                push_result.branch_push_result = source.push(br_to, 
 
1345
                    overwrite, stop_revision=revision_id)
 
1346
                push_result.workingtree_updated = False
 
1347
            except errors.NoWorkingTree:
 
1348
                push_result.branch_push_result = source.push(br_to,
 
1349
                    overwrite, stop_revision=revision_id)
 
1350
                push_result.workingtree_updated = None # Not applicable
 
1351
            else:
 
1352
                tree_to.lock_write()
 
1353
                try:
 
1354
                    push_result.branch_push_result = source.push(
 
1355
                        tree_to.branch, overwrite, stop_revision=revision_id)
 
1356
                    tree_to.update()
 
1357
                finally:
 
1358
                    tree_to.unlock()
 
1359
                push_result.workingtree_updated = True
 
1360
            push_result.old_revno = push_result.branch_push_result.old_revno
 
1361
            push_result.old_revid = push_result.branch_push_result.old_revid
 
1362
            push_result.target_branch = \
 
1363
                push_result.branch_push_result.target_branch
 
1364
        return push_result
 
1365
 
 
1366
 
 
1367
class BzrDirHooks(hooks.Hooks):
 
1368
    """Hooks for BzrDir operations."""
 
1369
 
 
1370
    def __init__(self):
 
1371
        """Create the default hooks."""
 
1372
        hooks.Hooks.__init__(self)
 
1373
        self.create_hook(hooks.HookPoint('pre_open',
 
1374
            "Invoked before attempting to open a BzrDir with the transport "
 
1375
            "that the open will use.", (1, 14), None))
 
1376
        self.create_hook(hooks.HookPoint('post_repo_init',
 
1377
            "Invoked after a repository has been initialized. "
 
1378
            "post_repo_init is called with a "
 
1379
            "bzrlib.bzrdir.RepoInitHookParams.",
 
1380
            (2, 2), None))
 
1381
 
 
1382
# install the default hooks
 
1383
BzrDir.hooks = BzrDirHooks()
 
1384
 
 
1385
 
 
1386
class RepoInitHookParams(object):
 
1387
    """Object holding parameters passed to *_repo_init hooks.
 
1388
 
 
1389
    There are 4 fields that hooks may wish to access:
 
1390
 
 
1391
    :ivar repository: Repository created
 
1392
    :ivar format: Repository format
 
1393
    :ivar bzrdir: The bzrdir for the repository
 
1394
    :ivar shared: The repository is shared
 
1395
    """
 
1396
 
 
1397
    def __init__(self, repository, format, a_bzrdir, shared):
 
1398
        """Create a group of RepoInitHook parameters.
 
1399
 
 
1400
        :param repository: Repository created
 
1401
        :param format: Repository format
 
1402
        :param bzrdir: The bzrdir for the repository
 
1403
        :param shared: The repository is shared
 
1404
        """
 
1405
        self.repository = repository
 
1406
        self.format = format
 
1407
        self.bzrdir = a_bzrdir
 
1408
        self.shared = shared
 
1409
 
 
1410
    def __eq__(self, other):
 
1411
        return self.__dict__ == other.__dict__
 
1412
 
 
1413
    def __repr__(self):
 
1414
        if self.repository:
 
1415
            return "<%s for %s>" % (self.__class__.__name__,
 
1416
                self.repository)
 
1417
        else:
 
1418
            return "<%s for %s>" % (self.__class__.__name__,
 
1419
                self.bzrdir)
 
1420
 
1182
1421
 
1183
1422
class BzrDirPreSplitOut(BzrDir):
1184
1423
    """A common class for the all-in-one formats."""
1224
1463
            tree.clone(result)
1225
1464
        return result
1226
1465
 
1227
 
    def create_branch(self):
 
1466
    def create_branch(self, name=None):
1228
1467
        """See BzrDir.create_branch."""
1229
 
        return self._format.get_branch_format().initialize(self)
 
1468
        return self._format.get_branch_format().initialize(self, name=name)
1230
1469
 
1231
 
    def destroy_branch(self):
 
1470
    def destroy_branch(self, name=None):
1232
1471
        """See BzrDir.destroy_branch."""
1233
1472
        raise errors.UnsupportedOperation(self.destroy_branch, self)
1234
1473
 
1255
1494
        # and that will have set it for us, its only
1256
1495
        # specific uses of create_workingtree in isolation
1257
1496
        # that can do wonky stuff here, and that only
1258
 
        # happens for creating checkouts, which cannot be 
 
1497
        # happens for creating checkouts, which cannot be
1259
1498
        # done on this format anyway. So - acceptable wart.
 
1499
        if hardlink:
 
1500
            warning("can't support hardlinked working trees in %r"
 
1501
                % (self,))
1260
1502
        try:
1261
1503
            result = self.open_workingtree(recommend_upgrade=False)
1262
1504
        except errors.NoSuchFile:
1284
1526
 
1285
1527
    def destroy_workingtree_metadata(self):
1286
1528
        """See BzrDir.destroy_workingtree_metadata."""
1287
 
        raise errors.UnsupportedOperation(self.destroy_workingtree_metadata, 
 
1529
        raise errors.UnsupportedOperation(self.destroy_workingtree_metadata,
1288
1530
                                          self)
1289
1531
 
1290
 
    def get_branch_transport(self, branch_format):
 
1532
    def get_branch_transport(self, branch_format, name=None):
1291
1533
        """See BzrDir.get_branch_transport()."""
 
1534
        if name is not None:
 
1535
            raise errors.NoColocatedBranchSupport(self)
1292
1536
        if branch_format is None:
1293
1537
            return self.transport
1294
1538
        try:
1322
1566
        # if the format is not the same as the system default,
1323
1567
        # an upgrade is needed.
1324
1568
        if format is None:
 
1569
            symbol_versioning.warn(symbol_versioning.deprecated_in((1, 13, 0))
 
1570
                % 'needs_format_conversion(format=None)')
1325
1571
            format = BzrDirFormat.get_default_format()
1326
1572
        return not isinstance(self._format, format.__class__)
1327
1573
 
1328
 
    def open_branch(self, unsupported=False):
 
1574
    def open_branch(self, name=None, unsupported=False,
 
1575
                    ignore_fallbacks=False):
1329
1576
        """See BzrDir.open_branch."""
1330
1577
        from bzrlib.branch import BzrBranchFormat4
1331
1578
        format = BzrBranchFormat4()
1332
1579
        self._check_supported(format, unsupported)
1333
 
        return format.open(self, _found=True)
 
1580
        return format.open(self, name, _found=True)
1334
1581
 
1335
1582
    def sprout(self, url, revision_id=None, force_new_repo=False,
1336
1583
               possible_transports=None, accelerator_tree=None,
1337
 
               hardlink=False, stacked=False):
 
1584
               hardlink=False, stacked=False, create_tree_if_local=True,
 
1585
               source_branch=None):
1338
1586
        """See BzrDir.sprout()."""
 
1587
        if source_branch is not None:
 
1588
            my_branch = self.open_branch()
 
1589
            if source_branch.base != my_branch.base:
 
1590
                raise AssertionError(
 
1591
                    "source branch %r is not within %r with branch %r" %
 
1592
                    (source_branch, self, my_branch))
1339
1593
        if stacked:
1340
1594
            raise errors.UnstackableBranchFormat(
1341
1595
                self._format, self.root_transport.base)
 
1596
        if not create_tree_if_local:
 
1597
            raise errors.MustHaveWorkingTree(
 
1598
                self._format, self.root_transport.base)
1342
1599
        from bzrlib.workingtree import WorkingTreeFormat2
1343
1600
        self._make_tail(url)
1344
1601
        result = self._format._initialize_for_clone(url)
1350
1607
            self.open_branch().sprout(result, revision_id=revision_id)
1351
1608
        except errors.NotBranchError:
1352
1609
            pass
 
1610
 
1353
1611
        # we always want a working tree
1354
1612
        WorkingTreeFormat2().initialize(result,
1355
1613
                                        accelerator_tree=accelerator_tree,
1359
1617
 
1360
1618
class BzrDir4(BzrDirPreSplitOut):
1361
1619
    """A .bzr version 4 control object.
1362
 
    
 
1620
 
1363
1621
    This is a deprecated format and may be removed after sept 2006.
1364
1622
    """
1365
1623
 
1369
1627
 
1370
1628
    def needs_format_conversion(self, format=None):
1371
1629
        """Format 4 dirs are always in need of conversion."""
 
1630
        if format is None:
 
1631
            symbol_versioning.warn(symbol_versioning.deprecated_in((1, 13, 0))
 
1632
                % 'needs_format_conversion(format=None)')
1372
1633
        return True
1373
1634
 
1374
1635
    def open_repository(self):
1383
1644
    This is a deprecated format and may be removed after sept 2006.
1384
1645
    """
1385
1646
 
 
1647
    def has_workingtree(self):
 
1648
        """See BzrDir.has_workingtree."""
 
1649
        return True
 
1650
    
1386
1651
    def open_repository(self):
1387
1652
        """See BzrDir.open_repository."""
1388
1653
        from bzrlib.repofmt.weaverepo import RepositoryFormat5
1404
1669
    This is a deprecated format and may be removed after sept 2006.
1405
1670
    """
1406
1671
 
 
1672
    def has_workingtree(self):
 
1673
        """See BzrDir.has_workingtree."""
 
1674
        return True
 
1675
    
1407
1676
    def open_repository(self):
1408
1677
        """See BzrDir.open_repository."""
1409
1678
        from bzrlib.repofmt.weaverepo import RepositoryFormat6
1420
1689
 
1421
1690
class BzrDirMeta1(BzrDir):
1422
1691
    """A .bzr meta version 1 control object.
1423
 
    
1424
 
    This is the first control object where the 
 
1692
 
 
1693
    This is the first control object where the
1425
1694
    individual aspects are really split out: there are separate repository,
1426
1695
    workingtree and branch subdirectories and any subset of the three can be
1427
1696
    present within a BzrDir.
1431
1700
        """See BzrDir.can_convert_format()."""
1432
1701
        return True
1433
1702
 
1434
 
    def create_branch(self):
 
1703
    def create_branch(self, name=None):
1435
1704
        """See BzrDir.create_branch."""
1436
 
        return self._format.get_branch_format().initialize(self)
 
1705
        return self._format.get_branch_format().initialize(self, name=name)
1437
1706
 
1438
 
    def destroy_branch(self):
 
1707
    def destroy_branch(self, name=None):
1439
1708
        """See BzrDir.create_branch."""
 
1709
        if name is not None:
 
1710
            raise errors.NoColocatedBranchSupport(self)
1440
1711
        self.transport.delete_tree('branch')
1441
1712
 
1442
1713
    def create_repository(self, shared=False):
1485
1756
        format = BranchFormat.find_format(self)
1486
1757
        return format.get_reference(self)
1487
1758
 
1488
 
    def get_branch_transport(self, branch_format):
 
1759
    def get_branch_transport(self, branch_format, name=None):
1489
1760
        """See BzrDir.get_branch_transport()."""
 
1761
        if name is not None:
 
1762
            raise errors.NoColocatedBranchSupport(self)
 
1763
        # XXX: this shouldn't implicitly create the directory if it's just
 
1764
        # promising to get a transport -- mbp 20090727
1490
1765
        if branch_format is None:
1491
1766
            return self.transport.clone('branch')
1492
1767
        try:
1527
1802
            pass
1528
1803
        return self.transport.clone('checkout')
1529
1804
 
 
1805
    def has_workingtree(self):
 
1806
        """Tell if this bzrdir contains a working tree.
 
1807
 
 
1808
        This will still raise an exception if the bzrdir has a workingtree that
 
1809
        is remote & inaccessible.
 
1810
 
 
1811
        Note: if you're going to open the working tree, you should just go
 
1812
        ahead and try, and not ask permission first.
 
1813
        """
 
1814
        from bzrlib.workingtree import WorkingTreeFormat
 
1815
        try:
 
1816
            WorkingTreeFormat.find_format(self)
 
1817
        except errors.NoWorkingTree:
 
1818
            return False
 
1819
        return True
 
1820
 
1530
1821
    def needs_format_conversion(self, format=None):
1531
1822
        """See BzrDir.needs_format_conversion()."""
1532
1823
        if format is None:
 
1824
            symbol_versioning.warn(symbol_versioning.deprecated_in((1, 13, 0))
 
1825
                % 'needs_format_conversion(format=None)')
 
1826
        if format is None:
1533
1827
            format = BzrDirFormat.get_default_format()
1534
1828
        if not isinstance(self._format, format.__class__):
1535
1829
            # it is not a meta dir format, conversion is needed.
1542
1836
                return True
1543
1837
        except errors.NoRepositoryPresent:
1544
1838
            pass
1545
 
        try:
1546
 
            if not isinstance(self.open_branch()._format,
 
1839
        for branch in self.list_branches():
 
1840
            if not isinstance(branch._format,
1547
1841
                              format.get_branch_format().__class__):
1548
1842
                # the branch needs an upgrade.
1549
1843
                return True
1550
 
        except errors.NotBranchError:
1551
 
            pass
1552
1844
        try:
1553
1845
            my_wt = self.open_workingtree(recommend_upgrade=False)
1554
1846
            if not isinstance(my_wt._format,
1559
1851
            pass
1560
1852
        return False
1561
1853
 
1562
 
    def open_branch(self, unsupported=False):
 
1854
    def open_branch(self, name=None, unsupported=False,
 
1855
                    ignore_fallbacks=False):
1563
1856
        """See BzrDir.open_branch."""
1564
1857
        format = self.find_branch_format()
1565
1858
        self._check_supported(format, unsupported)
1566
 
        return format.open(self, _found=True)
 
1859
        return format.open(self, name=name,
 
1860
            _found=True, ignore_fallbacks=ignore_fallbacks)
1567
1861
 
1568
1862
    def open_repository(self, unsupported=False):
1569
1863
        """See BzrDir.open_repository."""
1583
1877
        return format.open(self, _found=True)
1584
1878
 
1585
1879
    def _get_config(self):
1586
 
        return config.BzrDirConfig(self.transport)
 
1880
        return config.TransportConfig(self.transport, 'control.conf')
1587
1881
 
1588
1882
 
1589
1883
class BzrDirFormat(object):
1594
1888
     * a format string,
1595
1889
     * an open routine.
1596
1890
 
1597
 
    Formats are placed in a dict by their format string for reference 
 
1891
    Formats are placed in a dict by their format string for reference
1598
1892
    during bzrdir opening. These should be subclasses of BzrDirFormat
1599
1893
    for consistency.
1600
1894
 
1601
1895
    Once a format is deprecated, just deprecate the initialize and open
1602
 
    methods on the format class. Do not deprecate the object, as the 
 
1896
    methods on the format class. Do not deprecate the object, as the
1603
1897
    object will be created every system load.
 
1898
 
 
1899
    :cvar colocated_branches: Whether this formats supports colocated branches.
1604
1900
    """
1605
1901
 
1606
1902
    _default_format = None
1611
1907
 
1612
1908
    _control_formats = []
1613
1909
    """The registered control formats - .bzr, ....
1614
 
    
 
1910
 
1615
1911
    This is a list of BzrDirFormat objects.
1616
1912
    """
1617
1913
 
1623
1919
 
1624
1920
    _lock_file_name = 'branch-lock'
1625
1921
 
 
1922
    colocated_branches = False
 
1923
    """Whether co-located branches are supported for this control dir format.
 
1924
    """
 
1925
 
1626
1926
    # _lock_class must be set in subclasses to the lock type, typ.
1627
1927
    # TransportLock or LockDir
1628
1928
 
1645
1945
    def probe_transport(klass, transport):
1646
1946
        """Return the .bzrdir style format present in a directory."""
1647
1947
        try:
1648
 
            format_string = transport.get(".bzr/branch-format").read()
 
1948
            format_string = transport.get_bytes(".bzr/branch-format")
1649
1949
        except errors.NoSuchFile:
1650
1950
            raise errors.NotBranchError(path=transport.base)
1651
1951
 
1676
1976
        current default format. In the case of plugins we can/should provide
1677
1977
        some means for them to extend the range of returnable converters.
1678
1978
 
1679
 
        :param format: Optional format to override the default format of the 
 
1979
        :param format: Optional format to override the default format of the
1680
1980
                       library.
1681
1981
        """
1682
1982
        raise NotImplementedError(self.get_converter)
1683
1983
 
1684
1984
    def initialize(self, url, possible_transports=None):
1685
1985
        """Create a bzr control dir at this url and return an opened copy.
1686
 
        
 
1986
 
 
1987
        While not deprecated, this method is very specific and its use will
 
1988
        lead to many round trips to setup a working environment. See
 
1989
        initialize_on_transport_ex for a [nearly] all-in-one method.
 
1990
 
1687
1991
        Subclasses should typically override initialize_on_transport
1688
1992
        instead of this method.
1689
1993
        """
1692
1996
 
1693
1997
    def initialize_on_transport(self, transport):
1694
1998
        """Initialize a new bzrdir in the base directory of a Transport."""
1695
 
        # Since we don't have a .bzr directory, inherit the
 
1999
        try:
 
2000
            # can we hand off the request to the smart server rather than using
 
2001
            # vfs calls?
 
2002
            client_medium = transport.get_smart_medium()
 
2003
        except errors.NoSmartMedium:
 
2004
            return self._initialize_on_transport_vfs(transport)
 
2005
        else:
 
2006
            # Current RPC's only know how to create bzr metadir1 instances, so
 
2007
            # we still delegate to vfs methods if the requested format is not a
 
2008
            # metadir1
 
2009
            if type(self) != BzrDirMetaFormat1:
 
2010
                return self._initialize_on_transport_vfs(transport)
 
2011
            remote_format = RemoteBzrDirFormat()
 
2012
            self._supply_sub_formats_to(remote_format)
 
2013
            return remote_format.initialize_on_transport(transport)
 
2014
 
 
2015
    def initialize_on_transport_ex(self, transport, use_existing_dir=False,
 
2016
        create_prefix=False, force_new_repo=False, stacked_on=None,
 
2017
        stack_on_pwd=None, repo_format_name=None, make_working_trees=None,
 
2018
        shared_repo=False, vfs_only=False):
 
2019
        """Create this format on transport.
 
2020
 
 
2021
        The directory to initialize will be created.
 
2022
 
 
2023
        :param force_new_repo: Do not use a shared repository for the target,
 
2024
                               even if one is available.
 
2025
        :param create_prefix: Create any missing directories leading up to
 
2026
            to_transport.
 
2027
        :param use_existing_dir: Use an existing directory if one exists.
 
2028
        :param stacked_on: A url to stack any created branch on, None to follow
 
2029
            any target stacking policy.
 
2030
        :param stack_on_pwd: If stack_on is relative, the location it is
 
2031
            relative to.
 
2032
        :param repo_format_name: If non-None, a repository will be
 
2033
            made-or-found. Should none be found, or if force_new_repo is True
 
2034
            the repo_format_name is used to select the format of repository to
 
2035
            create.
 
2036
        :param make_working_trees: Control the setting of make_working_trees
 
2037
            for a new shared repository when one is made. None to use whatever
 
2038
            default the format has.
 
2039
        :param shared_repo: Control whether made repositories are shared or
 
2040
            not.
 
2041
        :param vfs_only: If True do not attempt to use a smart server
 
2042
        :return: repo, bzrdir, require_stacking, repository_policy. repo is
 
2043
            None if none was created or found, bzrdir is always valid.
 
2044
            require_stacking is the result of examining the stacked_on
 
2045
            parameter and any stacking policy found for the target.
 
2046
        """
 
2047
        if not vfs_only:
 
2048
            # Try to hand off to a smart server 
 
2049
            try:
 
2050
                client_medium = transport.get_smart_medium()
 
2051
            except errors.NoSmartMedium:
 
2052
                pass
 
2053
            else:
 
2054
                # TODO: lookup the local format from a server hint.
 
2055
                remote_dir_format = RemoteBzrDirFormat()
 
2056
                remote_dir_format._network_name = self.network_name()
 
2057
                self._supply_sub_formats_to(remote_dir_format)
 
2058
                return remote_dir_format.initialize_on_transport_ex(transport,
 
2059
                    use_existing_dir=use_existing_dir, create_prefix=create_prefix,
 
2060
                    force_new_repo=force_new_repo, stacked_on=stacked_on,
 
2061
                    stack_on_pwd=stack_on_pwd, repo_format_name=repo_format_name,
 
2062
                    make_working_trees=make_working_trees, shared_repo=shared_repo)
 
2063
        # XXX: Refactor the create_prefix/no_create_prefix code into a
 
2064
        #      common helper function
 
2065
        # The destination may not exist - if so make it according to policy.
 
2066
        def make_directory(transport):
 
2067
            transport.mkdir('.')
 
2068
            return transport
 
2069
        def redirected(transport, e, redirection_notice):
 
2070
            note(redirection_notice)
 
2071
            return transport._redirected_to(e.source, e.target)
 
2072
        try:
 
2073
            transport = do_catching_redirections(make_directory, transport,
 
2074
                redirected)
 
2075
        except errors.FileExists:
 
2076
            if not use_existing_dir:
 
2077
                raise
 
2078
        except errors.NoSuchFile:
 
2079
            if not create_prefix:
 
2080
                raise
 
2081
            transport.create_prefix()
 
2082
 
 
2083
        require_stacking = (stacked_on is not None)
 
2084
        # Now the target directory exists, but doesn't have a .bzr
 
2085
        # directory. So we need to create it, along with any work to create
 
2086
        # all of the dependent branches, etc.
 
2087
 
 
2088
        result = self.initialize_on_transport(transport)
 
2089
        if repo_format_name:
 
2090
            try:
 
2091
                # use a custom format
 
2092
                result._format.repository_format = \
 
2093
                    repository.network_format_registry.get(repo_format_name)
 
2094
            except AttributeError:
 
2095
                # The format didn't permit it to be set.
 
2096
                pass
 
2097
            # A repository is desired, either in-place or shared.
 
2098
            repository_policy = result.determine_repository_policy(
 
2099
                force_new_repo, stacked_on, stack_on_pwd,
 
2100
                require_stacking=require_stacking)
 
2101
            result_repo, is_new_repo = repository_policy.acquire_repository(
 
2102
                make_working_trees, shared_repo)
 
2103
            if not require_stacking and repository_policy._require_stacking:
 
2104
                require_stacking = True
 
2105
                result._format.require_stacking()
 
2106
            result_repo.lock_write()
 
2107
        else:
 
2108
            result_repo = None
 
2109
            repository_policy = None
 
2110
        return result_repo, result, require_stacking, repository_policy
 
2111
 
 
2112
    def _initialize_on_transport_vfs(self, transport):
 
2113
        """Initialize a new bzrdir using VFS calls.
 
2114
 
 
2115
        :param transport: The transport to create the .bzr directory in.
 
2116
        :return: A
 
2117
        """
 
2118
        # Since we are creating a .bzr directory, inherit the
1696
2119
        # mode from the root directory
1697
2120
        temp_control = lockable_files.LockableFiles(transport,
1698
2121
                            '', lockable_files.TransportLock)
1728
2151
        """Is this format supported?
1729
2152
 
1730
2153
        Supported formats must be initializable and openable.
1731
 
        Unsupported formats may not support initialization or committing or 
 
2154
        Unsupported formats may not support initialization or committing or
1732
2155
        some other features depending on the reason for not being supported.
1733
2156
        """
1734
2157
        return True
1735
2158
 
 
2159
    def network_name(self):
 
2160
        """A simple byte string uniquely identifying this format for RPC calls.
 
2161
 
 
2162
        Bzr control formats use thir disk format string to identify the format
 
2163
        over the wire. Its possible that other control formats have more
 
2164
        complex detection requirements, so we permit them to use any unique and
 
2165
        immutable string they desire.
 
2166
        """
 
2167
        raise NotImplementedError(self.network_name)
 
2168
 
1736
2169
    def same_model(self, target_format):
1737
 
        return (self.repository_format.rich_root_data == 
 
2170
        return (self.repository_format.rich_root_data ==
1738
2171
            target_format.rich_root_data)
1739
2172
 
1740
2173
    @classmethod
1741
2174
    def known_formats(klass):
1742
2175
        """Return all the known formats.
1743
 
        
 
2176
 
1744
2177
        Concrete formats should override _known_formats.
1745
2178
        """
1746
 
        # There is double indirection here to make sure that control 
1747
 
        # formats used by more than one dir format will only be probed 
 
2179
        # There is double indirection here to make sure that control
 
2180
        # formats used by more than one dir format will only be probed
1748
2181
        # once. This can otherwise be quite expensive for remote connections.
1749
2182
        result = set()
1750
2183
        for format in klass._control_formats:
1751
2184
            result.update(format._known_formats())
1752
2185
        return result
1753
 
    
 
2186
 
1754
2187
    @classmethod
1755
2188
    def _known_formats(klass):
1756
2189
        """Return the known format instances for this control format."""
1758
2191
 
1759
2192
    def open(self, transport, _found=False):
1760
2193
        """Return an instance of this format for the dir transport points at.
1761
 
        
 
2194
 
1762
2195
        _found is a private parameter, do not use it.
1763
2196
        """
1764
2197
        if not _found:
1765
2198
            found_format = BzrDirFormat.find_format(transport)
1766
2199
            if not isinstance(found_format, self.__class__):
1767
2200
                raise AssertionError("%s was asked to open %s, but it seems to need "
1768
 
                        "format %s" 
 
2201
                        "format %s"
1769
2202
                        % (self, transport, found_format))
 
2203
            # Allow subclasses - use the found format.
 
2204
            self._supply_sub_formats_to(found_format)
 
2205
            return found_format._open(transport)
1770
2206
        return self._open(transport)
1771
2207
 
1772
2208
    def _open(self, transport):
1780
2216
    @classmethod
1781
2217
    def register_format(klass, format):
1782
2218
        klass._formats[format.get_format_string()] = format
 
2219
        # bzr native formats have a network name of their format string.
 
2220
        network_format_registry.register(format.get_format_string(), format.__class__)
1783
2221
 
1784
2222
    @classmethod
1785
2223
    def register_control_format(klass, format):
1786
2224
        """Register a format that does not use '.bzr' for its control dir.
1787
2225
 
1788
2226
        TODO: This should be pulled up into a 'ControlDirFormat' base class
1789
 
        which BzrDirFormat can inherit from, and renamed to register_format 
 
2227
        which BzrDirFormat can inherit from, and renamed to register_format
1790
2228
        there. It has been done without that for now for simplicity of
1791
2229
        implementation.
1792
2230
        """
1810
2248
 
1811
2249
    def __str__(self):
1812
2250
        # Trim the newline
1813
 
        return self.get_format_string().rstrip()
 
2251
        return self.get_format_description().rstrip()
 
2252
 
 
2253
    def _supply_sub_formats_to(self, other_format):
 
2254
        """Give other_format the same values for sub formats as this has.
 
2255
 
 
2256
        This method is expected to be used when parameterising a
 
2257
        RemoteBzrDirFormat instance with the parameters from a
 
2258
        BzrDirMetaFormat1 instance.
 
2259
 
 
2260
        :param other_format: other_format is a format which should be
 
2261
            compatible with whatever sub formats are supported by self.
 
2262
        :return: None.
 
2263
        """
1814
2264
 
1815
2265
    @classmethod
1816
2266
    def unregister_format(klass, format):
1848
2298
        """See BzrDirFormat.get_converter()."""
1849
2299
        # there is one and only one upgrade path here.
1850
2300
        return ConvertBzrDir4To5()
1851
 
        
 
2301
 
1852
2302
    def initialize_on_transport(self, transport):
1853
2303
        """Format 4 branches cannot be created."""
1854
2304
        raise errors.UninitializableFormat(self)
1857
2307
        """Format 4 is not supported.
1858
2308
 
1859
2309
        It is not supported because the model changed from 4 to 5 and the
1860
 
        conversion logic is expensive - so doing it on the fly was not 
 
2310
        conversion logic is expensive - so doing it on the fly was not
1861
2311
        feasible.
1862
2312
        """
1863
2313
        return False
1864
2314
 
 
2315
    def network_name(self):
 
2316
        return self.get_format_string()
 
2317
 
1865
2318
    def _open(self, transport):
1866
2319
        """See BzrDirFormat._open."""
1867
2320
        return BzrDir4(transport, self)
1873
2326
    repository_format = property(__return_repository_format)
1874
2327
 
1875
2328
 
1876
 
class BzrDirFormat5(BzrDirFormat):
 
2329
class BzrDirFormatAllInOne(BzrDirFormat):
 
2330
    """Common class for formats before meta-dirs."""
 
2331
 
 
2332
    def initialize_on_transport_ex(self, transport, use_existing_dir=False,
 
2333
        create_prefix=False, force_new_repo=False, stacked_on=None,
 
2334
        stack_on_pwd=None, repo_format_name=None, make_working_trees=None,
 
2335
        shared_repo=False):
 
2336
        """See BzrDirFormat.initialize_on_transport_ex."""
 
2337
        require_stacking = (stacked_on is not None)
 
2338
        # Format 5 cannot stack, but we've been asked to - actually init
 
2339
        # a Meta1Dir
 
2340
        if require_stacking:
 
2341
            format = BzrDirMetaFormat1()
 
2342
            return format.initialize_on_transport_ex(transport,
 
2343
                use_existing_dir=use_existing_dir, create_prefix=create_prefix,
 
2344
                force_new_repo=force_new_repo, stacked_on=stacked_on,
 
2345
                stack_on_pwd=stack_on_pwd, repo_format_name=repo_format_name,
 
2346
                make_working_trees=make_working_trees, shared_repo=shared_repo)
 
2347
        return BzrDirFormat.initialize_on_transport_ex(self, transport,
 
2348
            use_existing_dir=use_existing_dir, create_prefix=create_prefix,
 
2349
            force_new_repo=force_new_repo, stacked_on=stacked_on,
 
2350
            stack_on_pwd=stack_on_pwd, repo_format_name=repo_format_name,
 
2351
            make_working_trees=make_working_trees, shared_repo=shared_repo)
 
2352
 
 
2353
 
 
2354
class BzrDirFormat5(BzrDirFormatAllInOne):
1877
2355
    """Bzr control format 5.
1878
2356
 
1879
2357
    This format is a combined format for working tree, branch and repository.
1880
2358
    It has:
1881
 
     - Format 2 working trees [always] 
1882
 
     - Format 4 branches [always] 
 
2359
     - Format 2 working trees [always]
 
2360
     - Format 4 branches [always]
1883
2361
     - Format 5 repositories [always]
1884
2362
       Unhashed stores in the repository.
1885
2363
    """
1905
2383
 
1906
2384
    def _initialize_for_clone(self, url):
1907
2385
        return self.initialize_on_transport(get_transport(url), _cloning=True)
1908
 
        
 
2386
 
1909
2387
    def initialize_on_transport(self, transport, _cloning=False):
1910
2388
        """Format 5 dirs always have working tree, branch and repository.
1911
 
        
 
2389
 
1912
2390
        Except when they are being cloned.
1913
2391
        """
1914
2392
        from bzrlib.branch import BzrBranchFormat4
1920
2398
            result._init_workingtree()
1921
2399
        return result
1922
2400
 
 
2401
    def network_name(self):
 
2402
        return self.get_format_string()
 
2403
 
1923
2404
    def _open(self, transport):
1924
2405
        """See BzrDirFormat._open."""
1925
2406
        return BzrDir5(transport, self)
1931
2412
    repository_format = property(__return_repository_format)
1932
2413
 
1933
2414
 
1934
 
class BzrDirFormat6(BzrDirFormat):
 
2415
class BzrDirFormat6(BzrDirFormatAllInOne):
1935
2416
    """Bzr control format 6.
1936
2417
 
1937
2418
    This format is a combined format for working tree, branch and repository.
1938
2419
    It has:
1939
 
     - Format 2 working trees [always] 
1940
 
     - Format 4 branches [always] 
 
2420
     - Format 2 working trees [always]
 
2421
     - Format 4 branches [always]
1941
2422
     - Format 6 repositories [always]
1942
2423
    """
1943
2424
 
1959
2440
        """See BzrDirFormat.get_converter()."""
1960
2441
        # there is one and only one upgrade path here.
1961
2442
        return ConvertBzrDir6ToMeta()
1962
 
        
 
2443
 
1963
2444
    def _initialize_for_clone(self, url):
1964
2445
        return self.initialize_on_transport(get_transport(url), _cloning=True)
1965
2446
 
1966
2447
    def initialize_on_transport(self, transport, _cloning=False):
1967
2448
        """Format 6 dirs always have working tree, branch and repository.
1968
 
        
 
2449
 
1969
2450
        Except when they are being cloned.
1970
2451
        """
1971
2452
        from bzrlib.branch import BzrBranchFormat4
1977
2458
            result._init_workingtree()
1978
2459
        return result
1979
2460
 
 
2461
    def network_name(self):
 
2462
        return self.get_format_string()
 
2463
 
1980
2464
    def _open(self, transport):
1981
2465
        """See BzrDirFormat._open."""
1982
2466
        return BzrDir6(transport, self)
2004
2488
    def __init__(self):
2005
2489
        self._workingtree_format = None
2006
2490
        self._branch_format = None
 
2491
        self._repository_format = None
2007
2492
 
2008
2493
    def __eq__(self, other):
2009
2494
        if other.__class__ is not self.__class__:
2026
2511
    def set_branch_format(self, format):
2027
2512
        self._branch_format = format
2028
2513
 
 
2514
    def require_stacking(self, stack_on=None, possible_transports=None,
 
2515
            _skip_repo=False):
 
2516
        """We have a request to stack, try to ensure the formats support it.
 
2517
 
 
2518
        :param stack_on: If supplied, it is the URL to a branch that we want to
 
2519
            stack on. Check to see if that format supports stacking before
 
2520
            forcing an upgrade.
 
2521
        """
 
2522
        # Stacking is desired. requested by the target, but does the place it
 
2523
        # points at support stacking? If it doesn't then we should
 
2524
        # not implicitly upgrade. We check this here.
 
2525
        new_repo_format = None
 
2526
        new_branch_format = None
 
2527
 
 
2528
        # a bit of state for get_target_branch so that we don't try to open it
 
2529
        # 2 times, for both repo *and* branch
 
2530
        target = [None, False, None] # target_branch, checked, upgrade anyway
 
2531
        def get_target_branch():
 
2532
            if target[1]:
 
2533
                # We've checked, don't check again
 
2534
                return target
 
2535
            if stack_on is None:
 
2536
                # No target format, that means we want to force upgrading
 
2537
                target[:] = [None, True, True]
 
2538
                return target
 
2539
            try:
 
2540
                target_dir = BzrDir.open(stack_on,
 
2541
                    possible_transports=possible_transports)
 
2542
            except errors.NotBranchError:
 
2543
                # Nothing there, don't change formats
 
2544
                target[:] = [None, True, False]
 
2545
                return target
 
2546
            except errors.JailBreak:
 
2547
                # JailBreak, JFDI and upgrade anyway
 
2548
                target[:] = [None, True, True]
 
2549
                return target
 
2550
            try:
 
2551
                target_branch = target_dir.open_branch()
 
2552
            except errors.NotBranchError:
 
2553
                # No branch, don't upgrade formats
 
2554
                target[:] = [None, True, False]
 
2555
                return target
 
2556
            target[:] = [target_branch, True, False]
 
2557
            return target
 
2558
 
 
2559
        if (not _skip_repo and
 
2560
                 not self.repository_format.supports_external_lookups):
 
2561
            # We need to upgrade the Repository.
 
2562
            target_branch, _, do_upgrade = get_target_branch()
 
2563
            if target_branch is None:
 
2564
                # We don't have a target branch, should we upgrade anyway?
 
2565
                if do_upgrade:
 
2566
                    # stack_on is inaccessible, JFDI.
 
2567
                    # TODO: bad monkey, hard-coded formats...
 
2568
                    if self.repository_format.rich_root_data:
 
2569
                        new_repo_format = pack_repo.RepositoryFormatKnitPack5RichRoot()
 
2570
                    else:
 
2571
                        new_repo_format = pack_repo.RepositoryFormatKnitPack5()
 
2572
            else:
 
2573
                # If the target already supports stacking, then we know the
 
2574
                # project is already able to use stacking, so auto-upgrade
 
2575
                # for them
 
2576
                new_repo_format = target_branch.repository._format
 
2577
                if not new_repo_format.supports_external_lookups:
 
2578
                    # target doesn't, source doesn't, so don't auto upgrade
 
2579
                    # repo
 
2580
                    new_repo_format = None
 
2581
            if new_repo_format is not None:
 
2582
                self.repository_format = new_repo_format
 
2583
                note('Source repository format does not support stacking,'
 
2584
                     ' using format:\n  %s',
 
2585
                     new_repo_format.get_format_description())
 
2586
 
 
2587
        if not self.get_branch_format().supports_stacking():
 
2588
            # We just checked the repo, now lets check if we need to
 
2589
            # upgrade the branch format
 
2590
            target_branch, _, do_upgrade = get_target_branch()
 
2591
            if target_branch is None:
 
2592
                if do_upgrade:
 
2593
                    # TODO: bad monkey, hard-coded formats...
 
2594
                    new_branch_format = branch.BzrBranchFormat7()
 
2595
            else:
 
2596
                new_branch_format = target_branch._format
 
2597
                if not new_branch_format.supports_stacking():
 
2598
                    new_branch_format = None
 
2599
            if new_branch_format is not None:
 
2600
                # Does support stacking, use its format.
 
2601
                self.set_branch_format(new_branch_format)
 
2602
                note('Source branch format does not support stacking,'
 
2603
                     ' using format:\n  %s',
 
2604
                     new_branch_format.get_format_description())
 
2605
 
2029
2606
    def get_converter(self, format=None):
2030
2607
        """See BzrDirFormat.get_converter()."""
2031
2608
        if format is None:
2043
2620
        """See BzrDirFormat.get_format_description()."""
2044
2621
        return "Meta directory format 1"
2045
2622
 
 
2623
    def network_name(self):
 
2624
        return self.get_format_string()
 
2625
 
2046
2626
    def _open(self, transport):
2047
2627
        """See BzrDirFormat._open."""
2048
 
        return BzrDirMeta1(transport, self)
 
2628
        # Create a new format instance because otherwise initialisation of new
 
2629
        # metadirs share the global default format object leading to alias
 
2630
        # problems.
 
2631
        format = BzrDirMetaFormat1()
 
2632
        self._supply_sub_formats_to(format)
 
2633
        return BzrDirMeta1(transport, format)
2049
2634
 
2050
2635
    def __return_repository_format(self):
2051
2636
        """Circular import protection."""
2052
 
        if getattr(self, '_repository_format', None):
 
2637
        if self._repository_format:
2053
2638
            return self._repository_format
2054
2639
        from bzrlib.repository import RepositoryFormat
2055
2640
        return RepositoryFormat.get_default_format()
2056
2641
 
2057
 
    def __set_repository_format(self, value):
 
2642
    def _set_repository_format(self, value):
2058
2643
        """Allow changing the repository format for metadir formats."""
2059
2644
        self._repository_format = value
2060
2645
 
2061
 
    repository_format = property(__return_repository_format, __set_repository_format)
 
2646
    repository_format = property(__return_repository_format,
 
2647
        _set_repository_format)
 
2648
 
 
2649
    def _supply_sub_formats_to(self, other_format):
 
2650
        """Give other_format the same values for sub formats as this has.
 
2651
 
 
2652
        This method is expected to be used when parameterising a
 
2653
        RemoteBzrDirFormat instance with the parameters from a
 
2654
        BzrDirMetaFormat1 instance.
 
2655
 
 
2656
        :param other_format: other_format is a format which should be
 
2657
            compatible with whatever sub formats are supported by self.
 
2658
        :return: None.
 
2659
        """
 
2660
        if getattr(self, '_repository_format', None) is not None:
 
2661
            other_format.repository_format = self.repository_format
 
2662
        if self._branch_format is not None:
 
2663
            other_format._branch_format = self._branch_format
 
2664
        if self._workingtree_format is not None:
 
2665
            other_format.workingtree_format = self.workingtree_format
2062
2666
 
2063
2667
    def __get_workingtree_format(self):
2064
2668
        if self._workingtree_format is None:
2073
2677
                                  __set_workingtree_format)
2074
2678
 
2075
2679
 
 
2680
network_format_registry = registry.FormatRegistry()
 
2681
"""Registry of formats indexed by their network name.
 
2682
 
 
2683
The network name for a BzrDirFormat is an identifier that can be used when
 
2684
referring to formats with smart server operations. See
 
2685
BzrDirFormat.network_name() for more detail.
 
2686
"""
 
2687
 
 
2688
 
2076
2689
# Register bzr control format
2077
2690
BzrDirFormat.register_control_format(BzrDirFormat)
2078
2691
 
2110
2723
        self.absent_revisions = set()
2111
2724
        self.text_count = 0
2112
2725
        self.revisions = {}
2113
 
        
 
2726
 
2114
2727
    def convert(self, to_convert, pb):
2115
2728
        """See Converter.convert()."""
2116
2729
        self.bzrdir = to_convert
2117
 
        self.pb = pb
2118
 
        self.pb.note('starting upgrade from format 4 to 5')
2119
 
        if isinstance(self.bzrdir.transport, local.LocalTransport):
2120
 
            self.bzrdir.get_workingtree_transport(None).delete('stat-cache')
2121
 
        self._convert_to_weaves()
2122
 
        return BzrDir.open(self.bzrdir.root_transport.base)
 
2730
        if pb is not None:
 
2731
            warnings.warn("pb parameter to convert() is deprecated")
 
2732
        self.pb = ui.ui_factory.nested_progress_bar()
 
2733
        try:
 
2734
            ui.ui_factory.note('starting upgrade from format 4 to 5')
 
2735
            if isinstance(self.bzrdir.transport, local.LocalTransport):
 
2736
                self.bzrdir.get_workingtree_transport(None).delete('stat-cache')
 
2737
            self._convert_to_weaves()
 
2738
            return BzrDir.open(self.bzrdir.user_url)
 
2739
        finally:
 
2740
            self.pb.finished()
2123
2741
 
2124
2742
    def _convert_to_weaves(self):
2125
 
        self.pb.note('note: upgrade may be faster if all store files are ungzipped first')
 
2743
        ui.ui_factory.note('note: upgrade may be faster if all store files are ungzipped first')
2126
2744
        try:
2127
2745
            # TODO permissions
2128
2746
            stat = self.bzrdir.transport.stat('weaves')
2156
2774
        self.pb.clear()
2157
2775
        self._write_all_weaves()
2158
2776
        self._write_all_revs()
2159
 
        self.pb.note('upgraded to weaves:')
2160
 
        self.pb.note('  %6d revisions and inventories', len(self.revisions))
2161
 
        self.pb.note('  %6d revisions not present', len(self.absent_revisions))
2162
 
        self.pb.note('  %6d texts', self.text_count)
 
2777
        ui.ui_factory.note('upgraded to weaves:')
 
2778
        ui.ui_factory.note('  %6d revisions and inventories' % len(self.revisions))
 
2779
        ui.ui_factory.note('  %6d revisions not present' % len(self.absent_revisions))
 
2780
        ui.ui_factory.note('  %6d texts' % self.text_count)
2163
2781
        self._cleanup_spare_files_after_format4()
2164
2782
        self.branch._transport.put_bytes(
2165
2783
            'branch-format',
2222
2840
                revision_store.add_lines(key, None, osutils.split_lines(text))
2223
2841
        finally:
2224
2842
            self.pb.clear()
2225
 
            
 
2843
 
2226
2844
    def _load_one_rev(self, rev_id):
2227
2845
        """Load a revision object into memory.
2228
2846
 
2233
2851
                       len(self.known_revisions))
2234
2852
        if not self.branch.repository.has_revision(rev_id):
2235
2853
            self.pb.clear()
2236
 
            self.pb.note('revision {%s} not present in branch; '
2237
 
                         'will be converted as a ghost',
 
2854
            ui.ui_factory.note('revision {%s} not present in branch; '
 
2855
                         'will be converted as a ghost' %
2238
2856
                         rev_id)
2239
2857
            self.absent_revisions.add(rev_id)
2240
2858
        else:
2302
2920
        text_changed = False
2303
2921
        parent_candiate_entries = ie.parent_candidates(parent_invs)
2304
2922
        heads = graph.Graph(self).heads(parent_candiate_entries.keys())
2305
 
        # XXX: Note that this is unordered - and this is tolerable because 
 
2923
        # XXX: Note that this is unordered - and this is tolerable because
2306
2924
        # the previous code was also unordered.
2307
2925
        previous_entries = dict((head, parent_candiate_entries[head]) for head
2308
2926
            in heads)
2309
2927
        self.snapshot_ie(previous_entries, ie, w, rev_id)
2310
2928
        del ie.text_id
2311
2929
 
2312
 
    @symbol_versioning.deprecated_method(symbol_versioning.one_one)
2313
 
    def get_parents(self, revision_ids):
2314
 
        for revision_id in revision_ids:
2315
 
            yield self.revisions[revision_id].parent_ids
2316
 
 
2317
2930
    def get_parent_map(self, revision_ids):
2318
 
        """See graph._StackedParentsProvider.get_parent_map"""
 
2931
        """See graph.StackedParentsProvider.get_parent_map"""
2319
2932
        return dict((revision_id, self.revisions[revision_id])
2320
2933
                    for revision_id in revision_ids
2321
2934
                     if revision_id in self.revisions)
2325
2938
        # a call to:. This needs the path figured out. rather than a work_tree
2326
2939
        # a v4 revision_tree can be given, or something that looks enough like
2327
2940
        # one to give the file content to the entry if it needs it.
2328
 
        # and we need something that looks like a weave store for snapshot to 
 
2941
        # and we need something that looks like a weave store for snapshot to
2329
2942
        # save against.
2330
2943
        #ie.snapshot(rev, PATH, previous_revisions, REVISION_TREE, InMemoryWeaveStore(self.text_weaves))
2331
2944
        if len(previous_revisions) == 1:
2371
2984
    def convert(self, to_convert, pb):
2372
2985
        """See Converter.convert()."""
2373
2986
        self.bzrdir = to_convert
2374
 
        self.pb = pb
2375
 
        self.pb.note('starting upgrade from format 5 to 6')
2376
 
        self._convert_to_prefixed()
2377
 
        return BzrDir.open(self.bzrdir.root_transport.base)
 
2987
        pb = ui.ui_factory.nested_progress_bar()
 
2988
        try:
 
2989
            ui.ui_factory.note('starting upgrade from format 5 to 6')
 
2990
            self._convert_to_prefixed()
 
2991
            return BzrDir.open(self.bzrdir.user_url)
 
2992
        finally:
 
2993
            pb.finished()
2378
2994
 
2379
2995
    def _convert_to_prefixed(self):
2380
2996
        from bzrlib.store import TransportStore
2381
2997
        self.bzrdir.transport.delete('branch-format')
2382
2998
        for store_name in ["weaves", "revision-store"]:
2383
 
            self.pb.note("adding prefixes to %s" % store_name)
 
2999
            ui.ui_factory.note("adding prefixes to %s" % store_name)
2384
3000
            store_transport = self.bzrdir.transport.clone(store_name)
2385
3001
            store = TransportStore(store_transport, prefixed=True)
2386
3002
            for urlfilename in store_transport.list_dir('.'):
2413
3029
        from bzrlib.repofmt.weaverepo import RepositoryFormat7
2414
3030
        from bzrlib.branch import BzrBranchFormat5
2415
3031
        self.bzrdir = to_convert
2416
 
        self.pb = pb
 
3032
        self.pb = ui.ui_factory.nested_progress_bar()
2417
3033
        self.count = 0
2418
3034
        self.total = 20 # the steps we know about
2419
3035
        self.garbage_inventories = []
2420
3036
        self.dir_mode = self.bzrdir._get_dir_mode()
2421
3037
        self.file_mode = self.bzrdir._get_file_mode()
2422
3038
 
2423
 
        self.pb.note('starting upgrade from format 6 to metadir')
 
3039
        ui.ui_factory.note('starting upgrade from format 6 to metadir')
2424
3040
        self.bzrdir.transport.put_bytes(
2425
3041
                'branch-format',
2426
3042
                "Converting to format 6",
2447
3063
        self.bzrdir.transport.mkdir('repository', mode=self.dir_mode)
2448
3064
        self.make_lock('repository')
2449
3065
        # we hard code the formats here because we are converting into
2450
 
        # the meta format. The meta format upgrader can take this to a 
 
3066
        # the meta format. The meta format upgrader can take this to a
2451
3067
        # future format within each component.
2452
3068
        self.put_format('repository', RepositoryFormat7())
2453
3069
        for entry in repository_names:
2476
3092
        else:
2477
3093
            has_checkout = True
2478
3094
        if not has_checkout:
2479
 
            self.pb.note('No working tree.')
 
3095
            ui.ui_factory.note('No working tree.')
2480
3096
            # If some checkout files are there, we may as well get rid of them.
2481
3097
            for name, mandatory in checkout_files:
2482
3098
                if name in bzrcontents:
2499
3115
            'branch-format',
2500
3116
            BzrDirMetaFormat1().get_format_string(),
2501
3117
            mode=self.file_mode)
2502
 
        return BzrDir.open(self.bzrdir.root_transport.base)
 
3118
        self.pb.finished()
 
3119
        return BzrDir.open(self.bzrdir.user_url)
2503
3120
 
2504
3121
    def make_lock(self, name):
2505
3122
        """Make a lock for the new control dir name."""
2540
3157
    def convert(self, to_convert, pb):
2541
3158
        """See Converter.convert()."""
2542
3159
        self.bzrdir = to_convert
2543
 
        self.pb = pb
 
3160
        self.pb = ui.ui_factory.nested_progress_bar()
2544
3161
        self.count = 0
2545
3162
        self.total = 1
2546
3163
        self.step('checking repository format')
2551
3168
        else:
2552
3169
            if not isinstance(repo._format, self.target_format.repository_format.__class__):
2553
3170
                from bzrlib.repository import CopyConverter
2554
 
                self.pb.note('starting repository conversion')
 
3171
                ui.ui_factory.note('starting repository conversion')
2555
3172
                converter = CopyConverter(self.target_format.repository_format)
2556
3173
                converter.convert(repo, pb)
2557
 
        try:
2558
 
            branch = self.bzrdir.open_branch()
2559
 
        except errors.NotBranchError:
2560
 
            pass
2561
 
        else:
 
3174
        for branch in self.bzrdir.list_branches():
2562
3175
            # TODO: conversions of Branch and Tree should be done by
2563
3176
            # InterXFormat lookups/some sort of registry.
2564
3177
            # Avoid circular imports
2568
3181
            while old != new:
2569
3182
                if (old == _mod_branch.BzrBranchFormat5 and
2570
3183
                    new in (_mod_branch.BzrBranchFormat6,
2571
 
                        _mod_branch.BzrBranchFormat7)):
 
3184
                        _mod_branch.BzrBranchFormat7,
 
3185
                        _mod_branch.BzrBranchFormat8)):
2572
3186
                    branch_converter = _mod_branch.Converter5to6()
2573
3187
                elif (old == _mod_branch.BzrBranchFormat6 and
2574
 
                    new == _mod_branch.BzrBranchFormat7):
 
3188
                    new in (_mod_branch.BzrBranchFormat7,
 
3189
                            _mod_branch.BzrBranchFormat8)):
2575
3190
                    branch_converter = _mod_branch.Converter6to7()
 
3191
                elif (old == _mod_branch.BzrBranchFormat7 and
 
3192
                      new is _mod_branch.BzrBranchFormat8):
 
3193
                    branch_converter = _mod_branch.Converter7to8()
2576
3194
                else:
2577
 
                    raise errors.BadConversionTarget("No converter", new)
 
3195
                    raise errors.BadConversionTarget("No converter", new,
 
3196
                        branch._format)
2578
3197
                branch_converter.convert(branch)
2579
3198
                branch = self.bzrdir.open_branch()
2580
3199
                old = branch._format.__class__
2586
3205
            # TODO: conversions of Branch and Tree should be done by
2587
3206
            # InterXFormat lookups
2588
3207
            if (isinstance(tree, workingtree.WorkingTree3) and
2589
 
                not isinstance(tree, workingtree_4.WorkingTree4) and
 
3208
                not isinstance(tree, workingtree_4.DirStateWorkingTree) and
2590
3209
                isinstance(self.target_format.workingtree_format,
2591
 
                    workingtree_4.WorkingTreeFormat4)):
 
3210
                    workingtree_4.DirStateWorkingTreeFormat)):
2592
3211
                workingtree_4.Converter3to4().convert(tree)
 
3212
            if (isinstance(tree, workingtree_4.DirStateWorkingTree) and
 
3213
                not isinstance(tree, workingtree_4.WorkingTree5) and
 
3214
                isinstance(self.target_format.workingtree_format,
 
3215
                    workingtree_4.WorkingTreeFormat5)):
 
3216
                workingtree_4.Converter4to5().convert(tree)
 
3217
            if (isinstance(tree, workingtree_4.DirStateWorkingTree) and
 
3218
                not isinstance(tree, workingtree_4.WorkingTree6) and
 
3219
                isinstance(self.target_format.workingtree_format,
 
3220
                    workingtree_4.WorkingTreeFormat6)):
 
3221
                workingtree_4.Converter4or5to6().convert(tree)
 
3222
        self.pb.finished()
2593
3223
        return to_convert
2594
3224
 
2595
3225
 
2596
 
# This is not in remote.py because it's small, and needs to be registered.
2597
 
# Putting it in remote.py creates a circular import problem.
 
3226
# This is not in remote.py because it's relatively small, and needs to be
 
3227
# registered. Putting it in remote.py creates a circular import problem.
2598
3228
# we can make it a lazy object if the control formats is turned into something
2599
3229
# like a registry.
2600
3230
class RemoteBzrDirFormat(BzrDirMetaFormat1):
2601
3231
    """Format representing bzrdirs accessed via a smart server"""
2602
3232
 
 
3233
    def __init__(self):
 
3234
        BzrDirMetaFormat1.__init__(self)
 
3235
        # XXX: It's a bit ugly that the network name is here, because we'd
 
3236
        # like to believe that format objects are stateless or at least
 
3237
        # immutable,  However, we do at least avoid mutating the name after
 
3238
        # it's returned.  See <https://bugs.edge.launchpad.net/bzr/+bug/504102>
 
3239
        self._network_name = None
 
3240
 
 
3241
    def __repr__(self):
 
3242
        return "%s(_network_name=%r)" % (self.__class__.__name__,
 
3243
            self._network_name)
 
3244
 
2603
3245
    def get_format_description(self):
 
3246
        if self._network_name:
 
3247
            real_format = network_format_registry.get(self._network_name)
 
3248
            return 'Remote: ' + real_format.get_format_description()
2604
3249
        return 'bzr remote bzrdir'
2605
 
    
 
3250
 
 
3251
    def get_format_string(self):
 
3252
        raise NotImplementedError(self.get_format_string)
 
3253
 
 
3254
    def network_name(self):
 
3255
        if self._network_name:
 
3256
            return self._network_name
 
3257
        else:
 
3258
            raise AssertionError("No network name set.")
 
3259
 
2606
3260
    @classmethod
2607
3261
    def probe_transport(klass, transport):
2608
3262
        """Return a RemoteBzrDirFormat object if it looks possible."""
2637
3291
            return local_dir_format.initialize_on_transport(transport)
2638
3292
        client = _SmartClient(client_medium)
2639
3293
        path = client.remote_path_from_transport(transport)
2640
 
        response = client.call('BzrDirFormat.initialize', path)
 
3294
        try:
 
3295
            response = client.call('BzrDirFormat.initialize', path)
 
3296
        except errors.ErrorFromSmartServer, err:
 
3297
            remote._translate_error(err, path=path)
2641
3298
        if response[0] != 'ok':
2642
3299
            raise errors.SmartProtocolError('unexpected response code %s' % (response,))
2643
 
        return remote.RemoteBzrDir(transport)
 
3300
        format = RemoteBzrDirFormat()
 
3301
        self._supply_sub_formats_to(format)
 
3302
        return remote.RemoteBzrDir(transport, format)
 
3303
 
 
3304
    def parse_NoneTrueFalse(self, arg):
 
3305
        if not arg:
 
3306
            return None
 
3307
        if arg == 'False':
 
3308
            return False
 
3309
        if arg == 'True':
 
3310
            return True
 
3311
        raise AssertionError("invalid arg %r" % arg)
 
3312
 
 
3313
    def _serialize_NoneTrueFalse(self, arg):
 
3314
        if arg is False:
 
3315
            return 'False'
 
3316
        if arg:
 
3317
            return 'True'
 
3318
        return ''
 
3319
 
 
3320
    def _serialize_NoneString(self, arg):
 
3321
        return arg or ''
 
3322
 
 
3323
    def initialize_on_transport_ex(self, transport, use_existing_dir=False,
 
3324
        create_prefix=False, force_new_repo=False, stacked_on=None,
 
3325
        stack_on_pwd=None, repo_format_name=None, make_working_trees=None,
 
3326
        shared_repo=False):
 
3327
        try:
 
3328
            # hand off the request to the smart server
 
3329
            client_medium = transport.get_smart_medium()
 
3330
        except errors.NoSmartMedium:
 
3331
            do_vfs = True
 
3332
        else:
 
3333
            # Decline to open it if the server doesn't support our required
 
3334
            # version (3) so that the VFS-based transport will do it.
 
3335
            if client_medium.should_probe():
 
3336
                try:
 
3337
                    server_version = client_medium.protocol_version()
 
3338
                    if server_version != '2':
 
3339
                        do_vfs = True
 
3340
                    else:
 
3341
                        do_vfs = False
 
3342
                except errors.SmartProtocolError:
 
3343
                    # Apparently there's no usable smart server there, even though
 
3344
                    # the medium supports the smart protocol.
 
3345
                    do_vfs = True
 
3346
            else:
 
3347
                do_vfs = False
 
3348
        if not do_vfs:
 
3349
            client = _SmartClient(client_medium)
 
3350
            path = client.remote_path_from_transport(transport)
 
3351
            if client_medium._is_remote_before((1, 16)):
 
3352
                do_vfs = True
 
3353
        if do_vfs:
 
3354
            # TODO: lookup the local format from a server hint.
 
3355
            local_dir_format = BzrDirMetaFormat1()
 
3356
            self._supply_sub_formats_to(local_dir_format)
 
3357
            return local_dir_format.initialize_on_transport_ex(transport,
 
3358
                use_existing_dir=use_existing_dir, create_prefix=create_prefix,
 
3359
                force_new_repo=force_new_repo, stacked_on=stacked_on,
 
3360
                stack_on_pwd=stack_on_pwd, repo_format_name=repo_format_name,
 
3361
                make_working_trees=make_working_trees, shared_repo=shared_repo,
 
3362
                vfs_only=True)
 
3363
        return self._initialize_on_transport_ex_rpc(client, path, transport,
 
3364
            use_existing_dir, create_prefix, force_new_repo, stacked_on,
 
3365
            stack_on_pwd, repo_format_name, make_working_trees, shared_repo)
 
3366
 
 
3367
    def _initialize_on_transport_ex_rpc(self, client, path, transport,
 
3368
        use_existing_dir, create_prefix, force_new_repo, stacked_on,
 
3369
        stack_on_pwd, repo_format_name, make_working_trees, shared_repo):
 
3370
        args = []
 
3371
        args.append(self._serialize_NoneTrueFalse(use_existing_dir))
 
3372
        args.append(self._serialize_NoneTrueFalse(create_prefix))
 
3373
        args.append(self._serialize_NoneTrueFalse(force_new_repo))
 
3374
        args.append(self._serialize_NoneString(stacked_on))
 
3375
        # stack_on_pwd is often/usually our transport
 
3376
        if stack_on_pwd:
 
3377
            try:
 
3378
                stack_on_pwd = transport.relpath(stack_on_pwd)
 
3379
                if not stack_on_pwd:
 
3380
                    stack_on_pwd = '.'
 
3381
            except errors.PathNotChild:
 
3382
                pass
 
3383
        args.append(self._serialize_NoneString(stack_on_pwd))
 
3384
        args.append(self._serialize_NoneString(repo_format_name))
 
3385
        args.append(self._serialize_NoneTrueFalse(make_working_trees))
 
3386
        args.append(self._serialize_NoneTrueFalse(shared_repo))
 
3387
        request_network_name = self._network_name or \
 
3388
            BzrDirFormat.get_default_format().network_name()
 
3389
        try:
 
3390
            response = client.call('BzrDirFormat.initialize_ex_1.16',
 
3391
                request_network_name, path, *args)
 
3392
        except errors.UnknownSmartMethod:
 
3393
            client._medium._remember_remote_is_before((1,16))
 
3394
            local_dir_format = BzrDirMetaFormat1()
 
3395
            self._supply_sub_formats_to(local_dir_format)
 
3396
            return local_dir_format.initialize_on_transport_ex(transport,
 
3397
                use_existing_dir=use_existing_dir, create_prefix=create_prefix,
 
3398
                force_new_repo=force_new_repo, stacked_on=stacked_on,
 
3399
                stack_on_pwd=stack_on_pwd, repo_format_name=repo_format_name,
 
3400
                make_working_trees=make_working_trees, shared_repo=shared_repo,
 
3401
                vfs_only=True)
 
3402
        except errors.ErrorFromSmartServer, err:
 
3403
            remote._translate_error(err, path=path)
 
3404
        repo_path = response[0]
 
3405
        bzrdir_name = response[6]
 
3406
        require_stacking = response[7]
 
3407
        require_stacking = self.parse_NoneTrueFalse(require_stacking)
 
3408
        format = RemoteBzrDirFormat()
 
3409
        format._network_name = bzrdir_name
 
3410
        self._supply_sub_formats_to(format)
 
3411
        bzrdir = remote.RemoteBzrDir(transport, format, _client=client)
 
3412
        if repo_path:
 
3413
            repo_format = remote.response_tuple_to_repo_format(response[1:])
 
3414
            if repo_path == '.':
 
3415
                repo_path = ''
 
3416
            if repo_path:
 
3417
                repo_bzrdir_format = RemoteBzrDirFormat()
 
3418
                repo_bzrdir_format._network_name = response[5]
 
3419
                repo_bzr = remote.RemoteBzrDir(transport.clone(repo_path),
 
3420
                    repo_bzrdir_format)
 
3421
            else:
 
3422
                repo_bzr = bzrdir
 
3423
            final_stack = response[8] or None
 
3424
            final_stack_pwd = response[9] or None
 
3425
            if final_stack_pwd:
 
3426
                final_stack_pwd = urlutils.join(
 
3427
                    transport.base, final_stack_pwd)
 
3428
            remote_repo = remote.RemoteRepository(repo_bzr, repo_format)
 
3429
            if len(response) > 10:
 
3430
                # Updated server verb that locks remotely.
 
3431
                repo_lock_token = response[10] or None
 
3432
                remote_repo.lock_write(repo_lock_token, _skip_rpc=True)
 
3433
                if repo_lock_token:
 
3434
                    remote_repo.dont_leave_lock_in_place()
 
3435
            else:
 
3436
                remote_repo.lock_write()
 
3437
            policy = UseExistingRepository(remote_repo, final_stack,
 
3438
                final_stack_pwd, require_stacking)
 
3439
            policy.acquire_repository()
 
3440
        else:
 
3441
            remote_repo = None
 
3442
            policy = None
 
3443
        bzrdir._format.set_branch_format(self.get_branch_format())
 
3444
        if require_stacking:
 
3445
            # The repo has already been created, but we need to make sure that
 
3446
            # we'll make a stackable branch.
 
3447
            bzrdir._format.require_stacking(_skip_repo=True)
 
3448
        return remote_repo, bzrdir, require_stacking, policy
2644
3449
 
2645
3450
    def _open(self, transport):
2646
 
        return remote.RemoteBzrDir(transport)
 
3451
        return remote.RemoteBzrDir(transport, self)
2647
3452
 
2648
3453
    def __eq__(self, other):
2649
3454
        if not isinstance(other, RemoteBzrDirFormat):
2650
3455
            return False
2651
3456
        return self.get_format_description() == other.get_format_description()
2652
3457
 
2653
 
    @property
2654
 
    def repository_format(self):
2655
 
        # Using a property to avoid early loading of remote
2656
 
        return remote.RemoteRepositoryFormat()
 
3458
    def __return_repository_format(self):
 
3459
        # Always return a RemoteRepositoryFormat object, but if a specific bzr
 
3460
        # repository format has been asked for, tell the RemoteRepositoryFormat
 
3461
        # that it should use that for init() etc.
 
3462
        result = remote.RemoteRepositoryFormat()
 
3463
        custom_format = getattr(self, '_repository_format', None)
 
3464
        if custom_format:
 
3465
            if isinstance(custom_format, remote.RemoteRepositoryFormat):
 
3466
                return custom_format
 
3467
            else:
 
3468
                # We will use the custom format to create repositories over the
 
3469
                # wire; expose its details like rich_root_data for code to
 
3470
                # query
 
3471
                result._custom_format = custom_format
 
3472
        return result
 
3473
 
 
3474
    def get_branch_format(self):
 
3475
        result = BzrDirMetaFormat1.get_branch_format(self)
 
3476
        if not isinstance(result, remote.RemoteBranchFormat):
 
3477
            new_result = remote.RemoteBranchFormat()
 
3478
            new_result._custom_format = result
 
3479
            # cache the result
 
3480
            self.set_branch_format(new_result)
 
3481
            result = new_result
 
3482
        return result
 
3483
 
 
3484
    repository_format = property(__return_repository_format,
 
3485
        BzrDirMetaFormat1._set_repository_format) #.im_func)
2657
3486
 
2658
3487
 
2659
3488
BzrDirFormat.register_control_server_format(RemoteBzrDirFormat)
2670
3499
 
2671
3500
class BzrDirFormatRegistry(registry.Registry):
2672
3501
    """Registry of user-selectable BzrDir subformats.
2673
 
    
 
3502
 
2674
3503
    Differs from BzrDirFormat._control_formats in that it provides sub-formats,
2675
3504
    e.g. BzrDirMeta1 with weave repository.  Also, it's more user-oriented.
2676
3505
    """
2678
3507
    def __init__(self):
2679
3508
        """Create a BzrDirFormatRegistry."""
2680
3509
        self._aliases = set()
 
3510
        self._registration_order = list()
2681
3511
        super(BzrDirFormatRegistry, self).__init__()
2682
3512
 
2683
3513
    def aliases(self):
2694
3524
        """Register a metadir subformat.
2695
3525
 
2696
3526
        These all use a BzrDirMetaFormat1 bzrdir, but can be parameterized
2697
 
        by the Repository format.
 
3527
        by the Repository/Branch/WorkingTreeformats.
2698
3528
 
2699
3529
        :param repository_format: The fully-qualified repository format class
2700
3530
            name as a string.
2734
3564
    def register(self, key, factory, help, native=True, deprecated=False,
2735
3565
                 hidden=False, experimental=False, alias=False):
2736
3566
        """Register a BzrDirFormat factory.
2737
 
        
 
3567
 
2738
3568
        The factory must be a callable that takes one parameter: the key.
2739
3569
        It must produce an instance of the BzrDirFormat when called.
2740
3570
 
2745
3575
            BzrDirFormatInfo(native, deprecated, hidden, experimental))
2746
3576
        if alias:
2747
3577
            self._aliases.add(key)
 
3578
        self._registration_order.append(key)
2748
3579
 
2749
3580
    def register_lazy(self, key, module_name, member_name, help, native=True,
2750
3581
        deprecated=False, hidden=False, experimental=False, alias=False):
2752
3583
            help, BzrDirFormatInfo(native, deprecated, hidden, experimental))
2753
3584
        if alias:
2754
3585
            self._aliases.add(key)
 
3586
        self._registration_order.append(key)
2755
3587
 
2756
3588
    def set_default(self, key):
2757
3589
        """Set the 'default' key to be a clone of the supplied key.
2758
 
        
 
3590
 
2759
3591
        This method must be called once and only once.
2760
3592
        """
2761
3593
        registry.Registry.register(self, 'default', self.get(key),
2764
3596
 
2765
3597
    def set_default_repository(self, key):
2766
3598
        """Set the FormatRegistry default and Repository default.
2767
 
        
 
3599
 
2768
3600
        This is a transitional method while Repository.set_default_format
2769
3601
        is deprecated.
2770
3602
        """
2777
3609
        return self.get(key)()
2778
3610
 
2779
3611
    def help_topic(self, topic):
2780
 
        output = textwrap.dedent("""\
2781
 
            These formats can be used for creating branches, working trees, and
2782
 
            repositories.
2783
 
 
2784
 
            """)
 
3612
        output = ""
2785
3613
        default_realkey = None
2786
3614
        default_help = self.get_help('default')
2787
3615
        help_pairs = []
2788
 
        for key in self.keys():
 
3616
        for key in self._registration_order:
2789
3617
            if key == 'default':
2790
3618
                continue
2791
3619
            help = self.get_help(key)
2797
3625
        def wrapped(key, help, info):
2798
3626
            if info.native:
2799
3627
                help = '(native) ' + help
2800
 
            return ':%s:\n%s\n\n' % (key, 
2801
 
                    textwrap.fill(help, initial_indent='    ', 
2802
 
                    subsequent_indent='    '))
 
3628
            return ':%s:\n%s\n\n' % (key,
 
3629
                textwrap.fill(help, initial_indent='    ',
 
3630
                    subsequent_indent='    ',
 
3631
                    break_long_words=False))
2803
3632
        if default_realkey is not None:
2804
3633
            output += wrapped(default_realkey, '(default) %s' % default_help,
2805
3634
                              self.get_info('default'))
2815
3644
                experimental_pairs.append((key, help))
2816
3645
            else:
2817
3646
                output += wrapped(key, help, info)
 
3647
        output += "\nSee :doc:`formats-help` for more about storage formats."
 
3648
        other_output = ""
2818
3649
        if len(experimental_pairs) > 0:
2819
 
            output += "Experimental formats are shown below.\n\n"
 
3650
            other_output += "Experimental formats are shown below.\n\n"
2820
3651
            for key, help in experimental_pairs:
2821
3652
                info = self.get_info(key)
2822
 
                output += wrapped(key, help, info)
 
3653
                other_output += wrapped(key, help, info)
 
3654
        else:
 
3655
            other_output += \
 
3656
                "No experimental formats are available.\n\n"
2823
3657
        if len(deprecated_pairs) > 0:
2824
 
            output += "Deprecated formats are shown below.\n\n"
 
3658
            other_output += "\nDeprecated formats are shown below.\n\n"
2825
3659
            for key, help in deprecated_pairs:
2826
3660
                info = self.get_info(key)
2827
 
                output += wrapped(key, help, info)
 
3661
                other_output += wrapped(key, help, info)
 
3662
        else:
 
3663
            other_output += \
 
3664
                "\nNo deprecated formats are available.\n\n"
 
3665
        other_output += \
 
3666
                "\nSee :doc:`formats-help` for more about storage formats."
2828
3667
 
2829
 
        return output
 
3668
        if topic == 'other-formats':
 
3669
            return other_output
 
3670
        else:
 
3671
            return output
2830
3672
 
2831
3673
 
2832
3674
class RepositoryAcquisitionPolicy(object):
2861
3703
            try:
2862
3704
                stack_on = urlutils.rebase_url(self._stack_on,
2863
3705
                    self._stack_on_pwd,
2864
 
                    branch.bzrdir.root_transport.base)
 
3706
                    branch.user_url)
2865
3707
            except errors.InvalidRebaseURLs:
2866
3708
                stack_on = self._get_full_stack_on()
2867
3709
        try:
2868
3710
            branch.set_stacked_on_url(stack_on)
2869
 
        except errors.UnstackableBranchFormat:
 
3711
        except (errors.UnstackableBranchFormat,
 
3712
                errors.UnstackableRepositoryFormat):
2870
3713
            if self._require_stacking:
2871
3714
                raise
2872
3715
 
 
3716
    def requires_stacking(self):
 
3717
        """Return True if this policy requires stacking."""
 
3718
        return self._stack_on is not None and self._require_stacking
 
3719
 
2873
3720
    def _get_full_stack_on(self):
2874
3721
        """Get a fully-qualified URL for the stack_on location."""
2875
3722
        if self._stack_on is None:
2879
3726
        else:
2880
3727
            return urlutils.join(self._stack_on_pwd, self._stack_on)
2881
3728
 
2882
 
    def _add_fallback(self, repository):
 
3729
    def _add_fallback(self, repository, possible_transports=None):
2883
3730
        """Add a fallback to the supplied repository, if stacking is set."""
2884
3731
        stack_on = self._get_full_stack_on()
2885
3732
        if stack_on is None:
2886
3733
            return
2887
 
        stacked_dir = BzrDir.open(stack_on)
 
3734
        try:
 
3735
            stacked_dir = BzrDir.open(stack_on,
 
3736
                                      possible_transports=possible_transports)
 
3737
        except errors.JailBreak:
 
3738
            # We keep the stacking details, but we are in the server code so
 
3739
            # actually stacking is not needed.
 
3740
            return
2888
3741
        try:
2889
3742
            stacked_repo = stacked_dir.open_branch().repository
2890
3743
        except errors.NotBranchError:
2894
3747
        except errors.UnstackableRepositoryFormat:
2895
3748
            if self._require_stacking:
2896
3749
                raise
 
3750
        else:
 
3751
            self._require_stacking = True
2897
3752
 
2898
3753
    def acquire_repository(self, make_working_trees=None, shared=False):
2899
3754
        """Acquire a repository for this bzrdir.
2903
3758
        :param make_working_trees: If creating a repository, set
2904
3759
            make_working_trees to this value (if non-None)
2905
3760
        :param shared: If creating a repository, make it shared if True
2906
 
        :return: A repository
 
3761
        :return: A repository, is_new_flag (True if the repository was
 
3762
            created).
2907
3763
        """
2908
3764
        raise NotImplemented(RepositoryAcquisitionPolicy.acquire_repository)
2909
3765
 
2929
3785
 
2930
3786
        Creates the desired repository in the bzrdir we already have.
2931
3787
        """
 
3788
        stack_on = self._get_full_stack_on()
 
3789
        if stack_on:
 
3790
            format = self._bzrdir._format
 
3791
            format.require_stacking(stack_on=stack_on,
 
3792
                                    possible_transports=[self._bzrdir.root_transport])
 
3793
            if not self._require_stacking:
 
3794
                # We have picked up automatic stacking somewhere.
 
3795
                note('Using default stacking branch %s at %s', self._stack_on,
 
3796
                    self._stack_on_pwd)
2932
3797
        repository = self._bzrdir.create_repository(shared=shared)
2933
 
        self._add_fallback(repository)
 
3798
        self._add_fallback(repository,
 
3799
                           possible_transports=[self._bzrdir.transport])
2934
3800
        if make_working_trees is not None:
2935
3801
            repository.set_make_working_trees(make_working_trees)
2936
 
        return repository
 
3802
        return repository, True
2937
3803
 
2938
3804
 
2939
3805
class UseExistingRepository(RepositoryAcquisitionPolicy):
2955
3821
    def acquire_repository(self, make_working_trees=None, shared=False):
2956
3822
        """Implementation of RepositoryAcquisitionPolicy.acquire_repository
2957
3823
 
2958
 
        Returns an existing repository to use
 
3824
        Returns an existing repository to use.
2959
3825
        """
2960
 
        self._add_fallback(self._repository)
2961
 
        return self._repository
2962
 
 
2963
 
 
 
3826
        self._add_fallback(self._repository,
 
3827
                       possible_transports=[self._repository.bzrdir.transport])
 
3828
        return self._repository, False
 
3829
 
 
3830
 
 
3831
# Please register new formats after old formats so that formats
 
3832
# appear in chronological order and format descriptions can build
 
3833
# on previous ones.
2964
3834
format_registry = BzrDirFormatRegistry()
 
3835
# The pre-0.8 formats have their repository format network name registered in
 
3836
# repository.py. MetaDir formats have their repository format network name
 
3837
# inferred from their disk format string.
2965
3838
format_registry.register('weave', BzrDirFormat6,
2966
3839
    'Pre-0.8 format.  Slower than knit and does not'
2967
3840
    ' support checkouts or shared repositories.',
 
3841
    hidden=True,
2968
3842
    deprecated=True)
2969
 
format_registry.register_metadir('knit',
2970
 
    'bzrlib.repofmt.knitrepo.RepositoryFormatKnit1',
2971
 
    'Format using knits.  Recommended for interoperation with bzr <= 0.14.',
2972
 
    branch_format='bzrlib.branch.BzrBranchFormat5',
2973
 
    tree_format='bzrlib.workingtree.WorkingTreeFormat3')
2974
3843
format_registry.register_metadir('metaweave',
2975
3844
    'bzrlib.repofmt.weaverepo.RepositoryFormat7',
2976
3845
    'Transitional format in 0.8.  Slower than knit.',
2977
3846
    branch_format='bzrlib.branch.BzrBranchFormat5',
2978
3847
    tree_format='bzrlib.workingtree.WorkingTreeFormat3',
 
3848
    hidden=True,
 
3849
    deprecated=True)
 
3850
format_registry.register_metadir('knit',
 
3851
    'bzrlib.repofmt.knitrepo.RepositoryFormatKnit1',
 
3852
    'Format using knits.  Recommended for interoperation with bzr <= 0.14.',
 
3853
    branch_format='bzrlib.branch.BzrBranchFormat5',
 
3854
    tree_format='bzrlib.workingtree.WorkingTreeFormat3',
 
3855
    hidden=True,
2979
3856
    deprecated=True)
2980
3857
format_registry.register_metadir('dirstate',
2981
3858
    'bzrlib.repofmt.knitrepo.RepositoryFormatKnit1',
2985
3862
    # this uses bzrlib.workingtree.WorkingTreeFormat4 because importing
2986
3863
    # directly from workingtree_4 triggers a circular import.
2987
3864
    tree_format='bzrlib.workingtree.WorkingTreeFormat4',
2988
 
    )
 
3865
    hidden=True,
 
3866
    deprecated=True)
2989
3867
format_registry.register_metadir('dirstate-tags',
2990
3868
    'bzrlib.repofmt.knitrepo.RepositoryFormatKnit1',
2991
3869
    help='New in 0.15: Fast local operations and improved scaling for '
2993
3871
        ' Incompatible with bzr < 0.15.',
2994
3872
    branch_format='bzrlib.branch.BzrBranchFormat6',
2995
3873
    tree_format='bzrlib.workingtree.WorkingTreeFormat4',
2996
 
    )
 
3874
    hidden=True,
 
3875
    deprecated=True)
2997
3876
format_registry.register_metadir('rich-root',
2998
3877
    'bzrlib.repofmt.knitrepo.RepositoryFormatKnit4',
2999
3878
    help='New in 1.0.  Better handling of tree roots.  Incompatible with'
3000
 
        ' bzr < 1.0',
 
3879
        ' bzr < 1.0.',
3001
3880
    branch_format='bzrlib.branch.BzrBranchFormat6',
3002
3881
    tree_format='bzrlib.workingtree.WorkingTreeFormat4',
3003
 
    )
 
3882
    hidden=True,
 
3883
    deprecated=True)
3004
3884
format_registry.register_metadir('dirstate-with-subtree',
3005
3885
    'bzrlib.repofmt.knitrepo.RepositoryFormatKnit3',
3006
3886
    help='New in 0.15: Fast local operations and improved scaling for '
3016
3896
    help='New in 0.92: Pack-based format with data compatible with '
3017
3897
        'dirstate-tags format repositories. Interoperates with '
3018
3898
        'bzr repositories before 0.92 but cannot be read by bzr < 0.92. '
3019
 
        'Previously called knitpack-experimental.  '
3020
 
        'For more information, see '
3021
 
        'http://doc.bazaar-vcs.org/latest/developers/packrepo.html.',
 
3899
        ,
3022
3900
    branch_format='bzrlib.branch.BzrBranchFormat6',
3023
3901
    tree_format='bzrlib.workingtree.WorkingTreeFormat4',
3024
3902
    )
3027
3905
    help='New in 0.92: Pack-based format with data compatible with '
3028
3906
        'dirstate-with-subtree format repositories. Interoperates with '
3029
3907
        'bzr repositories before 0.92 but cannot be read by bzr < 0.92. '
3030
 
        'Previously called knitpack-experimental.  '
3031
 
        'For more information, see '
3032
 
        'http://doc.bazaar-vcs.org/latest/developers/packrepo.html.',
 
3908
        ,
3033
3909
    branch_format='bzrlib.branch.BzrBranchFormat6',
3034
3910
    tree_format='bzrlib.workingtree.WorkingTreeFormat4',
3035
3911
    hidden=True,
3037
3913
    )
3038
3914
format_registry.register_metadir('rich-root-pack',
3039
3915
    'bzrlib.repofmt.pack_repo.RepositoryFormatKnitPack4',
3040
 
    help='New in 1.0: Pack-based format with data compatible with '
3041
 
        'rich-root format repositories. Incompatible with'
3042
 
        ' bzr < 1.0',
 
3916
    help='New in 1.0: A variant of pack-0.92 that supports rich-root data '
 
3917
         '(needed for bzr-svn and bzr-git).',
3043
3918
    branch_format='bzrlib.branch.BzrBranchFormat6',
3044
3919
    tree_format='bzrlib.workingtree.WorkingTreeFormat4',
 
3920
    hidden=True,
3045
3921
    )
3046
3922
format_registry.register_metadir('1.6',
3047
3923
    'bzrlib.repofmt.pack_repo.RepositoryFormatKnitPack5',
3048
 
    help='A branch and pack based repository that supports stacking. ',
 
3924
    help='A format that allows a branch to indicate that there is another '
 
3925
         '(stacked) repository that should be used to access data that is '
 
3926
         'not present locally.',
3049
3927
    branch_format='bzrlib.branch.BzrBranchFormat7',
3050
3928
    tree_format='bzrlib.workingtree.WorkingTreeFormat4',
 
3929
    hidden=True,
3051
3930
    )
3052
3931
format_registry.register_metadir('1.6.1-rich-root',
3053
3932
    'bzrlib.repofmt.pack_repo.RepositoryFormatKnitPack5RichRoot',
3054
 
    help='A branch and pack based repository that supports stacking '
3055
 
         'and rich root data (needed for bzr-svn). ',
 
3933
    help='A variant of 1.6 that supports rich-root data '
 
3934
         '(needed for bzr-svn and bzr-git).',
3056
3935
    branch_format='bzrlib.branch.BzrBranchFormat7',
3057
3936
    tree_format='bzrlib.workingtree.WorkingTreeFormat4',
 
3937
    hidden=True,
3058
3938
    )
3059
3939
format_registry.register_metadir('1.9',
3060
3940
    'bzrlib.repofmt.pack_repo.RepositoryFormatKnitPack6',
3061
 
    help='A branch and pack based repository that uses btree indexes. ',
 
3941
    help='A repository format using B+tree indexes. These indexes '
 
3942
         'are smaller in size, have smarter caching and provide faster '
 
3943
         'performance for most operations.',
3062
3944
    branch_format='bzrlib.branch.BzrBranchFormat7',
3063
3945
    tree_format='bzrlib.workingtree.WorkingTreeFormat4',
 
3946
    hidden=True,
3064
3947
    )
3065
3948
format_registry.register_metadir('1.9-rich-root',
3066
3949
    'bzrlib.repofmt.pack_repo.RepositoryFormatKnitPack6RichRoot',
3067
 
    help='A branch and pack based repository that uses btree indexes '
3068
 
         'and rich root data (needed for bzr-svn). ',
 
3950
    help='A variant of 1.9 that supports rich-root data '
 
3951
         '(needed for bzr-svn and bzr-git).',
3069
3952
    branch_format='bzrlib.branch.BzrBranchFormat7',
3070
3953
    tree_format='bzrlib.workingtree.WorkingTreeFormat4',
3071
 
    )
3072
 
# The following two formats should always just be aliases.
3073
 
format_registry.register_metadir('development',
3074
 
    'bzrlib.repofmt.pack_repo.RepositoryFormatPackDevelopment2',
3075
 
    help='Current development format. Can convert data to and from pack-0.92 '
3076
 
        '(and anything compatible with pack-0.92) format repositories. '
3077
 
        'Repositories and branches in this format can only be read by bzr.dev. '
3078
 
        'Please read '
3079
 
        'http://doc.bazaar-vcs.org/latest/developers/development-repo.html '
 
3954
    hidden=True,
 
3955
    )
 
3956
format_registry.register_metadir('1.14',
 
3957
    'bzrlib.repofmt.pack_repo.RepositoryFormatKnitPack6',
 
3958
    help='A working-tree format that supports content filtering.',
 
3959
    branch_format='bzrlib.branch.BzrBranchFormat7',
 
3960
    tree_format='bzrlib.workingtree.WorkingTreeFormat5',
 
3961
    )
 
3962
format_registry.register_metadir('1.14-rich-root',
 
3963
    'bzrlib.repofmt.pack_repo.RepositoryFormatKnitPack6RichRoot',
 
3964
    help='A variant of 1.14 that supports rich-root data '
 
3965
         '(needed for bzr-svn and bzr-git).',
 
3966
    branch_format='bzrlib.branch.BzrBranchFormat7',
 
3967
    tree_format='bzrlib.workingtree.WorkingTreeFormat5',
 
3968
    )
 
3969
# The following un-numbered 'development' formats should always just be aliases.
 
3970
format_registry.register_metadir('development-rich-root',
 
3971
    'bzrlib.repofmt.groupcompress_repo.RepositoryFormatCHK1',
 
3972
    help='Current development format. Supports rich roots. Can convert data '
 
3973
        'to and from rich-root-pack (and anything compatible with '
 
3974
        'rich-root-pack) format repositories. Repositories and branches in '
 
3975
        'this format can only be read by bzr.dev. Please read '
 
3976
        'http://doc.bazaar.canonical.com/latest/developers/development-repo.html '
3080
3977
        'before use.',
3081
3978
    branch_format='bzrlib.branch.BzrBranchFormat7',
3082
 
    tree_format='bzrlib.workingtree.WorkingTreeFormat4',
 
3979
    tree_format='bzrlib.workingtree.WorkingTreeFormat6',
3083
3980
    experimental=True,
3084
3981
    alias=True,
 
3982
    hidden=True,
3085
3983
    )
3086
3984
format_registry.register_metadir('development-subtree',
3087
3985
    'bzrlib.repofmt.pack_repo.RepositoryFormatPackDevelopment2Subtree',
3089
3987
        'from pack-0.92-subtree (and anything compatible with '
3090
3988
        'pack-0.92-subtree) format repositories. Repositories and branches in '
3091
3989
        'this format can only be read by bzr.dev. Please read '
3092
 
        'http://doc.bazaar-vcs.org/latest/developers/development-repo.html '
 
3990
        'http://doc.bazaar.canonical.com/latest/developers/development-repo.html '
3093
3991
        'before use.',
3094
3992
    branch_format='bzrlib.branch.BzrBranchFormat7',
3095
 
    tree_format='bzrlib.workingtree.WorkingTreeFormat4',
 
3993
    tree_format='bzrlib.workingtree.WorkingTreeFormat6',
3096
3994
    experimental=True,
3097
 
    alias=True,
 
3995
    hidden=True,
 
3996
    alias=False, # Restore to being an alias when an actual development subtree format is added
 
3997
                 # This current non-alias status is simply because we did not introduce a
 
3998
                 # chk based subtree format.
3098
3999
    )
 
4000
 
3099
4001
# And the development formats above will have aliased one of the following:
3100
 
format_registry.register_metadir('development2',
3101
 
    'bzrlib.repofmt.pack_repo.RepositoryFormatPackDevelopment2',
3102
 
    help='1.6.1 with B+Tree based index. '
3103
 
        'Please read '
3104
 
        'http://doc.bazaar-vcs.org/latest/developers/development-repo.html '
3105
 
        'before use.',
3106
 
    branch_format='bzrlib.branch.BzrBranchFormat7',
3107
 
    tree_format='bzrlib.workingtree.WorkingTreeFormat4',
3108
 
    hidden=True,
3109
 
    experimental=True,
3110
 
    )
3111
 
format_registry.register_metadir('development2-subtree',
3112
 
    'bzrlib.repofmt.pack_repo.RepositoryFormatPackDevelopment2Subtree',
3113
 
    help='1.6.1-subtree with B+Tree based index. '
3114
 
        'Please read '
3115
 
        'http://doc.bazaar-vcs.org/latest/developers/development-repo.html '
3116
 
        'before use.',
3117
 
    branch_format='bzrlib.branch.BzrBranchFormat7',
3118
 
    tree_format='bzrlib.workingtree.WorkingTreeFormat4',
3119
 
    hidden=True,
3120
 
    experimental=True,
3121
 
    )
 
4002
format_registry.register_metadir('development6-rich-root',
 
4003
    'bzrlib.repofmt.groupcompress_repo.RepositoryFormatCHK1',
 
4004
    help='pack-1.9 with 255-way hashed CHK inv, group compress, rich roots '
 
4005
        'Please read '
 
4006
        'http://doc.bazaar.canonical.com/latest/developers/development-repo.html '
 
4007
        'before use.',
 
4008
    branch_format='bzrlib.branch.BzrBranchFormat7',
 
4009
    tree_format='bzrlib.workingtree.WorkingTreeFormat6',
 
4010
    hidden=True,
 
4011
    experimental=True,
 
4012
    )
 
4013
 
 
4014
format_registry.register_metadir('development7-rich-root',
 
4015
    'bzrlib.repofmt.groupcompress_repo.RepositoryFormatCHK2',
 
4016
    help='pack-1.9 with 255-way hashed CHK inv, bencode revision, group compress, '
 
4017
        'rich roots. Please read '
 
4018
        'http://doc.bazaar.canonical.com/latest/developers/development-repo.html '
 
4019
        'before use.',
 
4020
    branch_format='bzrlib.branch.BzrBranchFormat7',
 
4021
    tree_format='bzrlib.workingtree.WorkingTreeFormat6',
 
4022
    hidden=True,
 
4023
    experimental=True,
 
4024
    )
 
4025
 
 
4026
format_registry.register_metadir('2a',
 
4027
    'bzrlib.repofmt.groupcompress_repo.RepositoryFormat2a',
 
4028
    help='First format for bzr 2.0 series.\n'
 
4029
        'Uses group-compress storage.\n'
 
4030
        'Provides rich roots which are a one-way transition.\n',
 
4031
        # 'storage in packs, 255-way hashed CHK inventory, bencode revision, group compress, '
 
4032
        # 'rich roots. Supported by bzr 1.16 and later.',
 
4033
    branch_format='bzrlib.branch.BzrBranchFormat7',
 
4034
    tree_format='bzrlib.workingtree.WorkingTreeFormat6',
 
4035
    experimental=True,
 
4036
    )
 
4037
 
 
4038
# The following format should be an alias for the rich root equivalent 
 
4039
# of the default format
 
4040
format_registry.register_metadir('default-rich-root',
 
4041
    'bzrlib.repofmt.groupcompress_repo.RepositoryFormat2a',
 
4042
    branch_format='bzrlib.branch.BzrBranchFormat7',
 
4043
    tree_format='bzrlib.workingtree.WorkingTreeFormat6',
 
4044
    alias=True,
 
4045
    hidden=True,
 
4046
    help='Same as 2a.')
 
4047
 
3122
4048
# The current format that is made on 'bzr init'.
3123
 
format_registry.set_default('pack-0.92')
 
4049
format_registry.set_default('2a')