~bzr-pqm/bzr/bzr.dev

« back to all changes in this revision

Viewing changes to bzrlib/builtins.py

  • Committer: Robert Collins
  • Date: 2010-06-21 01:30:45 UTC
  • mfrom: (5309 +trunk)
  • mto: This revision was merged to the branch mainline in revision 5310.
  • Revision ID: robertc@robertcollins.net-20100621013045-s59nfjps3rkcn53j
Merge trunk to fix NEWS sections.

Show diffs side-by-side

added added

removed removed

Lines of Context:
491
491
    takes_options = [
492
492
        Option('force',
493
493
               help='Remove the working tree even if it has '
494
 
                    'uncommitted changes.'),
 
494
                    'uncommitted or shelved changes.'),
495
495
        ]
496
496
 
497
497
    def run(self, location_list, force=False):
511
511
            if not force:
512
512
                if (working.has_changes()):
513
513
                    raise errors.UncommittedChanges(working)
 
514
                if working.get_shelf_manager().last_shelf() is not None:
 
515
                    raise errors.ShelvedChanges(working)
514
516
 
515
517
            if working.user_url != working.branch.user_url:
516
518
                raise errors.BzrCommandError("You cannot remove the working tree"
536
538
        if tree:
537
539
            try:
538
540
                wt = WorkingTree.open_containing(location)[0]
539
 
                wt.lock_read()
 
541
                self.add_cleanup(wt.lock_read().unlock)
540
542
            except (errors.NoWorkingTree, errors.NotLocalUrl):
541
543
                raise errors.NoWorkingTree(location)
542
 
            self.add_cleanup(wt.unlock)
543
544
            revid = wt.last_revision()
544
545
            try:
545
546
                revno_t = wt.branch.revision_id_to_dotted_revno(revid)
548
549
            revno = ".".join(str(n) for n in revno_t)
549
550
        else:
550
551
            b = Branch.open_containing(location)[0]
551
 
            b.lock_read()
552
 
            self.add_cleanup(b.unlock)
 
552
            self.add_cleanup(b.lock_read().unlock)
553
553
            revno = b.revno()
554
554
        self.cleanup_now()
555
555
        self.outf.write(str(revno) + '\n')
575
575
        try:
576
576
            wt = WorkingTree.open_containing(directory)[0]
577
577
            b = wt.branch
578
 
            wt.lock_read()
579
 
            self.add_cleanup(wt.unlock)
 
578
            self.add_cleanup(wt.lock_read().unlock)
580
579
        except (errors.NoWorkingTree, errors.NotLocalUrl):
581
580
            wt = None
582
581
            b = Branch.open_containing(directory)[0]
583
 
            b.lock_read()
584
 
            self.add_cleanup(b.unlock)
 
582
            self.add_cleanup(b.lock_read().unlock)
585
583
        revision_ids = []
586
584
        if revision is not None:
587
585
            revision_ids.extend(rev.as_revision_id(b) for rev in revision)
686
684
                should_print=(not is_quiet()))
687
685
 
688
686
        if base_tree:
689
 
            base_tree.lock_read()
690
 
            self.add_cleanup(base_tree.unlock)
 
687
            self.add_cleanup(base_tree.lock_read().unlock)
691
688
        tree, file_list = tree_files_for_add(file_list)
692
689
        added, ignored = tree.smart_add(file_list, not
693
690
            no_recurse, action=action, save=not dry_run)
765
762
 
766
763
        revision = _get_one_revision('inventory', revision)
767
764
        work_tree, file_list = tree_files(file_list)
768
 
        work_tree.lock_read()
769
 
        self.add_cleanup(work_tree.unlock)
 
765
        self.add_cleanup(work_tree.lock_read().unlock)
770
766
        if revision is not None:
771
767
            tree = revision.as_tree(work_tree.branch)
772
768
 
773
769
            extra_trees = [work_tree]
774
 
            tree.lock_read()
775
 
            self.add_cleanup(tree.unlock)
 
770
            self.add_cleanup(tree.lock_read().unlock)
