Mercurial > repos > guerler > hhblits
comparison lib/python3.8/site-packages/pip/_vendor/pytoml/parser.py @ 0:9e54283cc701 draft
"planemo upload commit d12c32a45bcd441307e632fca6d9af7d60289d44"
author | guerler |
---|---|
date | Mon, 27 Jul 2020 03:47:31 -0400 |
parents | |
children |
comparison
equal
deleted
inserted
replaced
-1:000000000000 | 0:9e54283cc701 |
---|---|
1 import re, sys | |
2 from .core import TomlError | |
3 from .utils import rfc3339_re, parse_rfc3339_re | |
4 | |
5 if sys.version_info[0] == 2: | |
6 _chr = unichr | |
7 else: | |
8 _chr = chr | |
9 | |
10 def load(fin, translate=lambda t, x, v: v, object_pairs_hook=dict): | |
11 return loads(fin.read(), translate=translate, object_pairs_hook=object_pairs_hook, filename=getattr(fin, 'name', repr(fin))) | |
12 | |
13 def loads(s, filename='<string>', translate=lambda t, x, v: v, object_pairs_hook=dict): | |
14 if isinstance(s, bytes): | |
15 s = s.decode('utf-8') | |
16 | |
17 s = s.replace('\r\n', '\n') | |
18 | |
19 root = object_pairs_hook() | |
20 tables = object_pairs_hook() | |
21 scope = root | |
22 | |
23 src = _Source(s, filename=filename) | |
24 ast = _p_toml(src, object_pairs_hook=object_pairs_hook) | |
25 | |
26 def error(msg): | |
27 raise TomlError(msg, pos[0], pos[1], filename) | |
28 | |
29 def process_value(v, object_pairs_hook): | |
30 kind, text, value, pos = v | |
31 if kind == 'array': | |
32 if value and any(k != value[0][0] for k, t, v, p in value[1:]): | |
33 error('array-type-mismatch') | |
34 value = [process_value(item, object_pairs_hook=object_pairs_hook) for item in value] | |
35 elif kind == 'table': | |
36 value = object_pairs_hook([(k, process_value(value[k], object_pairs_hook=object_pairs_hook)) for k in value]) | |
37 return translate(kind, text, value) | |
38 | |
39 for kind, value, pos in ast: | |
40 if kind == 'kv': | |
41 k, v = value | |
42 if k in scope: | |
43 error('duplicate_keys. Key "{0}" was used more than once.'.format(k)) | |
44 scope[k] = process_value(v, object_pairs_hook=object_pairs_hook) | |
45 else: | |
46 is_table_array = (kind == 'table_array') | |
47 cur = tables | |
48 for name in value[:-1]: | |
49 if isinstance(cur.get(name), list): | |
50 d, cur = cur[name][-1] | |
51 else: | |
52 d, cur = cur.setdefault(name, (None, object_pairs_hook())) | |
53 | |
54 scope = object_pairs_hook() | |
55 name = value[-1] | |
56 if name not in cur: | |
57 if is_table_array: | |
58 cur[name] = [(scope, object_pairs_hook())] | |
59 else: | |
60 cur[name] = (scope, object_pairs_hook()) | |
61 elif isinstance(cur[name], list): | |
62 if not is_table_array: | |
63 error('table_type_mismatch') | |
64 cur[name].append((scope, object_pairs_hook())) | |
65 else: | |
66 if is_table_array: | |
67 error('table_type_mismatch') | |
68 old_scope, next_table = cur[name] | |
69 if old_scope is not None: | |
70 error('duplicate_tables') | |
71 cur[name] = (scope, next_table) | |
72 | |
73 def merge_tables(scope, tables): | |
74 if scope is None: | |
75 scope = object_pairs_hook() | |
76 for k in tables: | |
77 if k in scope: | |
78 error('key_table_conflict') | |
79 v = tables[k] | |
80 if isinstance(v, list): | |
81 scope[k] = [merge_tables(sc, tbl) for sc, tbl in v] | |
82 else: | |
83 scope[k] = merge_tables(v[0], v[1]) | |
84 return scope | |
85 | |
86 return merge_tables(root, tables) | |
87 | |
88 class _Source: | |
89 def __init__(self, s, filename=None): | |
90 self.s = s | |
91 self._pos = (1, 1) | |
92 self._last = None | |
93 self._filename = filename | |
94 self.backtrack_stack = [] | |
95 | |
96 def last(self): | |
97 return self._last | |
98 | |
99 def pos(self): | |
100 return self._pos | |
101 | |
102 def fail(self): | |
103 return self._expect(None) | |
104 | |
105 def consume_dot(self): | |
106 if self.s: | |
107 self._last = self.s[0] | |
108 self.s = self[1:] | |
109 self._advance(self._last) | |
110 return self._last | |
111 return None | |
112 | |
113 def expect_dot(self): | |
114 return self._expect(self.consume_dot()) | |
115 | |
116 def consume_eof(self): | |
117 if not self.s: | |
118 self._last = '' | |
119 return True | |
120 return False | |
121 | |
122 def expect_eof(self): | |
123 return self._expect(self.consume_eof()) | |
124 | |
125 def consume(self, s): | |
126 if self.s.startswith(s): | |
127 self.s = self.s[len(s):] | |
128 self._last = s | |
129 self._advance(s) | |
130 return True | |
131 return False | |
132 | |
133 def expect(self, s): | |
134 return self._expect(self.consume(s)) | |
135 | |
136 def consume_re(self, re): | |
137 m = re.match(self.s) | |
138 if m: | |
139 self.s = self.s[len(m.group(0)):] | |
140 self._last = m | |
141 self._advance(m.group(0)) | |
142 return m | |
143 return None | |
144 | |
145 def expect_re(self, re): | |
146 return self._expect(self.consume_re(re)) | |
147 | |
148 def __enter__(self): | |
149 self.backtrack_stack.append((self.s, self._pos)) | |
150 | |
151 def __exit__(self, type, value, traceback): | |
152 if type is None: | |
153 self.backtrack_stack.pop() | |
154 else: | |
155 self.s, self._pos = self.backtrack_stack.pop() | |
156 return type == TomlError | |
157 | |
158 def commit(self): | |
159 self.backtrack_stack[-1] = (self.s, self._pos) | |
160 | |
161 def _expect(self, r): | |
162 if not r: | |
163 raise TomlError('msg', self._pos[0], self._pos[1], self._filename) | |
164 return r | |
165 | |
166 def _advance(self, s): | |
167 suffix_pos = s.rfind('\n') | |
168 if suffix_pos == -1: | |
169 self._pos = (self._pos[0], self._pos[1] + len(s)) | |
170 else: | |
171 self._pos = (self._pos[0] + s.count('\n'), len(s) - suffix_pos) | |
172 | |
173 _ews_re = re.compile(r'(?:[ \t]|#[^\n]*\n|#[^\n]*\Z|\n)*') | |
174 def _p_ews(s): | |
175 s.expect_re(_ews_re) | |
176 | |
177 _ws_re = re.compile(r'[ \t]*') | |
178 def _p_ws(s): | |
179 s.expect_re(_ws_re) | |
180 | |
181 _escapes = { 'b': '\b', 'n': '\n', 'r': '\r', 't': '\t', '"': '"', | |
182 '\\': '\\', 'f': '\f' } | |
183 | |
184 _basicstr_re = re.compile(r'[^"\\\000-\037]*') | |
185 _short_uni_re = re.compile(r'u([0-9a-fA-F]{4})') | |
186 _long_uni_re = re.compile(r'U([0-9a-fA-F]{8})') | |
187 _escapes_re = re.compile(r'[btnfr\"\\]') | |
188 _newline_esc_re = re.compile('\n[ \t\n]*') | |
189 def _p_basicstr_content(s, content=_basicstr_re): | |
190 res = [] | |
191 while True: | |
192 res.append(s.expect_re(content).group(0)) | |
193 if not s.consume('\\'): | |
194 break | |
195 if s.consume_re(_newline_esc_re): | |
196 pass | |
197 elif s.consume_re(_short_uni_re) or s.consume_re(_long_uni_re): | |
198 v = int(s.last().group(1), 16) | |
199 if 0xd800 <= v < 0xe000: | |
200 s.fail() | |
201 res.append(_chr(v)) | |
202 else: | |
203 s.expect_re(_escapes_re) | |
204 res.append(_escapes[s.last().group(0)]) | |
205 return ''.join(res) | |
206 | |
207 _key_re = re.compile(r'[0-9a-zA-Z-_]+') | |
208 def _p_key(s): | |
209 with s: | |
210 s.expect('"') | |
211 r = _p_basicstr_content(s, _basicstr_re) | |
212 s.expect('"') | |
213 return r | |
214 if s.consume('\''): | |
215 if s.consume('\'\''): | |
216 s.consume('\n') | |
217 r = s.expect_re(_litstr_ml_re).group(0) | |
218 s.expect('\'\'\'') | |
219 else: | |
220 r = s.expect_re(_litstr_re).group(0) | |
221 s.expect('\'') | |
222 return r | |
223 return s.expect_re(_key_re).group(0) | |
224 | |
225 _float_re = re.compile(r'[+-]?(?:0|[1-9](?:_?\d)*)(?:\.\d(?:_?\d)*)?(?:[eE][+-]?(?:\d(?:_?\d)*))?') | |
226 | |
227 _basicstr_ml_re = re.compile(r'(?:""?(?!")|[^"\\\000-\011\013-\037])*') | |
228 _litstr_re = re.compile(r"[^'\000\010\012-\037]*") | |
229 _litstr_ml_re = re.compile(r"(?:(?:|'|'')(?:[^'\000-\010\013-\037]))*") | |
230 def _p_value(s, object_pairs_hook): | |
231 pos = s.pos() | |
232 | |
233 if s.consume('true'): | |
234 return 'bool', s.last(), True, pos | |
235 if s.consume('false'): | |
236 return 'bool', s.last(), False, pos | |
237 | |
238 if s.consume('"'): | |
239 if s.consume('""'): | |
240 s.consume('\n') | |
241 r = _p_basicstr_content(s, _basicstr_ml_re) | |
242 s.expect('"""') | |
243 else: | |
244 r = _p_basicstr_content(s, _basicstr_re) | |
245 s.expect('"') | |
246 return 'str', r, r, pos | |
247 | |
248 if s.consume('\''): | |
249 if s.consume('\'\''): | |
250 s.consume('\n') | |
251 r = s.expect_re(_litstr_ml_re).group(0) | |
252 s.expect('\'\'\'') | |
253 else: | |
254 r = s.expect_re(_litstr_re).group(0) | |
255 s.expect('\'') | |
256 return 'str', r, r, pos | |
257 | |
258 if s.consume_re(rfc3339_re): | |
259 m = s.last() | |
260 return 'datetime', m.group(0), parse_rfc3339_re(m), pos | |
261 | |
262 if s.consume_re(_float_re): | |
263 m = s.last().group(0) | |
264 r = m.replace('_','') | |
265 if '.' in m or 'e' in m or 'E' in m: | |
266 return 'float', m, float(r), pos | |
267 else: | |
268 return 'int', m, int(r, 10), pos | |
269 | |
270 if s.consume('['): | |
271 items = [] | |
272 with s: | |
273 while True: | |
274 _p_ews(s) | |
275 items.append(_p_value(s, object_pairs_hook=object_pairs_hook)) | |
276 s.commit() | |
277 _p_ews(s) | |
278 s.expect(',') | |
279 s.commit() | |
280 _p_ews(s) | |
281 s.expect(']') | |
282 return 'array', None, items, pos | |
283 | |
284 if s.consume('{'): | |
285 _p_ws(s) | |
286 items = object_pairs_hook() | |
287 if not s.consume('}'): | |
288 k = _p_key(s) | |
289 _p_ws(s) | |
290 s.expect('=') | |
291 _p_ws(s) | |
292 items[k] = _p_value(s, object_pairs_hook=object_pairs_hook) | |
293 _p_ws(s) | |
294 while s.consume(','): | |
295 _p_ws(s) | |
296 k = _p_key(s) | |
297 _p_ws(s) | |
298 s.expect('=') | |
299 _p_ws(s) | |
300 items[k] = _p_value(s, object_pairs_hook=object_pairs_hook) | |
301 _p_ws(s) | |
302 s.expect('}') | |
303 return 'table', None, items, pos | |
304 | |
305 s.fail() | |
306 | |
307 def _p_stmt(s, object_pairs_hook): | |
308 pos = s.pos() | |
309 if s.consume( '['): | |
310 is_array = s.consume('[') | |
311 _p_ws(s) | |
312 keys = [_p_key(s)] | |
313 _p_ws(s) | |
314 while s.consume('.'): | |
315 _p_ws(s) | |
316 keys.append(_p_key(s)) | |
317 _p_ws(s) | |
318 s.expect(']') | |
319 if is_array: | |
320 s.expect(']') | |
321 return 'table_array' if is_array else 'table', keys, pos | |
322 | |
323 key = _p_key(s) | |
324 _p_ws(s) | |
325 s.expect('=') | |
326 _p_ws(s) | |
327 value = _p_value(s, object_pairs_hook=object_pairs_hook) | |
328 return 'kv', (key, value), pos | |
329 | |
330 _stmtsep_re = re.compile(r'(?:[ \t]*(?:#[^\n]*)?\n)+[ \t]*') | |
331 def _p_toml(s, object_pairs_hook): | |
332 stmts = [] | |
333 _p_ews(s) | |
334 with s: | |
335 stmts.append(_p_stmt(s, object_pairs_hook=object_pairs_hook)) | |
336 while True: | |
337 s.commit() | |
338 s.expect_re(_stmtsep_re) | |
339 stmts.append(_p_stmt(s, object_pairs_hook=object_pairs_hook)) | |
340 _p_ews(s) | |
341 s.expect_eof() | |
342 return stmts |