~bzr-pqm/bzr/bzr.dev

« back to all changes in this revision

Viewing changes to bzrlib/config.py

  • Committer: John Arbash Meinel
  • Date: 2006-10-11 00:23:23 UTC
  • mfrom: (2070 +trunk)
  • mto: This revision was merged to the branch mainline in revision 2071.
  • Revision ID: john@arbash-meinel.com-20061011002323-82ba88c293d7caff
[merge] bzr.dev 2070

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
 
# Copyright (C) 2005 Canonical Ltd
 
1
# Copyright (C) 2005 by Canonical Ltd
2
2
#   Authors: Robert Collins <robert.collins@canonical.com>
3
3
#
4
4
# This program is free software; you can redistribute it and/or modify
75
75
from bzrlib import (
76
76
    errors,
77
77
    osutils,
78
 
    symbol_versioning,
79
78
    urlutils,
80
 
    win32utils,
81
79
    )
82
80
import bzrlib.util.configobj.configobj as configobj
83
81
""")
95
93
SIGN_NEVER=2
96
94
 
97
95
 
98
 
POLICY_NONE = 0
99
 
POLICY_NORECURSE = 1
100
 
POLICY_APPENDPATH = 2
101
 
 
102
 
_policy_name = {
103
 
    POLICY_NONE: None,
104
 
    POLICY_NORECURSE: 'norecurse',
105
 
    POLICY_APPENDPATH: 'appendpath',
106
 
    }
107
 
_policy_value = {
108
 
    None: POLICY_NONE,
109
 
    'none': POLICY_NONE,
110
 
    'norecurse': POLICY_NORECURSE,
111
 
    'appendpath': POLICY_APPENDPATH,
112
 
    }
113
 
 
114
 
 
115
 
STORE_LOCATION = POLICY_NONE
116
 
STORE_LOCATION_NORECURSE = POLICY_NORECURSE
117
 
STORE_LOCATION_APPENDPATH = POLICY_APPENDPATH
118
 
STORE_BRANCH = 3
119
 
STORE_GLOBAL = 4
120
 
 
121
 
 
122
96
class ConfigObj(configobj.ConfigObj):
123
97
 
124
98
    def get_bool(self, section, key):
288
262
            raise errors.ParseConfigError(e.errors, e.config.filename)
289
263
        return self._parser
290
264
 
291
 
    def _get_matching_sections(self):
292
 
        """Return an ordered list of (section_name, extra_path) pairs.
293
 
 
294
 
        If the section contains inherited configuration, extra_path is
295
 
        a string containing the additional path components.
296
 
        """
297
 
        section = self._get_section()
298
 
        if section is not None:
299
 
            return [(section, '')]
300
 
        else:
301
 
            return []
302
 
 
303
265
    def _get_section(self):
304
266
        """Override this to define the section used by the config."""
305
267
        return "DEFAULT"
306
268
 
307
 
    def _get_option_policy(self, section, option_name):
308
 
        """Return the policy for the given (section, option_name) pair."""
309
 
        return POLICY_NONE
310
 
 
311
269
    def _get_signature_checking(self):
312
270
        """See Config._get_signature_checking."""
313
271
        policy = self._get_user_option('check_signatures')
326
284
 
327
285
    def _get_user_option(self, option_name):
328
286
        """See Config._get_user_option."""
329
 
        for (section, extra_path) in self._get_matching_sections():
330
 
            try:
331
 
                value = self._get_parser().get_value(section, option_name)
332
 
            except KeyError:
333
 
                continue
334
 
            policy = self._get_option_policy(section, option_name)
335
 
            if policy == POLICY_NONE:
336
 
                return value
337
 
            elif policy == POLICY_NORECURSE:
338
 
                # norecurse items only apply to the exact path
339
 
                if extra_path:
340
 
                    continue
341
 
                else:
342
 
                    return value
343
 
            elif policy == POLICY_APPENDPATH:
344
 
                if extra_path:
345
 
                    value = urlutils.join(value, extra_path)
346
 
                return value
347
 
            else:
348
 
                raise AssertionError('Unexpected config policy %r' % policy)
349
 
        else:
350
 
            return None
 
287
        try:
 
288
            return self._get_parser().get_value(self._get_section(),
 
289
                                                option_name)
 
290
        except KeyError:
 
291
            pass
351
292
 
352
293
    def _gpg_signing_command(self):
353
294
        """See Config.gpg_signing_command."""
445
386
            location = urlutils.local_path_from_url(location)
446
387
        self.location = location
447
388
 
448
 
    def _get_matching_sections(self):
449
 
        """Return an ordered list of section names matching this location."""
 
389
    def _get_section(self):
 
390
        """Get the section we should look in for config items.
 
391
 
 
392
        Returns None if none exists. 
 
393
        TODO: perhaps return a NullSection that thunks through to the 
 
394
              global config.
 