776
771
        else:
777
772
            tree = work_tree
778
773
            extra_trees = []
838
833
        if len(names_list) < 2:
839
834
            raise errors.BzrCommandError("missing file argument")
840
835
        tree, rel_names = tree_files(names_list, canonicalize=False)
841
 
        tree.lock_tree_write()
842
 
        self.add_cleanup(tree.unlock)
 
836
        self.add_cleanup(tree.lock_tree_write().unlock)
843
837
        self._run(tree, names_list, rel_names, after)
844
838
 
845
839
    def run_auto(self, names_list, after, dry_run):
850
844
            raise errors.BzrCommandError('--after cannot be specified with'
851
845
                                         ' --auto.')
852
846
        work_tree, file_list = tree_files(names_list, default_branch='.')
853
 
        work_tree.lock_tree_write()
854
 
        self.add_cleanup(work_tree.unlock)
 
847
        self.add_cleanup(work_tree.lock_tree_write().unlock)
855
848
        rename_map.RenameMap.guess_renames(work_tree, dry_run)
856
849
 
857
850
    def _run(self, tree, names_list, rel_names, after):
988
981
        try:
989
982
            tree_to = WorkingTree.open_containing(directory)[0]
990
983
            branch_to = tree_to.branch
991
 
            tree_to.lock_write()
992
 
            self.add_cleanup(tree_to.unlock)
 
984
            self.add_cleanup(tree_to.lock_write().unlock)
993
985
        except errors.NoWorkingTree:
994
986
            tree_to = None
995
987
            branch_to = Branch.open_containing(directory)[0]
996
 
            branch_to.lock_write()
997
 
            self.add_cleanup(branch_to.unlock)
 
988
            self.add_cleanup(branch_to.lock_write().unlock)
998
989
 
999
990
        if local and not branch_to.get_bound_location():
1000
991
            raise errors.LocalRequiresBoundBranch()
1031
1022
        else:
1032
1023
            branch_from = Branch.open(location,
1033
1024
                possible_transports=possible_transports)
1034
 
            branch_from.lock_read()
1035
 
            self.add_cleanup(branch_from.unlock)
 
1025
            self.add_cleanup(branch_from.lock_read().unlock)
1036
1026
 
1037
1027
            if branch_to.get_parent() is None or remember:
1038
1028
                branch_to.set_parent(branch_from.base)
1218
1208
        accelerator_tree, br_from = bzrdir.BzrDir.open_tree_or_branch(
1219
1209
            from_location)
1220
1210
        revision = _get_one_revision('branch', revision)
1221
 
        br_from.lock_read()
1222
 
        self.add_cleanup(br_from.unlock)
 
1211
        self.add_cleanup(br_from.lock_read().unlock)
1223
1212
        if revision is not None:
1224
1213
            revision_id = revision.as_revision_id(br_from)
1225
1214
        else:
1349
1338
            except errors.NoWorkingTree:
1350
1339
                source.bzrdir.create_workingtree(revision_id)
1351
1340
                return
1352
 
 
1353
 
        if not lightweight:
1354
 
            message = ('Copying history to "%s". '
1355
 
                'To checkout without local history use --lightweight.' % to_location)
1356
 
            ui.ui_factory.show_message(message)
1357
1341
        source.create_checkout(to_location, revision_id, lightweight,
1358
1342
                               accelerator_tree, hardlink)
1359
1343
 
1370
1354
    @display_command
1371
1355
    def run(self, dir=u'.'):
1372
1356
        tree = WorkingTree.open_containing(dir)[0]
1373
 
        tree.lock_read()
1374
 
        self.add_cleanup(tree.unlock)
 
1357
        self.add_cleanup(tree.lock_read().unlock)
1375
1358
        new_inv = tree.inventory
1376
1359
        old_tree = tree.basis_tree()
1377
 
        old_tree.lock_read()
1378
 
        self.add_cleanup(old_tree.unlock)
 
1360
        self.add_cleanup(old_tree.lock_read().unlock)
1379
1361
        old_inv = old_tree.inventory
