75
75
from bzrlib.trace import mutter, note, warning, is_quiet, get_verbosity_level
78
@symbol_versioning.deprecated_function(symbol_versioning.deprecated_in((2, 3, 0)))
78
79
def tree_files(file_list, default_branch=u'.', canonicalize=True,
81
return internal_tree_files(file_list, default_branch, canonicalize,
83
except errors.FileInWrongBranch, e:
84
raise errors.BzrCommandError("%s is not in the same branch as %s" %
85
(e.path, file_list[0]))
81
return internal_tree_files(file_list, default_branch, canonicalize,
88
85
def tree_files_for_add(file_list):
153
150
# XXX: Bad function name; should possibly also be a class method of
154
151
# WorkingTree rather than a function.
152
@symbol_versioning.deprecated_function(symbol_versioning.deprecated_in((2, 3, 0)))
155
153
def internal_tree_files(file_list, default_branch=u'.', canonicalize=True,
156
154
apply_view=True):
157
155
"""Convert command-line paths to a WorkingTree and relative paths.
157
Deprecated: use WorkingTree.open_containing_paths instead.
159
159
This is typically used for command-line processors that take one or
160
160
more filenames, and infer the workingtree that contains them.
172
172
:return: workingtree, [relative_paths]
174
if file_list is None or len(file_list) == 0:
175
tree = WorkingTree.open_containing(default_branch)[0]
176
if tree.supports_views() and apply_view:
177
view_files = tree.views.lookup_view()
179
file_list = view_files
180
view_str = views.view_display_str(view_files)
181
note("Ignoring files outside view. View is %s" % view_str)
182
return tree, file_list
183
tree = WorkingTree.open_containing(osutils.realpath(file_list[0]))[0]
184
return tree, safe_relpath_files(tree, file_list, canonicalize,
185
apply_view=apply_view)
188
def safe_relpath_files(tree, file_list, canonicalize=True, apply_view=True):
189
"""Convert file_list into a list of relpaths in tree.
191
:param tree: A tree to operate on.
192
:param file_list: A list of user provided paths or None.
193
:param apply_view: if True and a view is set, apply it or check that
194
specified files are within it
195
:return: A list of relative paths.
196
:raises errors.PathNotChild: When a provided path is in a different tree
199
if file_list is None:
201
if tree.supports_views() and apply_view:
202
view_files = tree.views.lookup_view()
206
# tree.relpath exists as a "thunk" to osutils, but canonical_relpath
207
# doesn't - fix that up here before we enter the loop.
209
fixer = lambda p: osutils.canonical_relpath(tree.basedir, p)
212
for filename in file_list:
214
relpath = fixer(osutils.dereference_path(filename))
215
if view_files and not osutils.is_inside_any(view_files, relpath):
216
raise errors.FileOutsideView(filename, view_files)
217
new_list.append(relpath)
218
except errors.PathNotChild:
219
raise errors.FileInWrongBranch(tree.branch, filename)
174
return WorkingTree.open_containing_paths(
175
file_list, default_directory='.',
223
180
def _get_view_info_for_change_reporter(tree):
192
def _open_directory_or_containing_tree_or_branch(filename, directory):
193
"""Open the tree or branch containing the specified file, unless
194
the --directory option is used to specify a different branch."""
195
if directory is not None:
196
return (None, Branch.open(directory), filename)
197
return bzrdir.BzrDir.open_containing_tree_or_branch(filename)
235
200
# TODO: Make sure no commands unconditionally use the working directory as a
236
201
# branch. If a filename argument is used, the first of them should be used to
237
202
# specify the branch. (Perhaps this can be factored out into some kind of
315
280
raise errors.BzrCommandError('bzr status --revision takes exactly'
316
281
' one or two revision specifiers')
318
tree, relfile_list = tree_files(file_list)
283
tree, relfile_list = WorkingTree.open_containing_paths(file_list)
319
284
# Avoid asking for specific files when that is not needed.
320
285
if relfile_list == ['']:
321
286
relfile_list = None
353
318
self.outf.write(revtext.decode('utf-8'))
356
def run(self, revision_id=None, revision=None):
321
def run(self, revision_id=None, revision=None, directory=u'.'):
357
322
if revision_id is not None and revision is not None:
358
323
raise errors.BzrCommandError('You can only supply one of'
359
324
' revision_id or --revision')
360
325
if revision_id is None and revision is None:
361
326
raise errors.BzrCommandError('You must supply either'
362
327
' --revision or a revision_id')
363
b = WorkingTree.open_containing(u'.')[0].branch
328
b = WorkingTree.open_containing(directory)[0].branch
365
330
revisions = b.repository.revisions
366
331
if revisions is None:
504
469
if (working.has_changes()):
505
470
raise errors.UncommittedChanges(working)
471
if working.get_shelf_manager().last_shelf() is not None:
472
raise errors.ShelvedChanges(working)
507
474
if working.user_url != working.branch.user_url:
508
475
raise errors.BzrCommandError("You cannot remove the working tree"
530
497
wt = WorkingTree.open_containing(location)[0]
498
self.add_cleanup(wt.lock_read().unlock)
532
499
except (errors.NoWorkingTree, errors.NotLocalUrl):
533
500
raise errors.NoWorkingTree(location)
534
self.add_cleanup(wt.unlock)
535
501
revid = wt.last_revision()
537
503
revno_t = wt.branch.revision_id_to_dotted_revno(revid)
540
506
revno = ".".join(str(n) for n in revno_t)
542
508
b = Branch.open_containing(location)[0]
544
self.add_cleanup(b.unlock)
509
self.add_cleanup(b.lock_read().unlock)
545
510
revno = b.revno()
546
511
self.cleanup_now()
547
512
self.outf.write(str(revno) + '\n')
554
519
takes_args = ['revision_info*']
555
520
takes_options = [
522
custom_help('directory',
558
523
help='Branch to examine, '
559
'rather than the one containing the working directory.',
524
'rather than the one containing the working directory.'),
563
525
Option('tree', help='Show revno of working tree'),
571
533
wt = WorkingTree.open_containing(directory)[0]
574
self.add_cleanup(wt.unlock)
535
self.add_cleanup(wt.lock_read().unlock)
575
536
except (errors.NoWorkingTree, errors.NotLocalUrl):
577
538
b = Branch.open_containing(directory)[0]
579
self.add_cleanup(b.unlock)
539
self.add_cleanup(b.lock_read().unlock)
580
540
revision_ids = []
581
541
if revision is not None:
582
542
revision_ids.extend(rev.as_revision_id(b) for rev in revision)
681
641
should_print=(not is_quiet()))
684
base_tree.lock_read()
685
self.add_cleanup(base_tree.unlock)
644
self.add_cleanup(base_tree.lock_read().unlock)
686
645
tree, file_list = tree_files_for_add(file_list)
687
646
added, ignored = tree.smart_add(file_list, not
688
647
no_recurse, action=action, save=not dry_run)
759
718
raise errors.BzrCommandError('invalid kind %r specified' % (kind,))
761
720
revision = _get_one_revision('inventory', revision)
762
work_tree, file_list = tree_files(file_list)
763
work_tree.lock_read()
764
self.add_cleanup(work_tree.unlock)
721
work_tree, file_list = WorkingTree.open_containing_paths(file_list)
722
self.add_cleanup(work_tree.lock_read().unlock)
765
723
if revision is not None:
766
724
tree = revision.as_tree(work_tree.branch)
768
726
extra_trees = [work_tree]
770
self.add_cleanup(tree.unlock)
727
self.add_cleanup(tree.lock_read().unlock)
833
790
if len(names_list) < 2:
834
791
raise errors.BzrCommandError("missing file argument")
835
tree, rel_names = tree_files(names_list, canonicalize=False)
836
tree.lock_tree_write()
837
self.add_cleanup(tree.unlock)
792
tree, rel_names = WorkingTree.open_containing_paths(names_list, canonicalize=False)
793
self.add_cleanup(tree.lock_tree_write().unlock)
838
794
self._run(tree, names_list, rel_names, after)
840
796
def run_auto(self, names_list, after, dry_run):
845
801
raise errors.BzrCommandError('--after cannot be specified with'
847
work_tree, file_list = tree_files(names_list, default_branch='.')
848
work_tree.lock_tree_write()
849
self.add_cleanup(work_tree.unlock)
803
work_tree, file_list = WorkingTree.open_containing_paths(
804
names_list, default_directory='.')
805
self.add_cleanup(work_tree.lock_tree_write().unlock)
850
806
rename_map.RenameMap.guess_renames(work_tree, dry_run)
852
808
def _run(self, tree, names_list, rel_names, after):
960
916
takes_options = ['remember', 'overwrite', 'revision',
961
917
custom_help('verbose',
962
918
help='Show logs of pulled revisions.'),
919
custom_help('directory',
964
920
help='Branch to pull into, '
965
'rather than the one containing the working directory.',
921
'rather than the one containing the working directory.'),
970
923
help="Perform a local pull in a bound "
971
924
"branch. Local pulls are not applied to "
987
940
tree_to = WorkingTree.open_containing(directory)[0]
988
941
branch_to = tree_to.branch
990
self.add_cleanup(tree_to.unlock)
942
self.add_cleanup(tree_to.lock_write().unlock)
991
943
except errors.NoWorkingTree:
993
945
branch_to = Branch.open_containing(directory)[0]
994
branch_to.lock_write()
995
self.add_cleanup(branch_to.unlock)
946
self.add_cleanup(branch_to.lock_write().unlock)
997
948
if local and not branch_to.get_bound_location():
998
949
raise errors.LocalRequiresBoundBranch()
1030
981
branch_from = Branch.open(location,
1031
982
possible_transports=possible_transports)
1032
branch_from.lock_read()
1033
self.add_cleanup(branch_from.unlock)
983
self.add_cleanup(branch_from.lock_read().unlock)
1035
985
if branch_to.get_parent() is None or remember:
1036
986
branch_to.set_parent(branch_from.base)
1088
1038
Option('create-prefix',
1089
1039
help='Create the path leading up to the branch '
1090
1040
'if it does not already exist.'),
1041
custom_help('directory',
1092
1042
help='Branch to push from, '
1093
'rather than the one containing the working directory.',
1043
'rather than the one containing the working directory.'),
1097
1044
Option('use-existing-dir',
1098
1045
help='By default push will fail if the target'
1099
1046
' directory exists, but does not already'
1189
1136
_see_also = ['checkout']
1190
1137
takes_args = ['from_location', 'to_location?']
1191
takes_options = ['revision', Option('hardlink',
1192
help='Hard-link working tree files where possible.'),
1138
takes_options = ['revision',
1139
Option('hardlink', help='Hard-link working tree files where possible.'),
1140
Option('files-from', type=str,
1141
help="Get file contents from this tree."),
1193
1142
Option('no-tree',
1194
1143
help="Create a branch without a working-tree."),
1195
1144
Option('switch',
1214
1163
def run(self, from_location, to_location=None, revision=None,
1215
1164
hardlink=False, stacked=False, standalone=False, no_tree=False,
1216
use_existing_dir=False, switch=False, bind=False):
1165
use_existing_dir=False, switch=False, bind=False,
1217
1167
from bzrlib import switch as _mod_switch
1218
1168
from bzrlib.tag import _merge_tags_if_possible
1219
1169
accelerator_tree, br_from = bzrdir.BzrDir.open_tree_or_branch(
1171
if not (hardlink or files_from):
1172
# accelerator_tree is usually slower because you have to read N
1173
# files (no readahead, lots of seeks, etc), but allow the user to
1174
# explicitly request it
1175
accelerator_tree = None
1176
if files_from is not None and files_from != from_location:
1177
accelerator_tree = WorkingTree.open(files_from)
1221
1178
revision = _get_one_revision('branch', revision)
1223
self.add_cleanup(br_from.unlock)
1179
self.add_cleanup(br_from.lock_read().unlock)
1224
1180
if revision is not None:
1225
1181
revision_id = revision.as_revision_id(br_from)
1331
1287
to_location = branch_location
1332
1288
accelerator_tree, source = bzrdir.BzrDir.open_tree_or_branch(
1333
1289
branch_location)
1290
if not (hardlink or files_from):
1291
# accelerator_tree is usually slower because you have to read N
1292
# files (no readahead, lots of seeks, etc), but allow the user to
1293
# explicitly request it
1294
accelerator_tree = None
1334
1295
revision = _get_one_revision('checkout', revision)
1335
if files_from is not None:
1296
if files_from is not None and files_from != branch_location:
1336
1297
accelerator_tree = WorkingTree.open(files_from)
1337
1298
if revision is not None:
1338
1299
revision_id = revision.as_revision_id(source)
1366
1327
@display_command
1367
1328
def run(self, dir=u'.'):
1368
1329
tree = WorkingTree.open_containing(dir)[0]
1370
self.add_cleanup(tree.unlock)
1330
self.add_cleanup(tree.lock_read().unlock)
1371
1331
new_inv = tree.inventory
1372
1332
old_tree = tree.basis_tree()
1373
old_tree.lock_read()
1374
self.add_cleanup(old_tree.unlock)
1333
self.add_cleanup(old_tree.lock_read().unlock)
1375
1334
old_inv = old_tree.inventory
1377
1336
iterator = tree.iter_changes(old_tree, include_unchanged=True)
1415
1374
master = branch.get_master_branch(
1416
1375
possible_transports=possible_transports)
1417
1376
if master is not None:
1419
1377
branch_location = master.base
1380
branch_location = tree.branch.base
1421
1381
tree.lock_tree_write()
1422
branch_location = tree.branch.base
1423
1382
self.add_cleanup(tree.unlock)
1424
1383
# get rid of the final '/' and be ready for display
1425
1384
branch_location = urlutils.unescape_for_display(
1519
1478
class cmd_remove(Command):
1520
1479
__doc__ = """Remove files or directories.
1522
This makes bzr stop tracking changes to the specified files. bzr will delete
1523
them if they can easily be recovered using revert. If no options or
1524
parameters are given bzr will scan for files that are being tracked by bzr
1525
but missing in your tree and stop tracking them for you.
1481
This makes Bazaar stop tracking changes to the specified files. Bazaar will
1482
delete them if they can easily be recovered using revert otherwise they
1483
will be backed up (adding an extention of the form .~#~). If no options or
1484
parameters are given Bazaar will scan for files that are being tracked by
1485
Bazaar but missing in your tree and stop tracking them for you.
1527
1487
takes_args = ['file*']
1528
1488
takes_options = ['verbose',
1530
1490
RegistryOption.from_kwargs('file-deletion-strategy',
1531
1491
'The file deletion mode to be used.',
1532
1492
title='Deletion Strategy', value_switches=True, enum_switch=False,
1533
safe='Only delete files if they can be'
1534
' safely recovered (default).',
1493
safe='Backup changed files (default).',
1535
1494
keep='Delete from bzr but leave the working copy.',
1536
1495
force='Delete all the specified files, even if they can not be '
1537
1496
'recovered and even if they are non-empty directories.')]
1541
1500
def run(self, file_list, verbose=False, new=False,
1542
1501
file_deletion_strategy='safe'):
1543
tree, file_list = tree_files(file_list)
1502
tree, file_list = WorkingTree.open_containing_paths(file_list)
1545
1504
if file_list is not None:
1546
1505
file_list = [f for f in file_list]
1549
self.add_cleanup(tree.unlock)
1507
self.add_cleanup(tree.lock_write().unlock)
1550
1508
# Heuristics should probably all move into tree.remove_smart or
1636
1594
_see_also = ['check']
1637
1595
takes_args = ['branch?']
1597
Option('canonicalize-chks',
1598
help='Make sure CHKs are in canonical form (repairs '
1639
def run(self, branch="."):
1603
def run(self, branch=".", canonicalize_chks=False):
1640
1604
from bzrlib.reconcile import reconcile
1641
1605
dir = bzrdir.BzrDir.open(branch)
1606
reconcile(dir, canonicalize_chks=canonicalize_chks)
1645
1609
class cmd_revision_history(Command):
1985
1953
old_branch, new_branch,
1986
1954
specific_files, extra_trees) = get_trees_and_branches_to_diff_locked(
1987
1955
file_list, revision, old, new, self.add_cleanup, apply_view=True)
1956
# GNU diff on Windows uses ANSI encoding for filenames
1957
path_encoding = osutils.get_diff_header_encoding()
1988
1958
return show_diff_trees(old_tree, new_tree, sys.stdout,
1989
1959
specific_files=specific_files,
1990
1960
external_diff_options=diff_options,
1991
1961
old_label=old_label, new_label=new_label,
1992
extra_trees=extra_trees, using=using,
1962
extra_trees=extra_trees,
1963
path_encoding=path_encoding,
1993
1965
format_cls=format)
2003
1975
# level of effort but possibly much less IO. (Or possibly not,
2004
1976
# if the directories are very large...)
2005
1977
_see_also = ['status', 'ls']
2006
takes_options = ['show-ids']
1978
takes_options = ['directory', 'show-ids']
2008
1980
@display_command
2009
def run(self, show_ids=False):
2010
tree = WorkingTree.open_containing(u'.')[0]
2012
self.add_cleanup(tree.unlock)
1981
def run(self, show_ids=False, directory=u'.'):
1982
tree = WorkingTree.open_containing(directory)[0]
1983
self.add_cleanup(tree.lock_read().unlock)
2013
1984
old = tree.basis_tree()
2015
self.add_cleanup(old.unlock)
1985
self.add_cleanup(old.lock_read().unlock)
2016
1986
for path, ie in old.inventory.iter_entries():
2017
1987
if not tree.has_id(ie.file_id):
2018
1988
self.outf.write(path)
2030
2000
_see_also = ['status', 'ls']
2033
help='Write an ascii NUL (\\0) separator '
2034
'between files rather than a newline.')
2001
takes_options = ['directory', 'null']
2037
2003
@display_command
2038
def run(self, null=False):
2039
tree = WorkingTree.open_containing(u'.')[0]
2004
def run(self, null=False, directory=u'.'):
2005
tree = WorkingTree.open_containing(directory)[0]
2040
2006
td = tree.changes_from(tree.basis_tree())
2041
2007
for path, id, kind, text_modified, meta_modified in td.modified:
2053
2019
_see_also = ['status', 'ls']
2056
help='Write an ascii NUL (\\0) separator '
2057
'between files rather than a newline.')
2020
takes_options = ['directory', 'null']
2060
2022
@display_command
2061
def run(self, null=False):
2062
wt = WorkingTree.open_containing(u'.')[0]
2064
self.add_cleanup(wt.unlock)
2023
def run(self, null=False, directory=u'.'):
2024
wt = WorkingTree.open_containing(directory)[0]
2025
self.add_cleanup(wt.lock_read().unlock)
2065
2026
basis = wt.basis_tree()
2067
self.add_cleanup(basis.unlock)
2027
self.add_cleanup(basis.lock_read().unlock)
2068
2028
basis_inv = basis.inventory
2069
2029
inv = wt.inventory
2070
2030
for file_id in inv:
2073
2033
if inv.is_root(file_id) and len(basis_inv) == 0:
2075
2035
path = inv.id2path(file_id)
2076
if not os.access(osutils.abspath(path), os.F_OK):
2036
if not os.access(osutils.pathjoin(wt.basedir, path), os.F_OK):
2079
2039
self.outf.write(path + '\0')
2279
2239
help='Show just the specified revision.'
2280
2240
' See also "help revisionspec".'),
2242
RegistryOption('authors',
2243
'What names to list as authors - first, all or committer.',
2245
lazy_registry=('bzrlib.log', 'author_list_registry'),
2282
2247
Option('levels',
2283
2248
short_name='n',
2284
2249
help='Number of levels to display - 0 for all, 1 for flat.',
2353
2319
# find the file ids to log and check for directory filtering
2354
2320
b, file_info_list, rev1, rev2 = _get_info_for_log_files(
2355
revision, file_list)
2356
self.add_cleanup(b.unlock)
2321
revision, file_list, self.add_cleanup)
2357
2322
for relpath, file_id, kind in file_info_list:
2358
2323
if file_id is None:
2359
2324
raise errors.BzrCommandError(
2378
2343
dir, relpath = bzrdir.BzrDir.open_containing(location)
2379
2344
b = dir.open_branch()
2381
self.add_cleanup(b.unlock)
2345
self.add_cleanup(b.lock_read().unlock)
2382
2346
rev1, rev2 = _get_revision_range(revision, b, self.name())
2384
2348
# Decide on the type of delta & diff filtering to use
2404
2368
show_timezone=timezone,
2405
2369
delta_format=get_verbosity_level(),
2407
show_advice=levels is None)
2371
show_advice=levels is None,
2372
author_list_handler=authors)
2409
2374
# Choose the algorithm for doing the logging. It's annoying
2410
2375
# having multiple code paths like this but necessary until
2508
2473
tree, relpath = WorkingTree.open_containing(filename)
2509
2474
file_id = tree.path2id(relpath)
2510
2475
b = tree.branch
2512
self.add_cleanup(b.unlock)
2476
self.add_cleanup(b.lock_read().unlock)
2513
2477
touching_revs = log.find_touching_revisions(b, file_id)
2514
2478
for revno, revision_id, what in touching_revs:
2515
2479
self.outf.write("%6d %s\n" % (revno, what))
2528
2492
help='Recurse into subdirectories.'),
2529
2493
Option('from-root',
2530
2494
help='Print paths relative to the root of the branch.'),
2531
Option('unknown', help='Print unknown files.'),
2495
Option('unknown', short_name='u',
2496
help='Print unknown files.'),
2532
2497
Option('versioned', help='Print versioned files.',
2533
2498
short_name='V'),
2534
Option('ignored', help='Print ignored files.'),
2536
help='Write an ascii NUL (\\0) separator '
2537
'between files rather than a newline.'),
2499
Option('ignored', short_name='i',
2500
help='Print ignored files.'),
2501
Option('kind', short_name='k',
2539
2502
help='List entries of a particular kind: file, directory, symlink.',
2543
2508
@display_command
2544
2509
def run(self, revision=None, verbose=False,
2545
2510
recursive=False, from_root=False,
2546
2511
unknown=False, versioned=False, ignored=False,
2547
null=False, kind=None, show_ids=False, path=None):
2512
null=False, kind=None, show_ids=False, path=None, directory=None):
2549
2514
if kind and kind not in ('file', 'directory', 'symlink'):
2550
2515
raise errors.BzrCommandError('invalid kind specified')
2562
2527
raise errors.BzrCommandError('cannot specify both --from-root'
2565
tree, branch, relpath = bzrdir.BzrDir.open_containing_tree_or_branch(
2530
tree, branch, relpath = \
2531
_open_directory_or_containing_tree_or_branch(fs_path, directory)
2568
2533
# Calculate the prefix to use
2584
2549
view_str = views.view_display_str(view_files)
2585
2550
note("Ignoring files outside view. View is %s" % view_str)
2588
self.add_cleanup(tree.unlock)
2552
self.add_cleanup(tree.lock_read().unlock)
2589
2553
for fp, fc, fkind, fid, entry in tree.list_files(include_root=False,
2590
2554
from_dir=relpath, recursive=recursive):
2591
2555
# Apply additional masking
2640
2604
_see_also = ['ls']
2605
takes_options = ['directory']
2642
2607
@display_command
2644
for f in WorkingTree.open_containing(u'.')[0].unknowns():
2608
def run(self, directory=u'.'):
2609
for f in WorkingTree.open_containing(directory)[0].unknowns():
2645
2610
self.outf.write(osutils.quotefn(f) + '\n')
2713
2678
_see_also = ['status', 'ignored', 'patterns']
2714
2679
takes_args = ['name_pattern*']
2680
takes_options = ['directory',
2716
2681
Option('default-rules',
2717
2682
help='Display the default ignore rules that bzr uses.')
2720
def run(self, name_pattern_list=None, default_rules=None):
2685
def run(self, name_pattern_list=None, default_rules=None,
2721
2687
from bzrlib import ignores
2722
2688
if default_rules is not None:
2723
2689
# dump the default rules and exit
2729
2695
"NAME_PATTERN or --default-rules.")
2730
2696
name_pattern_list = [globbing.normalize_pattern(p)
2731
2697
for p in name_pattern_list]
2699
for p in name_pattern_list:
2700
if not globbing.Globster.is_pattern_valid(p):
2701
bad_patterns += ('\n %s' % p)
2703
msg = ('Invalid ignore pattern(s) found. %s' % bad_patterns)
2704
ui.ui_factory.show_error(msg)
2705
raise errors.InvalidPattern('')
2732
2706
for name_pattern in name_pattern_list:
2733
2707
if (name_pattern[0] == '/' or
2734
2708
(len(name_pattern) > 1 and name_pattern[1] == ':')):
2735
2709
raise errors.BzrCommandError(
2736
2710
"NAME_PATTERN should not be an absolute path")
2737
tree, relpath = WorkingTree.open_containing(u'.')
2711
tree, relpath = WorkingTree.open_containing(directory)
2738
2712
ignores.tree_ignores_add_patterns(tree, name_pattern_list)
2739
2713
ignored = globbing.Globster(name_pattern_list)
2715
self.add_cleanup(tree.lock_read().unlock)
2742
2716
for entry in tree.list_files():
2744
2718
if id is not None:
2745
2719
filename = entry[0]
2746
2720
if ignored.match(filename):
2747
2721
matches.append(filename)
2749
2722
if len(matches) > 0:
2750
2723
self.outf.write("Warning: the following files are version controlled and"
2751
2724
" match your ignore pattern:\n%s"
2767
2740
encoding_type = 'replace'
2768
2741
_see_also = ['ignore', 'ls']
2742
takes_options = ['directory']
2770
2744
@display_command
2772
tree = WorkingTree.open_containing(u'.')[0]
2774
self.add_cleanup(tree.unlock)
2745
def run(self, directory=u'.'):
2746
tree = WorkingTree.open_containing(directory)[0]
2747
self.add_cleanup(tree.lock_read().unlock)
2775
2748
for path, file_class, kind, file_id, entry in tree.list_files():
2776
2749
if file_class != 'I':
2790
2763
takes_args = ['revno']
2764
takes_options = ['directory']
2792
2766
@display_command
2793
def run(self, revno):
2767
def run(self, revno, directory=u'.'):
2795
2769
revno = int(revno)
2796
2770
except ValueError:
2797
2771
raise errors.BzrCommandError("not a valid revision-number: %r"
2799
revid = WorkingTree.open_containing(u'.')[0].branch.get_rev_id(revno)
2773
revid = WorkingTree.open_containing(directory)[0].branch.get_rev_id(revno)
2800
2774
self.outf.write("%s\n" % revid)
2829
2803
================= =========================
2831
2805
takes_args = ['dest', 'branch_or_subdir?']
2806
takes_options = ['directory',
2833
2807
Option('format',
2834
2808
help="Type of file to export to.",
2844
2818
'revision in which it was changed.'),
2846
2820
def run(self, dest, branch_or_subdir=None, revision=None, format=None,
2847
root=None, filters=False, per_file_timestamps=False):
2821
root=None, filters=False, per_file_timestamps=False, directory=u'.'):
2848
2822
from bzrlib.export import export
2850
2824
if branch_or_subdir is None:
2851
tree = WorkingTree.open_containing(u'.')[0]
2825
tree = WorkingTree.open_containing(directory)[0]
2852
2826
b = tree.branch
2875
2849
_see_also = ['ls']
2850
takes_options = ['directory',
2877
2851
Option('name-from-revision', help='The path name in the old tree.'),
2878
2852
Option('filters', help='Apply content filters to display the '
2879
2853
'convenience form.'),
2885
2859
@display_command
2886
2860
def run(self, filename, revision=None, name_from_revision=False,
2861
filters=False, directory=None):
2888
2862
if revision is not None and len(revision) != 1:
2889
2863
raise errors.BzrCommandError("bzr cat --revision takes exactly"
2890
2864
" one revision specifier")
2891
2865
tree, branch, relpath = \
2892
bzrdir.BzrDir.open_containing_tree_or_branch(filename)
2894
self.add_cleanup(branch.unlock)
2866
_open_directory_or_containing_tree_or_branch(filename, directory)
2867
self.add_cleanup(branch.lock_read().unlock)
2895
2868
return self._run(tree, branch, relpath, filename, revision,
2896
2869
name_from_revision, filters)
2900
2873
if tree is None:
2901
2874
tree = b.basis_tree()
2902
2875
rev_tree = _get_one_revision_tree('cat', revision, branch=b)
2903
rev_tree.lock_read()
2904
self.add_cleanup(rev_tree.unlock)
2876
self.add_cleanup(rev_tree.lock_read().unlock)
2906
2878
old_file_id = rev_tree.path2id(relpath)
3129
3101
properties = {}
3131
tree, selected_list = tree_files(selected_list)
3103
tree, selected_list = WorkingTree.open_containing_paths(selected_list)
3132
3104
if selected_list == ['']:
3133
3105
# workaround - commit of root of tree should be exactly the same
3134
3106
# as just default commit in that tree, and succeed even though
3169
3141
def get_message(commit_obj):
3170
3142
"""Callback to get commit message"""
3172
my_message = codecs.open(
3173
file, 'rt', osutils.get_user_encoding()).read()
3146
my_message = f.read().decode(osutils.get_user_encoding())
3174
3149
elif message is not None:
3175
3150
my_message = message
3205
3180
reporter=None, verbose=verbose, revprops=properties,
3206
3181
authors=author, timestamp=commit_stamp,
3207
3182
timezone=offset,
3208
exclude=safe_relpath_files(tree, exclude))
3183
exclude=tree.safe_relpath_files(exclude))
3209
3184
except PointlessCommit:
3210
3185
raise errors.BzrCommandError("No changes to commit."
3211
3186
" Use --unchanged to commit anyhow.")
3331
3306
bzr whoami "Frank Chu <fchu@example.com>"
3333
takes_options = [ Option('email',
3308
takes_options = [ 'directory',
3334
3310
help='Display email address only.'),
3335
3311
Option('branch',
3336
3312
help='Set identity for the current branch instead of '
3340
3316
encoding_type = 'replace'
3342
3318
@display_command
3343
def run(self, email=False, branch=False, name=None):
3319
def run(self, email=False, branch=False, name=None, directory=None):
3344
3320
if name is None:
3345
# use branch if we're inside one; otherwise global config
3347
c = Branch.open_containing('.')[0].get_config()
3348
except errors.NotBranchError:
3349
c = config.GlobalConfig()
3321
if directory is None:
3322
# use branch if we're inside one; otherwise global config
3324
c = Branch.open_containing(u'.')[0].get_config()
3325
except errors.NotBranchError:
3326
c = _mod_config.GlobalConfig()
3328
c = Branch.open(directory).get_config()
3351
3330
self.outf.write(c.user_email() + '\n')
3356
3335
# display a warning if an email address isn't included in the given name.
3358
config.extract_email_address(name)
3337
_mod_config.extract_email_address(name)
3359
3338
except errors.NoEmailInUsername, e:
3360
3339
warning('"%s" does not seem to contain an email address. '
3361
3340
'This is allowed, but not recommended.', name)
3363
3342
# use global config unless --branch given
3365
c = Branch.open_containing('.')[0].get_config()
3344
if directory is None:
3345
c = Branch.open_containing(u'.')[0].get_config()
3347
c = Branch.open(directory).get_config()
3367
c = config.GlobalConfig()
3349
c = _mod_config.GlobalConfig()
3368
3350
c.set_user_option('email', name)
3381
3363
_see_also = ['info']
3382
3364
takes_args = ['nickname?']
3383
def run(self, nickname=None):
3384
branch = Branch.open_containing(u'.')[0]
3365
takes_options = ['directory']
3366
def run(self, nickname=None, directory=u'.'):
3367
branch = Branch.open_containing(directory)[0]
3385
3368
if nickname is None:
3386
3369
self.printme(branch)
3436
3419
'bzr alias --remove expects an alias to remove.')
3437
3420
# If alias is not found, print something like:
3438
3421
# unalias: foo: not found
3439
c = config.GlobalConfig()
3422
c = _mod_config.GlobalConfig()
3440
3423
c.unset_alias(alias_name)
3442
3425
@display_command
3443
3426
def print_aliases(self):
3444
3427
"""Print out the defined aliases in a similar format to bash."""
3445
aliases = config.GlobalConfig().get_aliases()
3428
aliases = _mod_config.GlobalConfig().get_aliases()
3446
3429
for key, value in sorted(aliases.iteritems()):
3447
3430
self.outf.write('bzr alias %s="%s"\n' % (key, value))
3459
3442
def set_alias(self, alias_name, alias_command):
3460
3443
"""Save the alias in the global config."""
3461
c = config.GlobalConfig()
3444
c = _mod_config.GlobalConfig()
3462
3445
c.set_alias(alias_name, alias_command)
3537
3520
'throughout the test suite.',
3538
3521
type=get_transport_type),
3539
3522
Option('benchmark',
3540
help='Run the benchmarks rather than selftests.'),
3523
help='Run the benchmarks rather than selftests.',
3541
3525
Option('lsprof-timed',
3542
3526
help='Generate lsprof output for benchmarked'
3543
3527
' sections of code.'),
3544
3528
Option('lsprof-tests',
3545
3529
help='Generate lsprof output for each test.'),
3546
Option('cache-dir', type=str,
3547
help='Cache intermediate benchmark output in this '
3549
3530
Option('first',
3550
3531
help='Run all tests, but run specified tests first.',
3551
3532
short_name='f',
3586
3567
def run(self, testspecs_list=None, verbose=False, one=False,
3587
3568
transport=None, benchmark=None,
3588
lsprof_timed=None, cache_dir=None,
3589
3570
first=False, list_only=False,
3590
3571
randomize=None, exclude=None, strict=False,
3591
3572
load_list=None, debugflag=None, starting_with=None, subunit=False,
3592
3573
parallel=None, lsprof_tests=False):
3593
from bzrlib.tests import selftest
3594
import bzrlib.benchmarks as benchmarks
3595
from bzrlib.benchmarks import tree_creator
3597
# Make deprecation warnings visible, unless -Werror is set
3598
symbol_versioning.activate_deprecation_warnings(override=False)
3600
if cache_dir is not None:
3601
tree_creator.TreeCreator.CACHE_ROOT = osutils.abspath(cache_dir)
3574
from bzrlib import tests
3602
3576
if testspecs_list is not None:
3603
3577
pattern = '|'.join(testspecs_list)
3612
3586
self.additional_selftest_args['runner_class'] = SubUnitBzrRunner
3613
3587
# On Windows, disable automatic conversion of '\n' to '\r\n' in
3614
3588
# stdout, which would corrupt the subunit stream.
3615
if sys.platform == "win32" and sys.stdout.fileno() >= 0:
3589
# FIXME: This has been fixed in subunit trunk (>0.0.5) so the
3590
# following code can be deleted when it's sufficiently deployed
3591
# -- vila/mgz 20100514
3592
if (sys.platform == "win32"
3593
and getattr(sys.stdout, 'fileno', None) is not None):
3617
3595
msvcrt.setmode(sys.stdout.fileno(), os.O_BINARY)
3619
3597
self.additional_selftest_args.setdefault(
3620
3598
'suite_decorators', []).append(parallel)
3622
test_suite_factory = benchmarks.test_suite
3623
# Unless user explicitly asks for quiet, be verbose in benchmarks
3624
verbose = not is_quiet()
3625
# TODO: should possibly lock the history file...
3626
benchfile = open(".perf_history", "at", buffering=1)
3627
self.add_cleanup(benchfile.close)
3629
test_suite_factory = None
3600
raise errors.BzrCommandError(
3601
"--benchmark is no longer supported from bzr 2.2; "
3602
"use bzr-usertest instead")
3603
test_suite_factory = None
3631
3604
selftest_kwargs = {"verbose": verbose,
3632
3605
"pattern": pattern,
3633
3606
"stop_on_failure": one,
3635
3608
"test_suite_factory": test_suite_factory,
3636
3609
"lsprof_timed": lsprof_timed,
3637
3610
"lsprof_tests": lsprof_tests,
3638
"bench_history": benchfile,
3639
3611
"matching_tests_first": first,
3640
3612
"list_only": list_only,
3641
3613
"random_seed": randomize,
3646
3618
"starting_with": starting_with
3648
3620
selftest_kwargs.update(self.additional_selftest_args)
3649
result = selftest(**selftest_kwargs)
3622
# Make deprecation warnings visible, unless -Werror is set
3623
cleanup = symbol_versioning.activate_deprecation_warnings(
3626
result = tests.selftest(**selftest_kwargs)
3650
3629
return int(not result)
3691
3670
branch1 = Branch.open_containing(branch)[0]
3692
3671
branch2 = Branch.open_containing(other)[0]
3694
self.add_cleanup(branch1.unlock)
3696
self.add_cleanup(branch2.unlock)
3672
self.add_cleanup(branch1.lock_read().unlock)
3673
self.add_cleanup(branch2.lock_read().unlock)
3697
3674
last1 = ensure_null(branch1.last_revision())
3698
3675
last2 = ensure_null(branch2.last_revision())
3793
3770
' completely merged into the source, pull from the'
3794
3771
' source rather than merging. When this happens,'
3795
3772
' you do not need to commit the result.'),
3773
custom_help('directory',
3797
3774
help='Branch to merge into, '
3798
'rather than the one containing the working directory.',
3775
'rather than the one containing the working directory.'),
3802
3776
Option('preview', help='Instead of merging, show a diff of the'
3804
3778
Option('interactive', help='Select changes interactively.',
3837
3811
unversioned_filter=tree.is_ignored, view_info=view_info)
3838
3812
pb = ui.ui_factory.nested_progress_bar()
3839
3813
self.add_cleanup(pb.finished)
3841
self.add_cleanup(tree.unlock)
3814
self.add_cleanup(tree.lock_write().unlock)
3842
3815
if location is not None:
3844
3817
mergeable = bundle.read_mergeable_from_url(location,
3905
3878
def _do_preview(self, merger):
3906
3879
from bzrlib.diff import show_diff_trees
3907
3880
result_tree = self._get_preview(merger)
3881
path_encoding = osutils.get_diff_header_encoding()
3908
3882
show_diff_trees(merger.this_tree, result_tree, self.outf,
3909
old_label='', new_label='')
3883
old_label='', new_label='',
3884
path_encoding=path_encoding)
3911
3886
def _do_merge(self, merger, change_reporter, allow_pending, verified):
3912
3887
merger.change_reporter = change_reporter
4099
4074
from bzrlib.conflicts import restore
4100
4075
if merge_type is None:
4101
4076
merge_type = _mod_merge.Merge3Merger
4102
tree, file_list = tree_files(file_list)
4104
self.add_cleanup(tree.unlock)
4077
tree, file_list = WorkingTree.open_containing_paths(file_list)
4078
self.add_cleanup(tree.lock_write().unlock)
4105
4079
parents = tree.get_parent_ids()
4106
4080
if len(parents) != 2:
4107
4081
raise errors.BzrCommandError("Sorry, remerge only works after normal"
4217
4191
def run(self, revision=None, no_backup=False, file_list=None,
4218
4192
forget_merges=None):
4219
tree, file_list = tree_files(file_list)
4220
tree.lock_tree_write()
4221
self.add_cleanup(tree.unlock)
4193
tree, file_list = WorkingTree.open_containing_paths(file_list)
4194
self.add_cleanup(tree.lock_tree_write().unlock)
4222
4195
if forget_merges:
4223
4196
tree.set_parent_ids(tree.get_parent_ids()[:1])
4313
4286
_see_also = ['merge', 'pull']
4314
4287
takes_args = ['other_branch?']
4315
4288
takes_options = [
4316
4290
Option('reverse', 'Reverse the order of revisions.'),
4317
4291
Option('mine-only',
4318
4292
'Display changes in the local branch only.'),
4340
4314
theirs_only=False,
4341
4315
log_format=None, long=False, short=False, line=False,
4342
4316
show_ids=False, verbose=False, this=False, other=False,
4343
include_merges=False, revision=None, my_revision=None):
4317
include_merges=False, revision=None, my_revision=None,
4344
4319
from bzrlib.missing import find_unmerged, iter_log_revisions
4345
4320
def message(s):
4346
4321
if not is_quiet():
4359
4334
elif theirs_only:
4360
4335
restrict = 'remote'
4362
local_branch = Branch.open_containing(u".")[0]
4363
local_branch.lock_read()
4364
self.add_cleanup(local_branch.unlock)
4337
local_branch = Branch.open_containing(directory)[0]
4338
self.add_cleanup(local_branch.lock_read().unlock)
4366
4340
parent = local_branch.get_parent()
4367
4341
if other_branch is None:
4378
4352
if remote_branch.base == local_branch.base:
4379
4353
remote_branch = local_branch
4381
remote_branch.lock_read()
4382
self.add_cleanup(remote_branch.unlock)
4355
self.add_cleanup(remote_branch.lock_read().unlock)
4384
4357
local_revid_range = _revision_range_to_revid_range(
4385
4358
_get_revision_range(my_revision, local_branch,
4440
4413
message("Branches are up to date.\n")
4441
4414
self.cleanup_now()
4442
4415
if not status_code and parent is None and other_branch is not None:
4443
local_branch.lock_write()
4444
self.add_cleanup(local_branch.unlock)
4416
self.add_cleanup(local_branch.lock_write().unlock)
4445
4417
# handle race conditions - a parent might be set while we run.
4446
4418
if local_branch.get_parent() is None:
4447
4419
local_branch.set_parent(remote_branch.base)
4578
4549
Option('long', help='Show commit date in annotations.'),
4582
4554
encoding_type = 'exact'
4584
4556
@display_command
4585
4557
def run(self, filename, all=False, long=False, revision=None,
4558
show_ids=False, directory=None):
4587
4559
from bzrlib.annotate import annotate_file, annotate_file_tree
4588
4560
wt, branch, relpath = \
4589
bzrdir.BzrDir.open_containing_tree_or_branch(filename)
4561
_open_directory_or_containing_tree_or_branch(filename, directory)
4590
4562
if wt is not None:
4592
self.add_cleanup(wt.unlock)
4563
self.add_cleanup(wt.lock_read().unlock)
4595
self.add_cleanup(branch.unlock)
4565
self.add_cleanup(branch.lock_read().unlock)
4596
4566
tree = _get_one_revision_tree('annotate', revision, branch=branch)
4598
self.add_cleanup(tree.unlock)
4567
self.add_cleanup(tree.lock_read().unlock)
4599
4568
if wt is not None:
4600
4569
file_id = wt.path2id(relpath)
4620
4589
hidden = True # is this right ?
4621
4590
takes_args = ['revision_id*']
4622
takes_options = ['revision']
4591
takes_options = ['directory', 'revision']
4624
def run(self, revision_id_list=None, revision=None):
4593
def run(self, revision_id_list=None, revision=None, directory=u'.'):
4625
4594
if revision_id_list is not None and revision is not None:
4626
4595
raise errors.BzrCommandError('You can only supply one of revision_id or --revision')
4627
4596
if revision_id_list is None and revision is None:
4628
4597
raise errors.BzrCommandError('You must supply either --revision or a revision_id')
4629
b = WorkingTree.open_containing(u'.')[0].branch
4631
self.add_cleanup(b.unlock)
4598
b = WorkingTree.open_containing(directory)[0].branch
4599
self.add_cleanup(b.lock_write().unlock)
4632
4600
return self._run(b, revision_id_list, revision)
4634
4602
def _run(self, b, revision_id_list, revision):
4694
4662
_see_also = ['checkouts', 'unbind']
4695
4663
takes_args = ['location?']
4664
takes_options = ['directory']
4698
def run(self, location=None):
4699
b, relpath = Branch.open_containing(u'.')
4666
def run(self, location=None, directory=u'.'):
4667
b, relpath = Branch.open_containing(directory)
4700
4668
if location is None:
4702
4670
location = b.get_old_bound_location()
4730
4698
_see_also = ['checkouts', 'bind']
4731
4699
takes_args = []
4700
takes_options = ['directory']
4735
b, relpath = Branch.open_containing(u'.')
4702
def run(self, directory=u'.'):
4703
b, relpath = Branch.open_containing(directory)
4736
4704
if not b.unbind():
4737
4705
raise errors.BzrCommandError('Local branch is not bound')
4784
4752
b = control.open_branch()
4786
4754
if tree is not None:
4788
self.add_cleanup(tree.unlock)
4755
self.add_cleanup(tree.lock_write().unlock)
4791
self.add_cleanup(b.unlock)
4757
self.add_cleanup(b.lock_write().unlock)
4792
4758
return self._run(b, tree, dry_run, verbose, revision, force, local=local)
4794
4760
def _run(self, b, tree, dry_run, verbose, revision, force, local=False):
4848
4814
class cmd_break_lock(Command):
4849
__doc__ = """Break a dead lock on a repository, branch or working directory.
4815
__doc__ = """Break a dead lock.
4817
This command breaks a lock on a repository, branch, working directory or
4851
4820
CAUTION: Locks should only be broken when you are sure that the process
4852
4821
holding the lock has been stopped.
4859
4828
bzr break-lock bzr+ssh://example.com/bzr/foo
4829
bzr break-lock --conf ~/.bazaar
4861
4832
takes_args = ['location?']
4835
help='LOCATION is the directory where the config lock is.'),
4863
def run(self, location=None, show=False):
4838
def run(self, location=None, config=False):
4864
4839
if location is None:
4865
4840
location = u'.'
4866
control, relpath = bzrdir.BzrDir.open_containing(location)
4868
control.break_lock()
4869
except NotImplementedError:
4842
conf = _mod_config.LockableConfig(file_name=location)
4845
control, relpath = bzrdir.BzrDir.open_containing(location)
4847
control.break_lock()
4848
except NotImplementedError:
4873
4852
class cmd_wait_until_signalled(Command):
4902
4881
'result in a dynamically allocated port. The default port '
4903
4882
'depends on the protocol.',
4906
help='Serve contents of this directory.',
4884
custom_help('directory',
4885
help='Serve contents of this directory.'),
4908
4886
Option('allow-writes',
4909
4887
help='By default the server is a readonly server. Supplying '
4910
4888
'--allow-writes enables write access to the contents of '
4938
4916
def run(self, port=None, inet=False, directory=None, allow_writes=False,
4939
4917
protocol=None):
4940
from bzrlib.transport import get_transport, transport_server_registry
4918
from bzrlib import transport
4941
4919
if directory is None:
4942
4920
directory = os.getcwd()
4943
4921
if protocol is None:
4944
protocol = transport_server_registry.get()
4922
protocol = transport.transport_server_registry.get()
4945
4923
host, port = self.get_host_and_port(port)
4946
4924
url = urlutils.local_path_to_url(directory)
4947
4925
if not allow_writes:
4948
4926
url = 'readonly+' + url
4949
transport = get_transport(url)
4950
protocol(transport, host, port, inet)
4927
t = transport.get_transport(url)
4928
protocol(t, host, port, inet)
4953
4931
class cmd_join(Command):
5064
5043
encoding_type = 'exact'
5066
5045
def run(self, submit_branch=None, public_branch=None, patch_type='bundle',
5067
sign=False, revision=None, mail_to=None, message=None):
5046
sign=False, revision=None, mail_to=None, message=None,
5068
5048
from bzrlib.revision import ensure_null, NULL_REVISION
5069
5049
include_patch, include_bundle = {
5070
5050
'plain': (False, False),
5071
5051
'diff': (True, False),
5072
5052
'bundle': (True, True),
5074
branch = Branch.open('.')
5054
branch = Branch.open(directory)
5075
5055
stored_submit_branch = branch.get_submit_branch()
5076
5056
if submit_branch is None:
5077
5057
submit_branch = stored_submit_branch
5162
5142
given, in which case it is sent to a file.
5164
5144
Mail is sent using your preferred mail program. This should be transparent
5165
on Windows (it uses MAPI). On Linux, it requires the xdg-email utility.
5145
on Windows (it uses MAPI). On Unix, it requires the xdg-email utility.
5166
5146
If the preferred client can't be found (or used), your editor will be used.
5168
5148
To use a specific mail program, set the mail_client configuration option.
5339
5319
Option('delete',
5340
5320
help='Delete this tag rather than placing it.',
5343
help='Branch in which to place the tag.',
5322
custom_help('directory',
5323
help='Branch in which to place the tag.'),
5347
5324
Option('force',
5348
5325
help='Replace existing tags.',
5359
5336
branch, relpath = Branch.open_containing(directory)
5361
self.add_cleanup(branch.unlock)
5337
self.add_cleanup(branch.lock_write().unlock)
5363
5339
if tag_name is None:
5364
5340
raise errors.BzrCommandError("No tag specified to delete.")
5393
5369
_see_also = ['tag']
5394
5370
takes_options = [
5396
help='Branch whose tags should be displayed.',
5371
custom_help('directory',
5372
help='Branch whose tags should be displayed.'),
5400
5373
RegistryOption.from_kwargs('sort',
5401
5374
'Sort tags by different criteria.', title='Sorting',
5402
5375
alpha='Sort tags lexicographically (default).',
5423
self.add_cleanup(branch.unlock)
5395
self.add_cleanup(branch.lock_read().unlock)
5425
5397
graph = branch.repository.get_graph()
5426
5398
rev1, rev2 = _get_revision_range(revision, branch, self.name())
5575
5547
takes_args = ['to_location?']
5576
takes_options = [Option('force',
5548
takes_options = ['directory',
5577
5550
help='Switch even if local commits will be lost.'),
5579
5552
Option('create-branch', short_name='b',
5584
5557
def run(self, to_location=None, force=False, create_branch=False,
5558
revision=None, directory=u'.'):
5586
5559
from bzrlib import switch
5560
tree_location = directory
5588
5561
revision = _get_one_revision('switch', revision)
5589
5562
control_dir = bzrdir.BzrDir.open_containing(tree_location)[0]
5590
5563
if to_location is None:
5591
5564
if revision is None:
5592
5565
raise errors.BzrCommandError('You must supply either a'
5593
5566
' revision or a location')
5567
to_location = tree_location
5596
5569
branch = control_dir.open_branch()
5597
5570
had_explicit_nick = branch.get_config().has_explicit_nickname()
5735
tree, file_list = tree_files(file_list, apply_view=False)
5708
tree, file_list = WorkingTree.open_containing_paths(file_list,
5736
5710
current_view, view_dict = tree.views.get_view_info()
5737
5711
if name is None:
5738
5712
name = current_view
5886
5861
_see_also = ['unshelve']
5888
5863
def run(self, revision=None, all=False, file_list=None, message=None,
5889
writer=None, list=False, destroy=False):
5864
writer=None, list=False, destroy=False, directory=u'.'):
5891
5866
return self.run_for_list()
5892
5867
from bzrlib.shelf_ui import Shelver
5894
5869
writer = bzrlib.option.diff_writer_registry.get()
5896
5871
shelver = Shelver.from_args(writer(sys.stdout), revision, all,
5897
file_list, message, destroy=destroy)
5872
file_list, message, destroy=destroy, directory=directory)
5905
5880
def run_for_list(self):
5906
5881
tree = WorkingTree.open_containing('.')[0]
5908
self.add_cleanup(tree.unlock)
5882
self.add_cleanup(tree.lock_read().unlock)
5909
5883
manager = tree.get_shelf_manager()
5910
shelves = manager.active_shelves()
5884
shelves = shelf.list_shelves(tree)
5911
5885
if len(shelves) == 0:
5912
5886
note('No shelved changes.')
5914
for shelf_id in reversed(shelves):
5915
message = manager.get_metadata(shelf_id).get('message')
5917
message = '<no message>'
5888
for shelf_id, message in shelves:
5918
5889
self.outf.write('%3d: %s\n' % (shelf_id, message))
5930
5901
takes_args = ['shelf_id?']
5931
5902
takes_options = [
5932
5904
RegistryOption.from_kwargs(
5933
5905
'action', help="The action to perform.",
5934
5906
enum_switch=False, value_switches=True,
5943
5915
_see_also = ['shelve']
5945
def run(self, shelf_id=None, action='apply'):
5917
def run(self, shelf_id=None, action='apply', directory=u'.'):
5946
5918
from bzrlib.shelf_ui import Unshelver
5947
unshelver = Unshelver.from_args(shelf_id, action)
5919
unshelver = Unshelver.from_args(shelf_id, action, directory=directory)
5949
5921
unshelver.run()
5967
5939
To check what clean-tree will do, use --dry-run.
5969
takes_options = [Option('ignored', help='Delete all ignored files.'),
5941
takes_options = ['directory',
5942
Option('ignored', help='Delete all ignored files.'),
5970
5943
Option('detritus', help='Delete conflict files, merge'
5971
5944
' backups, and failed selftest dirs.'),
5972
5945
Option('unknown',
5975
5948
' deleting them.'),
5976
5949
Option('force', help='Do not prompt before deleting.')]
5977
5950
def run(self, unknown=False, ignored=False, detritus=False, dry_run=False,
5951
force=False, directory=u'.'):
5979
5952
from bzrlib.clean_tree import clean_tree
5980
5953
if not (unknown or ignored or detritus):
5984
clean_tree('.', unknown=unknown, ignored=ignored, detritus=detritus,
5985
dry_run=dry_run, no_prompt=force)
5957
clean_tree(directory, unknown=unknown, ignored=ignored,
5958
detritus=detritus, dry_run=dry_run, no_prompt=force)
5988
5961
class cmd_reference(Command):