395
        """
450
396
        sections = self._get_parser()
451
397
        location_names = self.location.split('/')
452
398
        if self.location.endswith('/'):
476
422
            # if section is longer, no match.
477
423
            if len(section_names) > len(location_names):
478
424
                continue
479
 
            matches.append((len(section_names), section,
480
 
                            '/'.join(location_names[len(section_names):])))
 
425
            # if path is longer, and recurse is not true, no match
 
426
            if len(section_names) < len(location_names):
 
427
                try:
 
428
                    if not self._get_parser()[section].as_bool('recurse'):
 
429
                        continue
 
430
                except KeyError:
 
431
                    pass
 
432
            matches.append((len(section_names), section))
 
433
        if not len(matches):
 
434
            return None
481
435
        matches.sort(reverse=True)
482
 
        sections = []
483
 
        for (length, section, extra_path) in matches:
484
 
            sections.append((section, extra_path))
485
 
            # should we stop looking for parent configs here?
486
 
            try:
487
 
                if self._get_parser()[section].as_bool('ignore_parents'):
488
 
                    break
489
 
            except KeyError:
490
 
                pass
491
 
        return sections
492
 
 
493
 
    def _get_option_policy(self, section, option_name):
494
 
        """Return the policy for the given (section, option_name) pair."""
495
 
        # check for the old 'recurse=False' flag
496
 
        try:
497
 
            recurse = self._get_parser()[section].as_bool('recurse')
498
 
        except KeyError:
499
 
            recurse = True
500
 
        if not recurse:
501
 
            return POLICY_NORECURSE
502
 
 
503
 
        policy_key = option_name + ':policy'
504
 
        try:
505
 
            policy_name = self._get_parser()[section][policy_key]
506
 
        except KeyError:
507
 
            policy_name = None
508
 
 
509
 
        return _policy_value[policy_name]
510
 
 
511
 
    def _set_option_policy(self, section, option_name, option_policy):
512
 
        """Set the policy for the given option name in the given section."""
513
 
        # The old recurse=False option affects all options in the
514
 
        # section.  To handle multiple policies in the section, we
515
 
        # need to convert it to a policy_norecurse key.
516
 
        try:
517
 
            recurse = self._get_parser()[section].as_bool('recurse')
518
 
        except KeyError:
519
 
            pass
520
 
        else:
521
 
            symbol_versioning.warn(
522
 
                'The recurse option is deprecated as of 0.14.  '
523
 
                'The section "%s" has been converted to use policies.'
524
 
                % section,
525
 
                DeprecationWarning)
526
 
            del self._get_parser()[section]['recurse']
527
 
            if not recurse:
528
 
                for key in self._get_parser()[section].keys():
529
 
                    if not key.endswith(':policy'):
530
 
                        self._get_parser()[section][key +
531
 
                                                    ':policy'] = 'norecurse'
532
 
 
533
 
        policy_key = option_name + ':policy'
534
 
        policy_name = _policy_name[option_policy]
535
 
        if policy_name is not None:
536
 
            self._get_parser()[section][policy_key] = policy_name
537
 
        else:
538
 
            if policy_key in self._get_parser()[section]:
539
 
                del self._get_parser()[section][policy_key]
540
 
 
541
 
    def set_user_option(self, option, value, store=STORE_LOCATION):
 
436
        return matches[0][1]
 
437
 
 
438
    def set_user_option(self, option, value):
542
439
        """Save option and its value in the configuration."""
543
 
        assert store in [STORE_LOCATION,
544
 
                         STORE_LOCATION_NORECURSE,
545
 
                         STORE_LOCATION_APPENDPATH], 'bad storage policy'
546
440
        # FIXME: RBC 20051029 This should refresh the parser and also take a
547
441
        # file lock on locations.conf.
548
442
        conf_dir = os.path.dirname(self._get_filename())
556
450
        elif location + '/' in self._get_parser():
557
451
            location = location + '/'
558
452
        self._get_parser()[location][option]=value
559
 
        # the allowed values of store match the config policies
560
 
        self._set_option_policy(location, option, store)
561
453
        self._get_parser().write(file(self._get_filename(), 'wb'))
562
454
 
563
455
 
638
530
                return value
639
531
        return None
640
532
 
641
 
    def set_user_option(self, name, value, store=STORE_BRANCH):
642
 
        if store == STORE_BRANCH:
 
533
    def set_user_option(self, name, value, local=False):
 
534
        if local is True:
 
535
            self._get_location_config().set_user_option(name, value)
 
536
        else:
643
537
            self._get_branch_data_config().set_option(value, name)
644
 
        elif store == STORE_GLOBAL:
645
 
            self._get_global_config().set_user_option(name, value)
646
 
        else:
647
 
            self._get_location_config().set_user_option(name, value, store)
 
538
 
648
539
 
649
540
    def _gpg_signing_command(self):
650
541
        """See Config.gpg_signing_command."""
668
559
        value = self._get_explicit_nickname()
669
560
        if value is not None:
670
561
            return value
671
 
        return urlutils.unescape(self.branch.base.split('/')[-2])
 
562
        return self.branch.base.split('/')[-2]
672
563
 
673
564
    def has_explicit_nickname(self):
674
565
        """Return true if a nickname has been explicitly assigned."""
710
601
    base = os.environ.get('BZR_HOME', None)
711
602
    if sys.platform == 'win32':
712
603
        if base is None:
713
 
            base = win32utils.get_appdata_location_unicode()
 
604
            base = os.environ.get('APPDATA', None)
714
605
        if base is None:
715
606
            base = os.environ.get('HOME', None)
716
607
        if base is None:
756
647
    """
757
648
    import socket
758
649
 
759
 
    if sys.platform == 'win32':
760
 
        name = win32utils.get_user_name_unicode()
761
 
        if name is None:
762
 
            raise errors.BzrError("Cannot autodetect user name.\n"
763
 
                                  "Please, set your name with command like:\n"
764
 
                                  'bzr whoami "Your Name <name@domain.com>"')
765
 
        host = win32utils.get_host_name_unicode()
766
 
        if host is None:
767
 
            host = socket.gethostname()
768
 
        return name, (name + '@' + host)
 
650
    # XXX: Any good way to get real user name on win32?
769
651
 
770
652
    try:
771
653
        import pwd