annotate mercurial/config.py @ 34449:47b9c572ca32

test-convert-cvs: make test compatible with chg The test uses the 'print' method instead of writing to stdout using 'ui.write' which leads to incompatibility with chg. This commit modifies the test to use the 'ui' object instead which fixes the problem. Test Plan: Ran the test 'test-convert-cvs.t' with and without '--chg' option. Differential Revision: https://phab.mercurial-scm.org/D923
author Saurabh Singh <singhsrb@fb.com>
date Tue, 03 Oct 2017 12:49:28 -0700
parents c41444a39de2
children 0efdfb57b05c
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
8229
ddf3d6656e7c config: add copyright and license header
Martin Geisler <mg@lazybytes.net>
parents: 8222
diff changeset
1 # config.py - configuration parsing for Mercurial
ddf3d6656e7c config: add copyright and license header
Martin Geisler <mg@lazybytes.net>
parents: 8222
diff changeset
2 #
ddf3d6656e7c config: add copyright and license header
Martin Geisler <mg@lazybytes.net>
parents: 8222
diff changeset
3 # Copyright 2009 Matt Mackall <mpm@selenic.com> and others
ddf3d6656e7c config: add copyright and license header
Martin Geisler <mg@lazybytes.net>
parents: 8222
diff changeset
4 #
ddf3d6656e7c config: add copyright and license header
Martin Geisler <mg@lazybytes.net>
parents: 8222
diff changeset
5 # This software may be used and distributed according to the terms of the
10263
25e572394f5c Update license to GPLv2+
Matt Mackall <mpm@selenic.com>
parents: 10042
diff changeset
6 # GNU General Public License version 2 or any later version.
8229
ddf3d6656e7c config: add copyright and license header
Martin Geisler <mg@lazybytes.net>
parents: 8222
diff changeset
7
25923
a027a0813b44 config: use absolute_import
Gregory Szorc <gregory.szorc@gmail.com>
parents: 25660
diff changeset
8 from __future__ import absolute_import
a027a0813b44 config: use absolute_import
Gregory Szorc <gregory.szorc@gmail.com>
parents: 25660
diff changeset
9
a027a0813b44 config: use absolute_import
Gregory Szorc <gregory.szorc@gmail.com>
parents: 25660
diff changeset
10 import errno
a027a0813b44 config: use absolute_import
Gregory Szorc <gregory.szorc@gmail.com>
parents: 25660
diff changeset
11 import os
a027a0813b44 config: use absolute_import
Gregory Szorc <gregory.szorc@gmail.com>
parents: 25660
diff changeset
12
a027a0813b44 config: use absolute_import
Gregory Szorc <gregory.szorc@gmail.com>
parents: 25660
diff changeset
13 from .i18n import _
a027a0813b44 config: use absolute_import
Gregory Szorc <gregory.szorc@gmail.com>
parents: 25660
diff changeset
14 from . import (
a027a0813b44 config: use absolute_import
Gregory Szorc <gregory.szorc@gmail.com>
parents: 25660
diff changeset
15 error,
31306
c920efa9d34b config: guard against setconfig specifying unicode values on py3
Augie Fackler <raf@durin42.com>
parents: 31176
diff changeset
16 pycompat,
25923
a027a0813b44 config: use absolute_import
Gregory Szorc <gregory.szorc@gmail.com>
parents: 25660
diff changeset
17 util,
a027a0813b44 config: use absolute_import
Gregory Szorc <gregory.szorc@gmail.com>
parents: 25660
diff changeset
18 )
8144
fca54469480e ui: introduce new config parser
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
19
8186
6a0018cdb2fe config: add some helper methods
Matt Mackall <mpm@selenic.com>
parents: 8185
diff changeset
20 class config(object):
31374
d30fb3de4b40 config: avoid using a mutable default
Martijn Pieters <mjpieters@fb.com>
parents: 31306
diff changeset
21 def __init__(self, data=None, includepaths=None):
8144
fca54469480e ui: introduce new config parser
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
22 self._data = {}
19087
7d82ad4b3727 config: discard "%unset" values defined in the other files read in previously
FUJIWARA Katsunori <foozy@lares.dti.ne.jp>
parents: 17537
diff changeset
23 self._unset = []
31374
d30fb3de4b40 config: avoid using a mutable default
Martijn Pieters <mjpieters@fb.com>
parents: 31306
diff changeset
24 self._includepaths = includepaths or []
8144
fca54469480e ui: introduce new config parser
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
25 if data:
fca54469480e ui: introduce new config parser
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
26 for k in data._data:
fca54469480e ui: introduce new config parser
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
27 self._data[k] = data[k].copy()
8185
dc10a7a3f1d4 config: split source data out into separate map
Matt Mackall <mpm@selenic.com>
parents: 8184
diff changeset
28 self._source = data._source.copy()
34357
c41444a39de2 config: use copy-on-write to improve copy performance
Jun Wu <quark@fb.com>
parents: 34131
diff changeset
29 else:
c41444a39de2 config: use copy-on-write to improve copy performance
Jun Wu <quark@fb.com>
parents: 34131
diff changeset
30 self._source = util.cowdict()
8144
fca54469480e ui: introduce new config parser
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
31 def copy(self):
fca54469480e ui: introduce new config parser
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
32 return config(self)
fca54469480e ui: introduce new config parser
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
33 def __contains__(self, section):
fca54469480e ui: introduce new config parser
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
34 return section in self._data
27696
e70c97cc9243 config: add hasconfig method and supporting plumbing
Bryan O'Sullivan <bos@serpentine.com>
parents: 25923
diff changeset
35 def hasitem(self, section, item):
e70c97cc9243 config: add hasconfig method and supporting plumbing
Bryan O'Sullivan <bos@serpentine.com>
parents: 25923
diff changeset
36 return item in self._data.get(section, {})
8186
6a0018cdb2fe config: add some helper methods
Matt Mackall <mpm@selenic.com>
parents: 8185
diff changeset
37 def __getitem__(self, section):
6a0018cdb2fe config: add some helper methods
Matt Mackall <mpm@selenic.com>
parents: 8185
diff changeset
38 return self._data.get(section, {})
6a0018cdb2fe config: add some helper methods
Matt Mackall <mpm@selenic.com>
parents: 8185
diff changeset
39 def __iter__(self):
6a0018cdb2fe config: add some helper methods
Matt Mackall <mpm@selenic.com>
parents: 8185
diff changeset
40 for d in self.sections():
6a0018cdb2fe config: add some helper methods
Matt Mackall <mpm@selenic.com>
parents: 8185
diff changeset
41 yield d
8193
94246e90081e config: add section filter to read
Matt Mackall <mpm@selenic.com>
parents: 8192
diff changeset
42 def update(self, src):
34357
c41444a39de2 config: use copy-on-write to improve copy performance
Jun Wu <quark@fb.com>
parents: 34131
diff changeset
43 self._source = self._source.preparewrite()
19087
7d82ad4b3727 config: discard "%unset" values defined in the other files read in previously
FUJIWARA Katsunori <foozy@lares.dti.ne.jp>
parents: 17537
diff changeset
44 for s, n in src._unset:
34357
c41444a39de2 config: use copy-on-write to improve copy performance
Jun Wu <quark@fb.com>
parents: 34131
diff changeset
45 ds = self._data.get(s, None)
c41444a39de2 config: use copy-on-write to improve copy performance
Jun Wu <quark@fb.com>
parents: 34131
diff changeset
46 if ds is not None and n in ds:
c41444a39de2 config: use copy-on-write to improve copy performance
Jun Wu <quark@fb.com>
parents: 34131
diff changeset
47 self._data[s] = ds.preparewrite()
19087
7d82ad4b3727 config: discard "%unset" values defined in the other files read in previously
FUJIWARA Katsunori <foozy@lares.dti.ne.jp>
parents: 17537
diff changeset
48 del self._data[s][n]
7d82ad4b3727 config: discard "%unset" values defined in the other files read in previously
FUJIWARA Katsunori <foozy@lares.dti.ne.jp>
parents: 17537
diff changeset
49 del self._source[(s, n)]
8193
94246e90081e config: add section filter to read
Matt Mackall <mpm@selenic.com>
parents: 8192
diff changeset
50 for s in src:
34357
c41444a39de2 config: use copy-on-write to improve copy performance
Jun Wu <quark@fb.com>
parents: 34131
diff changeset
51 ds = self._data.get(s, None)
c41444a39de2 config: use copy-on-write to improve copy performance
Jun Wu <quark@fb.com>
parents: 34131
diff changeset
52 if ds:
c41444a39de2 config: use copy-on-write to improve copy performance
Jun Wu <quark@fb.com>
parents: 34131
diff changeset
53 self._data[s] = ds.preparewrite()
c41444a39de2 config: use copy-on-write to improve copy performance
Jun Wu <quark@fb.com>
parents: 34131
diff changeset
54 else:
c41444a39de2 config: use copy-on-write to improve copy performance
Jun Wu <quark@fb.com>
parents: 34131
diff changeset
55 self._data[s] = util.cowsortdict()
8193
94246e90081e config: add section filter to read
Matt Mackall <mpm@selenic.com>
parents: 8192
diff changeset
56 self._data[s].update(src._data[s])
94246e90081e config: add section filter to read
Matt Mackall <mpm@selenic.com>
parents: 8192
diff changeset
57 self._source.update(src._source)
8144
fca54469480e ui: introduce new config parser
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
58 def get(self, section, item, default=None):
8185
dc10a7a3f1d4 config: split source data out into separate map
Matt Mackall <mpm@selenic.com>
parents: 8184
diff changeset
59 return self._data.get(section, {}).get(item, default)
15919
69e792cf7851 config: have a way to backup and restore value in config
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents: 14696
diff changeset
60
69e792cf7851 config: have a way to backup and restore value in config
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents: 14696
diff changeset
61 def backup(self, section, item):
17527
6e11d5cf8e39 spelling: value
timeless@mozdev.org
parents: 16944
diff changeset
62 """return a tuple allowing restore to reinstall a previous value
15919
69e792cf7851 config: have a way to backup and restore value in config
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents: 14696
diff changeset
63
17530
0dff04ffa15d grammar: it-handles
timeless@mozdev.org
parents: 17527
diff changeset
64 The main reason we need it is because it handles the "no data" case.
15919
69e792cf7851 config: have a way to backup and restore value in config
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents: 14696
diff changeset
65 """
69e792cf7851 config: have a way to backup and restore value in config
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents: 14696
diff changeset
66 try:
69e792cf7851 config: have a way to backup and restore value in config
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents: 14696
diff changeset
67 value = self._data[section][item]
69e792cf7851 config: have a way to backup and restore value in config
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents: 14696
diff changeset
68 source = self.source(section, item)
69e792cf7851 config: have a way to backup and restore value in config
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents: 14696
diff changeset
69 return (section, item, value, source)
69e792cf7851 config: have a way to backup and restore value in config
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents: 14696
diff changeset
70 except KeyError:
69e792cf7851 config: have a way to backup and restore value in config
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents: 14696
diff changeset
71 return (section, item)
69e792cf7851 config: have a way to backup and restore value in config
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents: 14696
diff changeset
72
8198
cf9accffd0b3 config: getsource -> source
Matt Mackall <mpm@selenic.com>
parents: 8193
diff changeset
73 def source(self, section, item):
8185
dc10a7a3f1d4 config: split source data out into separate map
Matt Mackall <mpm@selenic.com>
parents: 8184
diff changeset
74 return self._source.get((section, item), "")
8144
fca54469480e ui: introduce new config parser
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
75 def sections(self):
fca54469480e ui: introduce new config parser
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
76 return sorted(self._data.keys())
fca54469480e ui: introduce new config parser
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
77 def items(self, section):
32318
6a773d3050c9 config: make config.items() return a copy
Martin von Zweigbergk <martinvonz@google.com>
parents: 31481
diff changeset
78 return list(self._data.get(section, {}).iteritems())
8144
fca54469480e ui: introduce new config parser
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
79 def set(self, section, item, value, source=""):
31306
c920efa9d34b config: guard against setconfig specifying unicode values on py3
Augie Fackler <raf@durin42.com>
parents: 31176
diff changeset
80 if pycompat.ispy3:
c920efa9d34b config: guard against setconfig specifying unicode values on py3
Augie Fackler <raf@durin42.com>
parents: 31176
diff changeset
81 assert not isinstance(value, str), (
c920efa9d34b config: guard against setconfig specifying unicode values on py3
Augie Fackler <raf@durin42.com>
parents: 31176
diff changeset
82 'config values may not be unicode strings on Python 3')
8144
fca54469480e ui: introduce new config parser
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
83 if section not in self:
34357
c41444a39de2 config: use copy-on-write to improve copy performance
Jun Wu <quark@fb.com>
parents: 34131
diff changeset
84 self._data[section] = util.cowsortdict()
c41444a39de2 config: use copy-on-write to improve copy performance
Jun Wu <quark@fb.com>
parents: 34131
diff changeset
85 else:
c41444a39de2 config: use copy-on-write to improve copy performance
Jun Wu <quark@fb.com>
parents: 34131
diff changeset
86 self._data[section] = self._data[section].preparewrite()
8185
dc10a7a3f1d4 config: split source data out into separate map
Matt Mackall <mpm@selenic.com>
parents: 8184
diff changeset
87 self._data[section][item] = value
20789
d19c9bdbbf35 config: don't set source when no source is specified - don't overwrite with ''
Mads Kiilerich <madski@unity3d.com>
parents: 19087
diff changeset
88 if source:
34357
c41444a39de2 config: use copy-on-write to improve copy performance
Jun Wu <quark@fb.com>
parents: 34131
diff changeset
89 self._source = self._source.preparewrite()
20789
d19c9bdbbf35 config: don't set source when no source is specified - don't overwrite with ''
Mads Kiilerich <madski@unity3d.com>
parents: 19087
diff changeset
90 self._source[(section, item)] = source
8144
fca54469480e ui: introduce new config parser
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
91
15919
69e792cf7851 config: have a way to backup and restore value in config
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents: 14696
diff changeset
92 def restore(self, data):
69e792cf7851 config: have a way to backup and restore value in config
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents: 14696
diff changeset
93 """restore data returned by self.backup"""
34357
c41444a39de2 config: use copy-on-write to improve copy performance
Jun Wu <quark@fb.com>
parents: 34131
diff changeset
94 self._source = self._source.preparewrite()
15919
69e792cf7851 config: have a way to backup and restore value in config
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents: 14696
diff changeset
95 if len(data) == 4:
69e792cf7851 config: have a way to backup and restore value in config
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents: 14696
diff changeset
96 # restore old data
69e792cf7851 config: have a way to backup and restore value in config
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents: 14696
diff changeset
97 section, item, value, source = data
34357
c41444a39de2 config: use copy-on-write to improve copy performance
Jun Wu <quark@fb.com>
parents: 34131
diff changeset
98 self._data[section] = self._data[section].preparewrite()
15919
69e792cf7851 config: have a way to backup and restore value in config
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents: 14696
diff changeset
99 self._data[section][item] = value
69e792cf7851 config: have a way to backup and restore value in config
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents: 14696
diff changeset
100 self._source[(section, item)] = source
69e792cf7851 config: have a way to backup and restore value in config
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents: 14696
diff changeset
101 else:
69e792cf7851 config: have a way to backup and restore value in config
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents: 14696
diff changeset
102 # no data before, remove everything
69e792cf7851 config: have a way to backup and restore value in config
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents: 14696
diff changeset
103 section, item = data
69e792cf7851 config: have a way to backup and restore value in config
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents: 14696
diff changeset
104 if section in self._data:
22037
8665c647da6e config: fix restoreconfig of non existing config
Pierre-Yves David <pierre-yves.david@fb.com>
parents: 21910
diff changeset
105 self._data[section].pop(item, None)
15919
69e792cf7851 config: have a way to backup and restore value in config
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents: 14696
diff changeset
106 self._source.pop((section, item), None)
69e792cf7851 config: have a way to backup and restore value in config
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents: 14696
diff changeset
107
8265
52c5be55af82 config: add parse interface
Matt Mackall <mpm@selenic.com>
parents: 8263
diff changeset
108 def parse(self, src, data, sections=None, remap=None, include=None):
30349
954002426f78 config: mark parser regexes as bytes explicitly
Augie Fackler <augie@google.com>
parents: 27696
diff changeset
109 sectionre = util.re.compile(br'\[([^\[]+)\]')
954002426f78 config: mark parser regexes as bytes explicitly
Augie Fackler <augie@google.com>
parents: 27696
diff changeset
110 itemre = util.re.compile(br'([^=\s][^=]*?)\s*=\s*(.*\S|)')
954002426f78 config: mark parser regexes as bytes explicitly
Augie Fackler <augie@google.com>
parents: 27696
diff changeset
111 contre = util.re.compile(br'\s+(\S|\S.*\S)\s*$')
954002426f78 config: mark parser regexes as bytes explicitly
Augie Fackler <augie@google.com>
parents: 27696
diff changeset
112 emptyre = util.re.compile(br'(;|#|\s*$)')
954002426f78 config: mark parser regexes as bytes explicitly
Augie Fackler <augie@google.com>
parents: 27696
diff changeset
113 commentre = util.re.compile(br'(;|#)')
954002426f78 config: mark parser regexes as bytes explicitly
Augie Fackler <augie@google.com>
parents: 27696
diff changeset
114 unsetre = util.re.compile(br'%unset\s+(\S+)')
954002426f78 config: mark parser regexes as bytes explicitly
Augie Fackler <augie@google.com>
parents: 27696
diff changeset
115 includere = util.re.compile(br'%include\s+(\S|\S.*\S)\s*$')
8144
fca54469480e ui: introduce new config parser
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
116 section = ""
fca54469480e ui: introduce new config parser
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
117 item = None
fca54469480e ui: introduce new config parser
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
118 line = 0
9339
9be91129c96e config: improve code readability
Andrey <py4fun@gmail.com>
parents: 9136
diff changeset
119 cont = False
8180
6fc30fe7f3e7 hgweb: use config.config
Matt Mackall <mpm@selenic.com>
parents: 8144
diff changeset
120
9136
31177742f54a for calls expecting bool args, pass bool instead of int
Nicolas Dumazet <nicdumz.commits@gmail.com>
parents: 8312
diff changeset
121 for l in data.splitlines(True):
8144
fca54469480e ui: introduce new config parser
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
122 line += 1
16348
f350021ee32e config: discard UTF-8 BOM if found
Matt Mackall <mpm@selenic.com>
parents: 15919
diff changeset
123 if line == 1 and l.startswith('\xef\xbb\xbf'):
f350021ee32e config: discard UTF-8 BOM if found
Matt Mackall <mpm@selenic.com>
parents: 15919
diff changeset
124 # Someone set us up the BOM
f350021ee32e config: discard UTF-8 BOM if found
Matt Mackall <mpm@selenic.com>
parents: 15919
diff changeset
125 l = l[3:]
8144
fca54469480e ui: introduce new config parser
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
126 if cont:
14642
fdcdb221a922 config: handle comment lines in continuations (issue2854)
Matt Mackall <mpm@selenic.com>
parents: 14486
diff changeset
127 if commentre.match(l):
fdcdb221a922 config: handle comment lines in continuations (issue2854)
Matt Mackall <mpm@selenic.com>
parents: 14486
diff changeset
128 continue
8144
fca54469480e ui: introduce new config parser
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
129 m = contre.match(l)
fca54469480e ui: introduce new config parser
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
130 if m:
8193
94246e90081e config: add section filter to read
Matt Mackall <mpm@selenic.com>
parents: 8192
diff changeset
131 if sections and section not in sections:
94246e90081e config: add section filter to read
Matt Mackall <mpm@selenic.com>
parents: 8192
diff changeset
132 continue
8144
fca54469480e ui: introduce new config parser
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
133 v = self.get(section, item) + "\n" + m.group(1)
8265
52c5be55af82 config: add parse interface
Matt Mackall <mpm@selenic.com>
parents: 8263
diff changeset
134 self.set(section, item, v, "%s:%d" % (src, line))
8144
fca54469480e ui: introduce new config parser
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
135 continue
fca54469480e ui: introduce new config parser
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
136 item = None
9469
7f0f882af23d config: abort on indented non-continuation lines (issue1829)
Nicolas Dumazet <nicdumz.commits@gmail.com>
parents: 8312
diff changeset
137 cont = False
8183
2858ab754995 config: allow including other config files
Matt Mackall <mpm@selenic.com>
parents: 8180
diff changeset
138 m = includere.match(l)
25095
3182965b3971 config: give it an includepaths option for looking for config files
Jordi Gutiérrez Hermoso <jordigh@octave.org>
parents: 22419
diff changeset
139
3182965b3971 config: give it an includepaths option for looking for config files
Jordi Gutiérrez Hermoso <jordigh@octave.org>
parents: 22419
diff changeset
140 if m and include:
3182965b3971 config: give it an includepaths option for looking for config files
Jordi Gutiérrez Hermoso <jordigh@octave.org>
parents: 22419
diff changeset
141 expanded = util.expandpath(m.group(1))
3182965b3971 config: give it an includepaths option for looking for config files
Jordi Gutiérrez Hermoso <jordigh@octave.org>
parents: 22419
diff changeset
142 includepaths = [os.path.dirname(src)] + self._includepaths
3182965b3971 config: give it an includepaths option for looking for config files
Jordi Gutiérrez Hermoso <jordigh@octave.org>
parents: 22419
diff changeset
143
3182965b3971 config: give it an includepaths option for looking for config files
Jordi Gutiérrez Hermoso <jordigh@octave.org>
parents: 22419
diff changeset
144 for base in includepaths:
3182965b3971 config: give it an includepaths option for looking for config files
Jordi Gutiérrez Hermoso <jordigh@octave.org>
parents: 22419
diff changeset
145 inc = os.path.normpath(os.path.join(base, expanded))
3182965b3971 config: give it an includepaths option for looking for config files
Jordi Gutiérrez Hermoso <jordigh@octave.org>
parents: 22419
diff changeset
146
10042
7cdd2a7db2c2 config: raise ConfigError on non-existing include files
Martin Geisler <mg@lazybytes.net>
parents: 9471
diff changeset
147 try:
7cdd2a7db2c2 config: raise ConfigError on non-existing include files
Martin Geisler <mg@lazybytes.net>
parents: 9471
diff changeset
148 include(inc, remap=remap, sections=sections)
25095
3182965b3971 config: give it an includepaths option for looking for config files
Jordi Gutiérrez Hermoso <jordigh@octave.org>
parents: 22419
diff changeset
149 break
25660
328739ea70c3 global: mass rewrite to use modern exception syntax
Gregory Szorc <gregory.szorc@gmail.com>
parents: 25095
diff changeset
150 except IOError as inst:
14486
4e3eda05189b config: ignore include errors for nonexistent files
Matt Mackall <mpm@selenic.com>
parents: 13664
diff changeset
151 if inst.errno != errno.ENOENT:
4e3eda05189b config: ignore include errors for nonexistent files
Matt Mackall <mpm@selenic.com>
parents: 13664
diff changeset
152 raise error.ParseError(_("cannot include %s (%s)")
4e3eda05189b config: ignore include errors for nonexistent files
Matt Mackall <mpm@selenic.com>
parents: 13664
diff changeset
153 % (inc, inst.strerror),
4e3eda05189b config: ignore include errors for nonexistent files
Matt Mackall <mpm@selenic.com>
parents: 13664
diff changeset
154 "%s:%s" % (src, line))
8183
2858ab754995 config: allow including other config files
Matt Mackall <mpm@selenic.com>
parents: 8180
diff changeset
155 continue
8144
fca54469480e ui: introduce new config parser
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
156 if emptyre.match(l):
fca54469480e ui: introduce new config parser
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
157 continue
fca54469480e ui: introduce new config parser
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
158 m = sectionre.match(l)
fca54469480e ui: introduce new config parser
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
159 if m:
fca54469480e ui: introduce new config parser
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
160 section = m.group(1)
8298
9542f4c3fa1b config: make remap actually work
Matt Mackall <mpm@selenic.com>
parents: 8265
diff changeset
161 if remap:
9542f4c3fa1b config: make remap actually work
Matt Mackall <mpm@selenic.com>
parents: 8265
diff changeset
162 section = remap.get(section, section)
8144
fca54469480e ui: introduce new config parser
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
163 if section not in self:
34357
c41444a39de2 config: use copy-on-write to improve copy performance
Jun Wu <quark@fb.com>
parents: 34131
diff changeset
164 self._data[section] = util.cowsortdict()
8144
fca54469480e ui: introduce new config parser
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
165 continue
fca54469480e ui: introduce new config parser
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
166 m = itemre.match(l)
fca54469480e ui: introduce new config parser
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
167 if m:
fca54469480e ui: introduce new config parser
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
168 item = m.group(1)
9339
9be91129c96e config: improve code readability
Andrey <py4fun@gmail.com>
parents: 9136
diff changeset
169 cont = True
8193
94246e90081e config: add section filter to read
Matt Mackall <mpm@selenic.com>
parents: 8192
diff changeset
170 if sections and section not in sections:
94246e90081e config: add section filter to read
Matt Mackall <mpm@selenic.com>
parents: 8192
diff changeset
171 continue
8265
52c5be55af82 config: add parse interface
Matt Mackall <mpm@selenic.com>
parents: 8263
diff changeset
172 self.set(section, item, m.group(2), "%s:%d" % (src, line))
8144
fca54469480e ui: introduce new config parser
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
173 continue
8184
9189afe1eba3 config: add %unset name support
Matt Mackall <mpm@selenic.com>
parents: 8183
diff changeset
174 m = unsetre.match(l)
9189afe1eba3 config: add %unset name support
Matt Mackall <mpm@selenic.com>
parents: 8183
diff changeset
175 if m:
9189afe1eba3 config: add %unset name support
Matt Mackall <mpm@selenic.com>
parents: 8183
diff changeset
176 name = m.group(1)
8193
94246e90081e config: add section filter to read
Matt Mackall <mpm@selenic.com>
parents: 8192
diff changeset
177 if sections and section not in sections:
94246e90081e config: add section filter to read
Matt Mackall <mpm@selenic.com>
parents: 8192
diff changeset
178 continue
13031
3da456d0c885 code style: prefer 'is' and 'is not' tests with singletons
Martin Geisler <mg@aragost.com>
parents: 11292
diff changeset
179 if self.get(section, name) is not None:
8184
9189afe1eba3 config: add %unset name support
Matt Mackall <mpm@selenic.com>
parents: 8183
diff changeset
180 del self._data[section][name]
19087
7d82ad4b3727 config: discard "%unset" values defined in the other files read in previously
FUJIWARA Katsunori <foozy@lares.dti.ne.jp>
parents: 17537
diff changeset
181 self._unset.append((section, name))
8184
9189afe1eba3 config: add %unset name support
Matt Mackall <mpm@selenic.com>
parents: 8183
diff changeset
182 continue
9189afe1eba3 config: add %unset name support
Matt Mackall <mpm@selenic.com>
parents: 8183
diff changeset
183
11288
2123aad24d56 error: add new ParseError for various parsing errors
Matt Mackall <mpm@selenic.com>
parents: 11224
diff changeset
184 raise error.ParseError(l.rstrip(), ("%s:%s" % (src, line)))
8265
52c5be55af82 config: add parse interface
Matt Mackall <mpm@selenic.com>
parents: 8263
diff changeset
185
52c5be55af82 config: add parse interface
Matt Mackall <mpm@selenic.com>
parents: 8263
diff changeset
186 def read(self, path, fp=None, sections=None, remap=None):
52c5be55af82 config: add parse interface
Matt Mackall <mpm@selenic.com>
parents: 8263
diff changeset
187 if not fp:
31154
fd3f4bf9325e config: load included config files in binary mode
Augie Fackler <raf@durin42.com>
parents: 30349
diff changeset
188 fp = util.posixfile(path, 'rb')
31176
99c5843b228d config: add sanity assert that files are opened as binary
Augie Fackler <raf@durin42.com>
parents: 31155
diff changeset
189 assert getattr(fp, 'mode', r'rb') == r'rb', (
99c5843b228d config: add sanity assert that files are opened as binary
Augie Fackler <raf@durin42.com>
parents: 31155
diff changeset
190 'config files must be opened in binary mode, got fp=%r mode=%r' % (
99c5843b228d config: add sanity assert that files are opened as binary
Augie Fackler <raf@durin42.com>
parents: 31155
diff changeset
191 fp, fp.mode))
31155
8266802f0fa4 config: pass some optional args as keywords
Augie Fackler <raf@durin42.com>
parents: 31154
diff changeset
192 self.parse(path, fp.read(),
8266802f0fa4 config: pass some optional args as keywords
Augie Fackler <raf@durin42.com>
parents: 31154
diff changeset
193 sections=sections, remap=remap, include=self.read)
31481
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
194
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
195 def parselist(value):
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
196 """parse a configuration value as a list of comma/space separated strings
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
197
34131
0fa781320203 doctest: bulk-replace string literals with b'' for Python 3
Yuya Nishihara <yuya@tcha.org>
parents: 32318
diff changeset
198 >>> parselist(b'this,is "a small" ,test')
31481
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
199 ['this', 'is', 'a small', 'test']
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
200 """
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
201
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
202 def _parse_plain(parts, s, offset):
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
203 whitespace = False
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
204 while offset < len(s) and (s[offset:offset + 1].isspace()
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
205 or s[offset:offset + 1] == ','):
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
206 whitespace = True
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
207 offset += 1
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
208 if offset >= len(s):
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
209 return None, parts, offset
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
210 if whitespace:
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
211 parts.append('')
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
212 if s[offset:offset + 1] == '"' and not parts[-1]:
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
213 return _parse_quote, parts, offset + 1
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
214 elif s[offset:offset + 1] == '"' and parts[-1][-1] == '\\':
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
215 parts[-1] = parts[-1][:-1] + s[offset:offset + 1]
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
216 return _parse_plain, parts, offset + 1
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
217 parts[-1] += s[offset:offset + 1]
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
218 return _parse_plain, parts, offset + 1
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
219
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
220 def _parse_quote(parts, s, offset):
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
221 if offset < len(s) and s[offset:offset + 1] == '"': # ""
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
222 parts.append('')
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
223 offset += 1
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
224 while offset < len(s) and (s[offset:offset + 1].isspace() or
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
225 s[offset:offset + 1] == ','):
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
226 offset += 1
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
227 return _parse_plain, parts, offset
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
228
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
229 while offset < len(s) and s[offset:offset + 1] != '"':
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
230 if (s[offset:offset + 1] == '\\' and offset + 1 < len(s)
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
231 and s[offset + 1:offset + 2] == '"'):
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
232 offset += 1
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
233 parts[-1] += '"'
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
234 else:
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
235 parts[-1] += s[offset:offset + 1]
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
236 offset += 1
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
237
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
238 if offset >= len(s):
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
239 real_parts = _configlist(parts[-1])
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
240 if not real_parts:
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
241 parts[-1] = '"'
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
242 else:
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
243 real_parts[0] = '"' + real_parts[0]
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
244 parts = parts[:-1]
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
245 parts.extend(real_parts)
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
246 return None, parts, offset
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
247
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
248 offset += 1
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
249 while offset < len(s) and s[offset:offset + 1] in [' ', ',']:
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
250 offset += 1
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
251
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
252 if offset < len(s):
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
253 if offset + 1 == len(s) and s[offset:offset + 1] == '"':
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
254 parts[-1] += '"'
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
255 offset += 1
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
256 else:
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
257 parts.append('')
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
258 else:
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
259 return None, parts, offset
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
260
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
261 return _parse_plain, parts, offset
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
262
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
263 def _configlist(s):
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
264 s = s.rstrip(' ,')
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
265 if not s:
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
266 return []
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
267 parser, parts, offset = _parse_plain, [''], 0
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
268 while parser:
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
269 parser, parts, offset = parser(parts, s, offset)
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
270 return parts
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
271
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
272 if value is not None and isinstance(value, bytes):
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
273 result = _configlist(value.lstrip(' ,\n'))
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
274 else:
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
275 result = value
a7c687c35119 ui: move configlist parser to config.py
Jun Wu <quark@fb.com>
parents: 31374
diff changeset
276 return result or []