195
197
return self[section][name]
198
# FIXME: Until we can guarantee that each config file is loaded once and
199
# only once for a given bzrlib session, we don't want to re-read the file every
200
# time we query for an option so we cache the value (bad ! watch out for tests
201
# needing to restore the proper value). -- vila 20110219
202
_expand_default_value = None
203
def _get_expand_default_value():
204
global _expand_default_value
205
if _expand_default_value is not None:
206
return _expand_default_value
207
conf = GlobalConfig()
208
# Note that we must not use None for the expand value below or we'll run
209
# into infinite recursion. Using False really would be quite silly ;)
210
expand = conf.get_user_option_as_bool('bzr.config.expand', expand=True)
212
# This is an opt-in feature, you *really* need to clearly say you want
215
_expand_default_value = expand
219
200
class Config(object):
220
201
"""A configuration policy - what username, editor, gpg needs etc."""
226
207
"""Returns a unique ID for the config."""
227
208
raise NotImplementedError(self.config_id)
229
@deprecated_method(deprecated_in((2, 4, 0)))
230
def get_editor(self):
231
"""Get the users pop up editor."""
232
raise NotImplementedError
234
210
def get_change_editor(self, old_tree, new_tree):
235
211
from bzrlib import diff
236
212
cmd = self._get_change_editor()
373
349
"""Template method to provide a user option."""
376
def get_user_option(self, option_name, expand=None):
352
def get_user_option(self, option_name, expand=True):
377
353
"""Get a generic option - no special process, no default.
379
355
:param option_name: The queried option.
383
359
:returns: The value of the option.
386
expand = _get_expand_default_value()
387
361
value = self._get_user_option(option_name)
389
363
if isinstance(value, list):
637
611
for (oname, value, section, conf_id, parser) in self._get_options():
638
612
if oname.startswith('bzr.mergetool.'):
639
613
tool_name = oname[len('bzr.mergetool.'):]
640
tools[tool_name] = self.get_user_option(oname)
614
tools[tool_name] = self.get_user_option(oname, False)
641
615
trace.mutter('loaded merge tools: %r' % tools)
1079
1053
conf._create_from_string(str_or_unicode, save)
1082
@deprecated_method(deprecated_in((2, 4, 0)))
1083
def get_editor(self):
1084
return self._get_user_option('editor')
1086
1056
@needs_write_lock
1087
1057
def set_user_option(self, option, value):
1088
1058
"""Save option and its value in the configuration."""
1518
1488
"""Return per-user configuration directory as unicode string
1520
1490
By default this is %APPDATA%/bazaar/2.0 on Windows, ~/.bazaar on Mac OS X
1521
and Linux. On Linux, if there is a $XDG_CONFIG_HOME/bazaar directory,
1491
and Linux. On Mac OS X and Linux, if there is a $XDG_CONFIG_HOME/bazaar directory,
1522
1492
that will be used instead.
1524
1494
TODO: Global option --config-dir to override this.
1533
1503
# APPDATA, but hard to move. See bug 348640 for more.
1534
1504
return osutils.pathjoin(base, 'bazaar', '2.0')
1535
1505
if base is None:
1536
# GZ 2012-02-01: What should OSX use instead of XDG if anything?
1537
if sys.platform != 'darwin':
1538
xdg_dir = osutils.path_from_environ('XDG_CONFIG_HOME')
1540
xdg_dir = osutils.pathjoin(osutils._get_home_dir(), ".config")
1541
xdg_dir = osutils.pathjoin(xdg_dir, 'bazaar')
1542
if osutils.isdir(xdg_dir):
1544
"Using configuration in XDG directory %s." % xdg_dir)
1506
xdg_dir = osutils.path_from_environ('XDG_CONFIG_HOME')
1508
xdg_dir = osutils.pathjoin(osutils._get_home_dir(), ".config")
1509
xdg_dir = osutils.pathjoin(xdg_dir, 'bazaar')
1510
if osutils.isdir(xdg_dir):
1512
"Using configuration in XDG directory %s." % xdg_dir)
1546
1514
base = osutils._get_home_dir()
1547
1515
return osutils.pathjoin(base, ".bazaar")
1587
1555
def xdg_cache_dir():
1588
1556
# See http://standards.freedesktop.org/basedir-spec/latest/ar01s03.html
1589
1557
# Possibly this should be different on Windows?
1590
e = os.environ.get('XDG_CACHE_DIR', None)
1558
e = os.environ.get('XDG_CACHE_HOME', None)
1594
1562
return os.path.expanduser('~/.cache')
1597
def _get_default_mail_domain():
1565
def _get_default_mail_domain(mailname_file='/etc/mailname'):
1598
1566
"""If possible, return the assumed default email domain.
1600
1568
:returns: string mail domain, or None.
1603
1571
# No implementation yet; patches welcome
1606
f = open('/etc/mailname')
1574
f = open(mailname_file)
1607
1575
except (IOError, OSError), e:
1610
domain = f.read().strip()
1578
domain = f.readline().strip()
2163
2131
credential_store_registry.default_key = 'plain'
2134
class Base64CredentialStore(CredentialStore):
2135
__doc__ = """Base64 credential store for the authentication.conf file"""
2137
def decode_password(self, credentials):
2138
"""See CredentialStore.decode_password."""
2139
# GZ 2012-07-28: Will raise binascii.Error if password is not base64,
2140
# should probably propogate as something more useful.
2141
return base64.decodestring(credentials['password'])
2143
credential_store_registry.register('base64', Base64CredentialStore,
2144
help=Base64CredentialStore.__doc__)
2166
2147
class BzrDirConfig(object):
2168
2149
def __init__(self, bzrdir):
2175
2156
It may be set to a location, or None.
2177
This policy affects all branches contained by this bzrdir, except for
2178
those under repositories.
2158
This policy affects all branches contained by this control dir, except
2159
for those under repositories.
2180
2161
if self._config is None:
2181
raise errors.BzrError("Cannot set configuration in %s" % self._bzrdir)
2162
raise errors.BzrError("Cannot set configuration in %s"
2182
2164
if value is None:
2183
2165
self._config.set_option('', 'default_stack_on')
2190
2172
This will either be a location, or None.
2192
This policy affects all branches contained by this bzrdir, except for
2193
those under repositories.
2174
This policy affects all branches contained by this control dir, except
2175
for those under repositories.
2195
2177
if self._config is None:
2332
2314
:param help: a doc string to explain the option to the user.
2334
2316
:param from_unicode: a callable to convert the unicode string
2335
representing the option value in a store. This is not called for
2317
representing the option value in a store or its default value.
2338
2319
:param invalid: the action to be taken when an invalid value is
2339
2320
encountered in a store. This is called only when from_unicode is
2430
2411
value = self.default()
2431
2412
if not isinstance(value, unicode):
2432
2413
raise AssertionError(
2433
'Callable default values should be unicode')
2414
"Callable default value for '%s' should be unicode"
2435
2417
value = self.default
2420
def get_help_topic(self):
2438
2423
def get_help_text(self, additional_see_also=None, plain=True):
2439
2424
result = self.help
2440
2425
from bzrlib import help_topics
2486
2471
return float(unicode_str)
2489
# Use a an empty dict to initialize an empty configobj avoiding all
2490
# parsing and encoding checks
2474
# Use an empty dict to initialize an empty configobj avoiding all parsing and
2491
2476
_list_converter_config = configobj.ConfigObj(
2492
2477
{}, encoding='utf-8', list_values=True, interpolation=False)
2565
2550
return "".join(ret)
2553
_option_ref_re = lazy_regex.lazy_compile('({[^\d\W](?:\.\w|\w)*})')
2554
"""Describes an expandable option reference.
2556
We want to match the most embedded reference first.
2558
I.e. for '{{foo}}' we will get '{foo}',
2559
for '{bar{baz}}' we will get '{baz}'
2562
def iter_option_refs(string):
2563
# Split isolate refs so every other chunk is a ref
2565
for chunk in _option_ref_re.split(string):
2568
2570
class OptionRegistry(registry.Registry):
2569
2571
"""Register config options by their name.
2572
2574
some information from the option object itself.
2577
def _check_option_name(self, option_name):
2578
"""Ensures an option name is valid.
2580
:param option_name: The name to validate.
2582
if _option_ref_re.match('{%s}' % option_name) is None:
2583
raise errors.IllegalOptionName(option_name)
2575
2585
def register(self, option):
2576
2586
"""Register a new option to its name.
2578
2588
:param option: The option to register. Its name is used as the key.
2590
self._check_option_name(option.name)
2580
2591
super(OptionRegistry, self).register(option.name, option,
2581
2592
help=option.help)
2591
2602
:param member_name: the member of the module to return. If empty or
2592
2603
None, get() will return the module itself.
2605
self._check_option_name(key)
2594
2606
super(OptionRegistry, self).register_lazy(key,
2595
2607
module_name, member_name)
2816
2828
Each function takes branch, rev_id as parameters.
2830
option_registry.register_lazy('progress_bar', 'bzrlib.ui.text',
2818
2832
option_registry.register(
2819
2833
Option('public_branch',
2957
2971
self.options[name] = value
2959
2973
def remove(self, name):
2960
if name not in self.orig:
2974
if name not in self.orig and name in self.options:
2961
2975
self.orig[name] = self.get(name, None)
2962
2976
del self.options[name]
2985
2999
# Report concurrent updates in an ad-hoc way. This should only
2986
3000
# occurs when different processes try to update the same option
2987
3001
# which is not supported (as in: the config framework is not meant
2988
# to be used a sharing mechanism).
3002
# to be used as a sharing mechanism).
2989
3003
if expected != reloaded:
2990
3004
if actual is _DeletedOption:
2991
3005
actual = '<DELETED>'
3011
3025
mutable_section_class = MutableSection
3013
3027
def __init__(self):
3014
# Which sections need to be saved
3015
self.dirty_sections = []
3028
# Which sections need to be saved (by section id). We use a dict here
3029
# so the dirty sections can be shared by multiple callers.
3030
self.dirty_sections = {}
3017
3032
def is_loaded(self):
3018
3033
"""Returns True if the Store has been loaded.
3081
3096
# get_mutable_section() call below.
3083
3098
# Apply the changes from the preserved dirty sections
3084
for dirty in dirty_sections:
3085
clean = self.get_mutable_section(dirty.id)
3099
for section_id, dirty in dirty_sections.iteritems():
3100
clean = self.get_mutable_section(section_id)
3086
3101
clean.apply_changes(dirty, self)
3087
3102
# Everything is clean now
3088
self.dirty_sections = []
3103
self.dirty_sections = {}
3090
3105
def save_changes(self):
3091
3106
"""Saves the Store to persistent storage if changes occurred.
3225
3240
if not self._need_saving():
3227
3242
# Preserve the current version
3228
current = self._config_obj
3229
dirty_sections = list(self.dirty_sections)
3243
dirty_sections = dict(self.dirty_sections.items())
3230
3244
self.apply_changes(dirty_sections)
3231
3245
# Save to the persistent storage
3267
3281
except errors.NoSuchFile:
3268
3282
# The file doesn't exist, let's pretend it was empty
3269
3283
self._load_from_string('')
3284
if section_id in self.dirty_sections:
3285
# We already created a mutable section for this id
3286
return self.dirty_sections[section_id]
3270
3287
if section_id is None:
3271
3288
section = self._config_obj
3273
3290
section = self._config_obj.setdefault(section_id, {})
3274
3291
mutable_section = self.mutable_section_class(section_id, section)
3275
3292
# All mutable sections can become dirty
3276
self.dirty_sections.append(mutable_section)
3293
self.dirty_sections[section_id] = mutable_section
3277
3294
return mutable_section
3279
3296
def quote(self, value):
3393
3411
# on the relevant parts of the API that needs testing -- vila 20110503 (based
3394
3412
# on a poolie's remark)
3395
3413
class GlobalStore(LockableIniFileStore):
3414
"""A config store for global options.
3416
There is a single GlobalStore for a given process.
3397
3419
def __init__(self, possible_transports=None):
3398
3420
t = transport.get_transport_from_path(
3404
3426
class LocationStore(LockableIniFileStore):
3427
"""A config store for options specific to a location.
3429
There is a single LocationStore for a given process.
3406
3432
def __init__(self, possible_transports=None):
3407
3433
t = transport.get_transport_from_path(
3413
3439
class BranchStore(TransportIniFileStore):
3440
"""A config store for branch options.
3442
There is a single BranchStore for a given branch.
3415
3445
def __init__(self, branch):
3416
3446
super(BranchStore, self).__init__(branch.control_transport,
3470
3500
class LocationSection(Section):
3472
def __init__(self, section, extra_path):
3502
def __init__(self, section, extra_path, branch_name=None):
3473
3503
super(LocationSection, self).__init__(section.id, section.options)
3474
3504
self.extra_path = extra_path
3505
if branch_name is None:
3475
3507
self.locals = {'relpath': extra_path,
3476
'basename': urlutils.basename(extra_path)}
3508
'basename': urlutils.basename(extra_path),
3509
'branchname': branch_name}
3478
3511
def get(self, name, default=None, expand=True):
3479
3512
value = super(LocationSection, self).get(name, default)
3550
3582
def __init__(self, store, location):
3551
3583
super(LocationMatcher, self).__init__(store)
3584
url, params = urlutils.split_segment_parameters(location)
3552
3585
if location.startswith('file://'):
3553
3586
location = urlutils.local_path_from_url(location)
3554
3587
self.location = location
3588
branch_name = params.get('branch')
3589
if branch_name is None:
3590
self.branch_name = urlutils.basename(self.location)
3592
self.branch_name = urlutils.unescape(branch_name)
3556
3594
def _get_matching_sections(self):
3557
3595
"""Get all sections matching ``location``."""
3584
3622
section = iter_all_sections.next()
3585
3623
if section_id == section.id:
3586
matching_sections.append(
3587
(length, LocationSection(section, extra_path)))
3624
section = LocationSection(section, extra_path,
3626
matching_sections.append((length, section))
3589
3628
return matching_sections
3607
3646
yield self.store, section
3610
_option_ref_re = lazy_regex.lazy_compile('({[^{}\n]+})')
3611
"""Describes an expandable option reference.
3613
We want to match the most embedded reference first.
3615
I.e. for '{{foo}}' we will get '{foo}',
3616
for '{bar{baz}}' we will get '{baz}'
3619
def iter_option_refs(string):
3620
# Split isolate refs so every other chunk is a ref
3622
for chunk in _option_ref_re.split(string):
3649
# FIXME: _shared_stores should be an attribute of a library state once a
3650
# library_state object is always available.
3652
_shared_stores_at_exit_installed = False
3627
3654
class Stack(object):
3628
3655
"""A stack of configurations where an option can be defined"""
3655
3682
for store, section in sections():
3656
3683
yield store, section
3658
def get(self, name, expand=None, convert=True):
3685
def get(self, name, expand=True, convert=True):
3659
3686
"""Return the *first* option value found in the sections.
3661
3688
This is where we guarantee that sections coming from Store are loaded
3674
3701
:returns: The value of the option.
3676
3703
# FIXME: No caching of options nor sections yet -- vila 20110503
3678
expand = _get_expand_default_value()
3680
3705
found_store = None # Where the option value has been found
3681
3706
# If the option is registered, it may provide additional info about
3819
3844
return "<config.%s(%s)>" % (self.__class__.__name__, id(self))
3821
3846
def _get_overrides(self):
3822
# Hack around library_state.initialize never called
3847
# FIXME: Hack around library_state.initialize never called
3823
3848
if bzrlib.global_state is not None:
3824
3849
return bzrlib.global_state.cmdline_overrides.get_sections()
3852
def get_shared_store(self, store, state=None):
3853
"""Get a known shared store.
3855
Store urls uniquely identify them and are used to ensure a single copy
3856
is shared across all users.
3858
:param store: The store known to the caller.
3860
:param state: The library state where the known stores are kept.
3862
:returns: The store received if it's not a known one, an already known
3866
state = bzrlib.global_state
3868
global _shared_stores_at_exit_installed
3869
stores = _shared_stores
3870
def save_config_changes():
3871
for k, store in stores.iteritems():
3872
store.save_changes()
3873
if not _shared_stores_at_exit_installed:
3874
# FIXME: Ugly hack waiting for library_state to always be
3875
# available. -- vila 20120731
3877
atexit.register(save_config_changes)
3878
_shared_stores_at_exit_installed = True
3880
stores = state.config_stores
3881
url = store.external_url()
3828
3889
class MemoryStack(Stack):
3829
3890
"""A configuration stack defined from a string.
3895
3956
def __init__(self):
3896
gstore = GlobalStore()
3957
gstore = self.get_shared_store(GlobalStore())
3897
3958
super(GlobalStack, self).__init__(
3898
3959
[self._get_overrides,
3899
3960
NameMatcher(gstore, 'DEFAULT').get_sections],
3900
3961
gstore, mutable_section_id='DEFAULT')
3903
class LocationStack(_CompatibleStack):
3964
class LocationStack(Stack):
3904
3965
"""Per-location options falling back to global options stack.
3922
3983
"""Make a new stack for a location and global configuration.
3924
3985
:param location: A URL prefix to """
3925
lstore = LocationStore()
3986
lstore = self.get_shared_store(LocationStore())
3926
3987
if location.startswith('file://'):
3927
3988
location = urlutils.local_path_from_url(location)
3928
gstore = GlobalStore()
3989
gstore = self.get_shared_store(GlobalStore())
3929
3990
super(LocationStack, self).__init__(
3930
3991
[self._get_overrides,
3931
3992
LocationMatcher(lstore, location).get_sections,
3955
4016
def __init__(self, branch):
3956
lstore = LocationStore()
4017
lstore = self.get_shared_store(LocationStore())
3957
4018
bstore = branch._get_config_store()
3958
gstore = GlobalStore()
4019
gstore = self.get_shared_store(GlobalStore())
3959
4020
super(BranchStack, self).__init__(
3960
4021
[self._get_overrides,
3961
4022
LocationMatcher(lstore, branch.base).get_sections,
3983
4044
# unlock saves all the changes.
3986
class RemoteControlStack(_CompatibleStack):
4047
class RemoteControlStack(Stack):
3987
4048
"""Remote control-only options stack."""
3989
4050
# FIXME 2011-11-22 JRV This should probably be renamed to avoid confusion
4034
4095
class cmd_config(commands.Command):
4035
4096
__doc__ = """Display, set or remove a configuration option.
4037
Display the active value for a given option.
4098
Display the active value for option NAME.
4039
4100
If --all is specified, NAME is interpreted as a regular expression and all
4040
matching options are displayed mentioning their scope. The active value
4041
that bzr will take into account is the first one displayed for each option.
4043
If no NAME is given, --all .* is implied.
4045
Setting a value is achieved by using name=value without spaces. The value
4101
matching options are displayed mentioning their scope and without resolving
4102
option references in the value). The active value that bzr will take into
4103
account is the first one displayed for each option.
4105
If NAME is not given, --all .* is implied (all options are displayed for the
4108
Setting a value is achieved by using NAME=value without spaces. The value
4046
4109
is set in the most relevant scope and can be checked by displaying the
4112
Removing a value is achieved by using --remove NAME.
4050
4115
takes_args = ['name?']
4179
4245
def _set_config_option(self, name, value, directory, scope):
4180
4246
conf = self._get_stack(directory, scope, write_access=True)
4181
4247
conf.set(name, value)
4248
# Explicitly save the changes
4249
conf.store.save_changes()
4183
4251
def _remove_config_option(self, name, directory, scope):
4184
4252
if name is None:
4187
4255
conf = self._get_stack(directory, scope, write_access=True)
4189
4257
conf.remove(name)
4258
# Explicitly save the changes
4259
conf.store.save_changes()
4190
4260
except KeyError:
4191
4261
raise errors.NoSuchConfigOption(name)