1380
1362
        renames = []
1381
1363
        iterator = tree.iter_changes(old_tree, include_unchanged=True)
1419
1401
        master = branch.get_master_branch(
1420
1402
            possible_transports=possible_transports)
1421
1403
        if master is not None:
1422
 
            tree.lock_write()
1423
1404
            branch_location = master.base
 
1405
            tree.lock_write()
1424
1406
        else:
 
1407
            branch_location = tree.branch.base
1425
1408
            tree.lock_tree_write()
1426
 
            branch_location = tree.branch.base
1427
1409
        self.add_cleanup(tree.unlock)
1428
1410
        # get rid of the final '/' and be ready for display
1429
1411
        branch_location = urlutils.unescape_for_display(
1549
1531
        if file_list is not None:
1550
1532
            file_list = [f for f in file_list]
1551
1533
 
1552
 
        tree.lock_write()
1553
 
        self.add_cleanup(tree.unlock)
 
1534
        self.add_cleanup(tree.lock_write().unlock)
1554
1535
        # Heuristics should probably all move into tree.remove_smart or
1555
1536
        # some such?
1556
1537
        if new:
1989
1970
         old_branch, new_branch,
1990
1971
         specific_files, extra_trees) = get_trees_and_branches_to_diff_locked(
1991
1972
            file_list, revision, old, new, self.add_cleanup, apply_view=True)
 
1973
        # GNU diff on Windows uses ANSI encoding for filenames
 
1974
        path_encoding = osutils.get_diff_header_encoding()
1992
1975
        return show_diff_trees(old_tree, new_tree, sys.stdout,
1993
1976
                               specific_files=specific_files,
1994
1977
                               external_diff_options=diff_options,
1995
1978
                               old_label=old_label, new_label=new_label,
1996
 
                               extra_trees=extra_trees, using=using,
 
1979
                               extra_trees=extra_trees,
 
1980
                               path_encoding=path_encoding,
 
1981
                               using=using,
1997
1982
                               format_cls=format)
1998
1983
 
1999
1984
 
2012
1997
    @display_command
2013
1998
    def run(self, show_ids=False, directory=u'.'):
2014
1999
        tree = WorkingTree.open_containing(directory)[0]
2015
 
        tree.lock_read()
2016
 
        self.add_cleanup(tree.unlock)
 
2000
        self.add_cleanup(tree.lock_read().unlock)
2017
2001
        old = tree.basis_tree()
2018
 
        old.lock_read()
2019
 
        self.add_cleanup(old.unlock)
 
2002
        self.add_cleanup(old.lock_read().unlock)
2020
2003
        for path, ie in old.inventory.iter_entries():
2021
2004
            if not tree.has_id(ie.file_id):
2022
2005
                self.outf.write(path)
2056
2039
    @display_command
2057
2040
    def run(self, null=False, directory=u'.'):
2058
2041
        wt = WorkingTree.open_containing(directory)[0]
2059
 
        wt.lock_read()
2060
 
        self.add_cleanup(wt.unlock)
 
2042
        self.add_cleanup(wt.lock_read().unlock)
2061
2043
        basis = wt.basis_tree()
2062
 
        basis.lock_read()
2063
 
        self.add_cleanup(basis.unlock)
 
2044
        self.add_cleanup(basis.lock_read().unlock)
2064
2045
        basis_inv = basis.inventory
2065
2046
        inv = wt.inventory
2066
2047
        for file_id in inv:
2354
2335
        if file_list:
2355
2336
            # find the file ids to log and check for directory filtering
2356
2337
            b, file_info_list, rev1, rev2 = _get_info_for_log_files(
2357
 
                revision, file_list)
2358
 
            self.add_cleanup(b.unlock)
 
2338
                revision, file_list, self.add_cleanup)
2359
2339
            for relpath, file_id, kind in file_info_list:
2360
2340
                if file_id is None:
2361
2341
                    raise errors.BzrCommandError(
2379
2359
                location = '.'
2380
2360
            dir, relpath = bzrdir.BzrDir.open_containing(location)
2381
2361
            b = dir.open_branch()
2382
 
            b.lock_read()
2383
 
            self.add_cleanup(b.unlock)
 
2362
            self.add_cleanup(b.lock_read().unlock)
2384
2363
            rev1, rev2 = _get_revision_range(revision, b, self.name())
2385
2364
 
2386
2365
        # Decide on the type of delta & diff filtering to use
2511
2490
        tree, relpath = WorkingTree.open_containing(filename)
2512
2491
        file_id = tree.path2id(relpath)
2513
2492
        b = tree.branch
2514
 
        b.lock_read()
2515
 
        self.add_cleanup(b.unlock)
 
2493
        self.add_cleanup(b.lock_read().unlock)
2516
2494
        touching_revs = log.find_touching_revisions(b, file_id)
2517
2495
        for revno, revision_id, what in touching_revs:
2518
2496
            self.outf.write("%6d %s\n" % (revno, what))
2588
2566
                view_str = views.view_display_str(view_files)
2589
2567
                note("Ignoring files outside view. View is %s" % view_str)
2590
2568
 
2591
 
        tree.lock_read()
2592
 
        self.add_cleanup(tree.unlock)
 
2569
        self.add_cleanup(tree.lock_read().unlock)
2593
2570
        for fp, fc, fkind, fid, entry in tree.list_files(include_root=False,
2594
2571
            from_dir=relpath, recursive=recursive):
2595
2572
            # Apply additional masking
2777
2754
    @display_command
2778
2755
    def run(self, directory=u'.'):
2779
2756
        tree = WorkingTree.open_containing(directory)[0]
2780
 
        tree.lock_read()
2781
 
        self.add_cleanup(tree.unlock)
 
2757
        self.add_cleanup(tree.lock_read().unlock)
2782
2758
        for path, file_class, kind, file_id, entry in tree.list_files():
2783
2759
            if file_class != 'I':
2784
2760
                continue
2898
2874
                                         " one revision specifier")
2899
2875
        tree, branch, relpath = \
2900
2876
            _open_directory_or_containing_tree_or_branch(filename, directory)
2901
 
        branch.lock_read()
2902
 
        self.add_cleanup(branch.unlock)
 
2877
        self.add_cleanup(branch.lock_read().unlock)
2903
2878
        return self._run(tree, branch, relpath, filename, revision,
2904
2879
                         name_from_revision, filters)
2905
2880
 
2908
2883
        if tree is None:
2909
2884
            tree = b.basis_tree()
2910
2885
        rev_tree = _get_one_revision_tree('cat', revision, branch=b)
2911
 
        rev_tree.lock_read()
2912
 
        self.add_cleanup(rev_tree.unlock)
 
2886
        self.add_cleanup(rev_tree.lock_read().unlock)
2913
2887
 
2914
2888
        old_file_id = rev_tree.path2id(relpath)
2915
2889
 
3177
3151
        def get_message(commit_obj):
3178
3152
            """Callback to get commit message"""
3179
3153
            if file:
3180
 
                my_message = codecs.open(
3181
 
                    file, 'rt', osutils.get_user_encoding()).read()
 
3154
                f = codecs.open(file, 'rt', osutils.get_user_encoding())
 
3155
                try:
 
3156
                    my_message = f.read()
 
3157
                finally:
 
3158
                    f.close()
3182
3159
            elif message is not None:
3183
3160
                my_message = message
3184
3161
            else:
3338
3315
 
3339
3316
            bzr whoami "Frank Chu <fchu@example.com>"
3340
3317
    """
3341
 
    takes_options = [ Option('email',
 
3318
    takes_options = [ 'directory',
 
3319
                      Option('email',
3342
3320
                             help='Display email address only.'),
3343
3321
                      Option('branch',
3344
3322
                             help='Set identity for the current branch instead of '
3348
3326
    encoding_type = 'replace'
3349
3327
 
3350
3328
    @display_command
3351
 
    def run(self, email=False, branch=False, name=None):
 
3329
    def run(self, email=False, branch=False, name=None, directory=None):
3352
3330
        if name is None:
3353
 
            # use branch if we're inside one; otherwise global config
3354
 
            try:
3355
 
                c = Branch.open_containing('.')[0].get_config()
3356
 
            except errors.NotBranchError:
3357
 
                c = config.GlobalConfig()
 
3331
            if directory is None:
 
3332
                # use branch if we're inside one; otherwise global config
 
3333
                try:
 
3334
                    c = Branch.open_containing(u'.')[0].get_config()
 
3335
                except errors.NotBranchError:
 
3336
                    c = config.GlobalConfig()
 
3337
            else:
 
3338
                c = Branch.open(directory).get_config()
3358
3339
            if email:
3359
3340
                self.outf.write(c.user_email() + '\n')
3360
3341
            else:
3370
3351
 
3371
3352
        # use global config unless --branch given
3372
3353
        if branch:
3373
 
            c = Branch.open_containing('.')[0].get_config()
 
3354
            if directory is None:
 
3355
                c = Branch.open_containing(u'.')[0].get_config()
 
3356
            else:
 
3357
                c = Branch.open(directory).get_config()
3374
3358
        else:
3375
3359
            c = config.GlobalConfig()
3376
3360
        c.set_user_option('email', name)
3621
3605
            self.additional_selftest_args['runner_class'] = SubUnitBzrRunner
3622
3606
            # On Windows, disable automatic conversion of '\n' to '\r\n' in
3623
3607
            # stdout, which would corrupt the subunit stream. 
3624
 
            if sys.platform == "win32" and sys.stdout.fileno() >= 0:
 
3608
            # FIXME: This has been fixed in subunit trunk (>0.0.5) so the
 
3609
            # following code can be deleted when it's sufficiently deployed
 
3610
            # -- vila/mgz 20100514
 
3611
            if (sys.platform == "win32"
 
3612
                and getattr(sys.stdout, 'fileno', None) is not None):
3625
3613
                import msvcrt
3626
3614
                msvcrt.setmode(sys.stdout.fileno(), os.O_BINARY)
3627
3615
        if parallel:
3699
3687
 
3700
3688
        branch1 = Branch.open_containing(branch)[0]
3701
3689
        branch2 = Branch.open_containing(other)[0]
3702
 
        branch1.lock_read()
3703
 
        self.add_cleanup(branch1.unlock)
3704
 
        branch2.lock_read()
3705
 
        self.add_cleanup(branch2.unlock)
 
3690
        self.add_cleanup(branch1.lock_read().unlock)
 
3691
        self.add_cleanup(branch2.lock_read().unlock)
3706
3692
        last1 = ensure_null(branch1.last_revision())
3707
3693
        last2 = ensure_null(branch2.last_revision())
3708
3694
 
3843
3829
            unversioned_filter=tree.is_ignored, view_info=view_info)
3844
3830
        pb = ui.ui_factory.nested_progress_bar()
3845
3831
        self.add_cleanup(pb.finished)
3846
 
        tree.lock_write()
3847
 
        self.add_cleanup(tree.unlock)
 
3832
        self.add_cleanup(tree.lock_write().unlock)
3848
3833
        if location is not None:
3849
3834
            try:
3850
3835
                mergeable = bundle.read_mergeable_from_url(location,
3911
3896
    def _do_preview(self, merger):
3912
3897
        from bzrlib.diff import show_diff_trees
3913
3898
        result_tree = self._get_preview(merger)
 
3899
        path_encoding = osutils.get_diff_header_encoding()
3914
3900
        show_diff_trees(merger.this_tree, result_tree, self.outf,
3915
 
                        old_label='', new_label='')
 
3901
                        old_label='', new_label='',
 
3902
                        path_encoding=path_encoding)
3916
3903
 
3917
3904
    def _do_merge(self, merger, change_reporter, allow_pending, verified):
3918
3905
        merger.change_reporter = change_reporter
4106
4093
        if merge_type is None:
4107
4094
            merge_type = _mod_merge.Merge3Merger
4108
4095
        tree, file_list = tree_files(file_list)
4109
 
        tree.lock_write()
4110
 
        self.add_cleanup(tree.unlock)
 
4096
        self.add_cleanup(tree.lock_write().unlock)
4111
4097
        parents = tree.get_parent_ids()
4112
4098
        if len(parents) != 2:
4113
4099
            raise errors.BzrCommandError("Sorry, remerge only works after normal"
4223
4209
    def run(self, revision=None, no_backup=False, file_list=None,
4224
4210
            forget_merges=None):
4225
4211
        tree, file_list = tree_files(file_list)
4226
 
        tree.lock_tree_write()
4227
 
        self.add_cleanup(tree.unlock)
 
4212
        self.add_cleanup(tree.lock_tree_write().unlock)
4228
4213
        if forget_merges:
4229
4214
            tree.set_parent_ids(tree.get_parent_ids()[:1])
4230
4215
        else:
4319
4304
    _see_also = ['merge', 'pull']
4320
4305
    takes_args = ['other_branch?']
4321
4306
    takes_options = [
 
4307
        'directory',
4322
4308
        Option('reverse', 'Reverse the order of revisions.'),
4323
4309
        Option('mine-only',
4324
4310
               'Display changes in the local branch only.'),
4346
4332
            theirs_only=False,
4347
4333
            log_format=None, long=False, short=False, line=False,
4348
4334
            show_ids=False, verbose=False, this=False, other=False,
4349
 
            include_merges=False, revision=None, my_revision=None):
 
4335
            include_merges=False, revision=None, my_revision=None,
 
4336
            directory=u'.'):
4350
4337
        from bzrlib.missing import find_unmerged, iter_log_revisions
4351
4338
        def message(s):
4352
4339
            if not is_quiet():
4365
4352
        elif theirs_only:
4366
4353
            restrict = 'remote'
4367
4354
 
4368
 
        local_branch = Branch.open_containing(u".")[0]
4369
 
        local_branch.lock_read()
4370
 
        self.add_cleanup(local_branch.unlock)
 
4355
        local_branch = Branch.open_containing(directory)[0]
 
4356
        self.add_cleanup(local_branch.lock_read().unlock)
4371
4357
 
4372
4358
        parent = local_branch.get_parent()
4373
4359
        if other_branch is None:
4384
4370
        if remote_branch.base == local_branch.base:
4385
4371
            remote_branch = local_branch
4386
4372
        else:
4387
 
            remote_branch.lock_read()
4388
 
            self.add_cleanup(remote_branch.unlock)
 
4373
            self.add_cleanup(remote_branch.lock_read().unlock)
4389
4374
 
4390
4375
        local_revid_range = _revision_range_to_revid_range(
4391
4376
            _get_revision_range(my_revision, local_branch,
4446
4431
            message("Branches are up to date.\n")
4447
4432
        self.cleanup_now()
4448
4433
        if not status_code and parent is None and other_branch is not None:
4449
 
            local_branch.lock_write()
4450
 
            self.add_cleanup(local_branch.unlock)
 
4434
            self.add_cleanup(local_branch.lock_write().unlock)
4451
4435
            # handle race conditions - a parent might be set while we run.
4452
4436
            if local_branch.get_parent() is None:
4453
4437
                local_branch.set_parent(remote_branch.base)
4553
4537
            b = Branch.open_containing(branch)[0]
4554
4538
        else:
4555
4539
            b = Branch.open(branch)
4556
 
        b.lock_read()
4557
 
        self.add_cleanup(b.unlock)
 
4540
        self.add_cleanup(b.lock_read().unlock)
4558
4541
        if revision is None:
4559
4542
            rev_id = b.last_revision()
4560
4543
        else:
4595
4578
        wt, branch, relpath = \
4596
4579
            _open_directory_or_containing_tree_or_branch(filename, directory)
4597
4580
        if wt is not None:
4598
 
            wt.lock_read()
4599
 
            self.add_cleanup(wt.unlock)
 
4581
            self.add_cleanup(wt.lock_read().unlock)
4600
4582
        else:
4601
 
            branch.lock_read()
4602
 
            self.add_cleanup(branch.unlock)
 
4583
            self.add_cleanup(branch.lock_read().unlock)
4603
4584
        tree = _get_one_revision_tree('annotate', revision, branch=branch)
4604
 
        tree.lock_read()
4605
 
        self.add_cleanup(tree.unlock)
 
4585
        self.add_cleanup(tree.lock_read().unlock)
4606
4586
        if wt is not None:
4607
4587
            file_id = wt.path2id(relpath)
4608
4588
        else:
4634
4614
        if revision_id_list is None and revision is None:
4635
4615
            raise errors.BzrCommandError('You must supply either --revision or a revision_id')
4636
4616
        b = WorkingTree.open_containing(directory)[0].branch
4637
 
        b.lock_write()
4638
 
        self.add_cleanup(b.unlock)
 
4617
        self.add_cleanup(b.lock_write().unlock)
4639
4618
        return self._run(b, revision_id_list, revision)
4640
4619
 
4641
4620
    def _run(self, b, revision_id_list, revision):
4791
4770
            b = control.open_branch()
4792
4771
 
4793
4772
        if tree is not None:
4794
 
            tree.lock_write()
4795
 
            self.add_cleanup(tree.unlock)
 
4773
            self.add_cleanup(tree.lock_write().unlock)
4796
4774
        else:
4797
 
            b.lock_write()
4798
 
            self.add_cleanup(b.unlock)
 
4775
            self.add_cleanup(b.lock_write().unlock)
4799
4776
        return self._run(b, tree, dry_run, verbose, revision, force, local=local)
4800
4777
 
4801
4778
    def _run(self, b, tree, dry_run, verbose, revision, force, local=False):
5052
5029
    _see_also = ['send']
5053
5030
 
5054
5031
    takes_options = [
 
5032
        'directory',
5055
5033
        RegistryOption.from_kwargs('patch-type',
5056
5034
            'The type of patch to include in the directive.',
5057
5035
            title='Patch type',
5070
5048
    encoding_type = 'exact'
5071
5049
 
5072
5050
    def run(self, submit_branch=None, public_branch=None, patch_type='bundle',
5073
 
            sign=False, revision=None, mail_to=None, message=None):
 
5051
            sign=False, revision=None, mail_to=None, message=None,
 
5052
            directory=u'.'):
5074
5053
        from bzrlib.revision import ensure_null, NULL_REVISION
5075
5054
        include_patch, include_bundle = {
5076
5055
            'plain': (False, False),
5077
5056
            'diff': (True, False),
5078
5057
            'bundle': (True, True),
5079
5058
            }[patch_type]
5080
 
        branch = Branch.open('.')
 
5059
        branch = Branch.open(directory)
5081
5060
        stored_submit_branch = branch.get_submit_branch()
5082
5061
        if submit_branch is None:
5083
5062
            submit_branch = stored_submit_branch
5168
5147
    given, in which case it is sent to a file.
5169
5148
 
5170
5149
    Mail is sent using your preferred mail program.  This should be transparent
5171
 
    on Windows (it uses MAPI).  On Linux, it requires the xdg-email utility.
 
5150
    on Windows (it uses MAPI).  On Unix, it requires the xdg-email utility.
5172
5151
    If the preferred client can't be found (or used), your editor will be used.
5173
5152
 
5174
5153
    To use a specific mail program, set the mail_client configuration option.
5360
5339
            revision=None,
5361
5340
            ):
5362
5341
        branch, relpath = Branch.open_containing(directory)
5363
 
        branch.lock_write()
5364
 
        self.add_cleanup(branch.unlock)
 
5342
        self.add_cleanup(branch.lock_write().unlock)
5365
5343
        if delete:
5366
5344
            if tag_name is None:
5367
5345
                raise errors.BzrCommandError("No tag specified to delete.")
5419
5397
        if not tags:
5420
5398
            return
5421
5399
 
5422
 
        branch.lock_read()
5423
 
        self.add_cleanup(branch.unlock)
 
5400
        self.add_cleanup(branch.lock_read().unlock)
5424
5401
        if revision:
5425
5402
            graph = branch.repository.get_graph()
5426
5403
            rev1, rev2 = _get_revision_range(revision, branch, self.name())
5573
5550
    """
5574
5551
 
5575
5552
    takes_args = ['to_location?']
5576
 
    takes_options = [Option('force',
 
5553
    takes_options = ['directory',
 
5554
                     Option('force',
5577
5555
                        help='Switch even if local commits will be lost.'),
5578
5556
                     'revision',
5579
5557
                     Option('create-branch', short_name='b',
5582
5560
                    ]
5583
5561
 
5584
5562
    def run(self, to_location=None, force=False, create_branch=False,
5585
 
            revision=None):
 
5563
            revision=None, directory=u'.'):
5586
5564
        from bzrlib import switch
5587
 
        tree_location = '.'
 
5565
        tree_location = directory
5588
5566
        revision = _get_one_revision('switch', revision)
5589
5567
        control_dir = bzrdir.BzrDir.open_containing(tree_location)[0]
5590
5568
        if to_location is None:
5591
5569
            if revision is None:
5592
5570
                raise errors.BzrCommandError('You must supply either a'
5593
5571
                                             ' revision or a location')
5594
 
            to_location = '.'
 
5572
            to_location = tree_location
5595
5573
        try:
5596
5574
            branch = control_dir.open_branch()
5597
5575
            had_explicit_nick = branch.get_config().has_explicit_nickname()
5872
5850
    takes_args = ['file*']
5873
5851
 
5874
5852
    takes_options = [
 
5853
        'directory',
5875
5854
        'revision',
5876
5855
        Option('all', help='Shelve all changes.'),
5877
5856
        'message',
5886
5865
    _see_also = ['unshelve']
5887
5866
 
5888
5867
    def run(self, revision=None, all=False, file_list=None, message=None,
5889
 
            writer=None, list=False, destroy=False):
 
5868
            writer=None, list=False, destroy=False, directory=u'.'):
5890
5869
        if list:
5891
5870
            return self.run_for_list()
5892
5871
        from bzrlib.shelf_ui import Shelver
5894
5873
            writer = bzrlib.option.diff_writer_registry.get()
5895
5874
        try:
5896
5875
            shelver = Shelver.from_args(writer(sys.stdout), revision, all,
5897
 
                file_list, message, destroy=destroy)
 
5876
                file_list, message, destroy=destroy, directory=directory)
5898
5877
            try:
5899
5878
                shelver.run()
5900
5879
            finally:
5904
5883
 
5905
5884
    def run_for_list(self):
5906
5885
        tree = WorkingTree.open_containing('.')[0]
5907
 
        tree.lock_read()
5908
 
        self.add_cleanup(tree.unlock)
 
5886
        self.add_cleanup(tree.lock_read().unlock)
5909
5887
        manager = tree.get_shelf_manager()
5910
5888
        shelves = manager.active_shelves()
5911
5889
        if len(shelves) == 0:
5929
5907
 
5930
5908
    takes_args = ['shelf_id?']
5931
5909
    takes_options = [
 
5910
        'directory',
5932
5911
        RegistryOption.from_kwargs(
5933
5912
            'action', help="The action to perform.",
5934
5913
            enum_switch=False, value_switches=True,
5942
5921
    ]
5943
5922
    _see_also = ['shelve']
5944
5923
 
5945
 
    def run(self, shelf_id=None, action='apply'):
 
5924
    def run(self, shelf_id=None, action='apply', directory=u'.'):
5946
5925
        from bzrlib.shelf_ui import Unshelver
5947
 
        unshelver = Unshelver.from_args(shelf_id, action)
 
5926
        unshelver = Unshelver.from_args(shelf_id, action, directory=directory)
5948
5927
        try:
5949
5928
            unshelver.run()
5950
5929
        finally: