remove pyyaml2 (#18404)
Ilya Mashchenko committed
Aug 24, 2024 at 20:14 UTC
313f18b7e381952d93fe8b37a68ec77227ea7ba6
19 files changed
+2
-5855
.codacy.yml
-1
@@ -1,6 +1,5 @@
1
---
2
exclude_paths:
3
- - src/collectors/python.d.plugin/python_modules/pyyaml2/**
3
- src/collectors/python.d.plugin/python_modules/pyyaml3/**
4
- src/collectors/python.d.plugin/python_modules/urllib3/**
5
- src/collectors/python.d.plugin/python_modules/third_party/**
src/collectors/python.d.plugin/python_modules/bases/loaders.py
+2
-12
@@ -3,27 +3,17 @@
3
# Author: Ilya Mashchenko (ilyam8)
4
# SPDX-License-Identifier: GPL-3.0-or-later
5
6
-
7
-from sys import version_info
8
-
9
-PY_VERSION = version_info[:2]
10
-
6
try:
12
- if PY_VERSION > (3, 1):
13
- from pyyaml3 import SafeLoader as YamlSafeLoader
14
- else:
15
- from pyyaml2 import SafeLoader as YamlSafeLoader
7
+ from pyyaml3 import SafeLoader as YamlSafeLoader
8
except ImportError:
9
from yaml import SafeLoader as YamlSafeLoader
10
19
-
11
try:
12
from collections import OrderedDict
13
except ImportError:
14
from third_party.ordereddict import OrderedDict
15
25
-
26
-DEFAULT_MAPPING_TAG = 'tag:yaml.org,2002:map' if PY_VERSION > (3, 1) else u'tag:yaml.org,2002:map'
16
+DEFAULT_MAPPING_TAG = 'tag:yaml.org,2002:map'
17
18
19
def dict_constructor(loader, node):
src/collectors/python.d.plugin/python_modules/pyyaml2/__init__.py
deleted
-316
@@ -1,316 +0,0 @@
1
-# SPDX-License-Identifier: MIT
2
-
3
-from error import *
4
-
5
-from tokens import *
6
-from events import *
7
-from nodes import *
8
-
9
-from loader import *
10
-from dumper import *
11
-
12
-__version__ = '3.11'
13
-
14
-try:
15
- from cyaml import *
16
- __with_libyaml__ = True
17
-except ImportError:
18
- __with_libyaml__ = False
19
-
20
-def scan(stream, Loader=Loader):
21
- """
22
- Scan a YAML stream and produce scanning tokens.
23
- """
24
- loader = Loader(stream)
25
- try:
26
- while loader.check_token():
27
- yield loader.get_token()
28
- finally:
29
- loader.dispose()
30
-
31
-def parse(stream, Loader=Loader):
32
- """
33
- Parse a YAML stream and produce parsing events.
34
- """
35
- loader = Loader(stream)
36
- try:
37
- while loader.check_event():
38
- yield loader.get_event()
39
- finally:
40
- loader.dispose()
41
-
42
-def compose(stream, Loader=Loader):
43
- """
44
- Parse the first YAML document in a stream
45
- and produce the corresponding representation tree.
46
- """
47
- loader = Loader(stream)
48
- try:
49
- return loader.get_single_node()
50
- finally:
51
- loader.dispose()
52
-
53
-def compose_all(stream, Loader=Loader):
54
- """
55
- Parse all YAML documents in a stream
56
- and produce corresponding representation trees.
57
- """
58
- loader = Loader(stream)
59
- try:
60
- while loader.check_node():
61
- yield loader.get_node()
62
- finally:
63
- loader.dispose()
64
-
65
-def load(stream, Loader=Loader):
66
- """
67
- Parse the first YAML document in a stream
68
- and produce the corresponding Python object.
69
- """
70
- loader = Loader(stream)
71
- try:
72
- return loader.get_single_data()
73
- finally:
74
- loader.dispose()
75
-
76
-def load_all(stream, Loader=Loader):
77
- """
78
- Parse all YAML documents in a stream
79
- and produce corresponding Python objects.
80
- """
81
- loader = Loader(stream)
82
- try:
83
- while loader.check_data():
84
- yield loader.get_data()
85
- finally:
86
- loader.dispose()
87
-
88
-def safe_load(stream):
89
- """
90
- Parse the first YAML document in a stream
91
- and produce the corresponding Python object.
92
- Resolve only basic YAML tags.
93
- """
94
- return load(stream, SafeLoader)
95
-
96
-def safe_load_all(stream):
97
- """
98
- Parse all YAML documents in a stream
99
- and produce corresponding Python objects.
100
- Resolve only basic YAML tags.
101
- """
102
- return load_all(stream, SafeLoader)
103
-
104
-def emit(events, stream=None, Dumper=Dumper,
105
- canonical=None, indent=None, width=None,
106
- allow_unicode=None, line_break=None):
107
- """
108
- Emit YAML parsing events into a stream.
109
- If stream is None, return the produced string instead.
110
- """
111
- getvalue = None
112
- if stream is None:
113
- from StringIO import StringIO
114
- stream = StringIO()
115
- getvalue = stream.getvalue
116
- dumper = Dumper(stream, canonical=canonical, indent=indent, width=width,
117
- allow_unicode=allow_unicode, line_break=line_break)
118
- try:
119
- for event in events:
120
- dumper.emit(event)
121
- finally:
122
- dumper.dispose()
123
- if getvalue:
124
- return getvalue()
125
-
126
-def serialize_all(nodes, stream=None, Dumper=Dumper,
127
- canonical=None, indent=None, width=None,
128
- allow_unicode=None, line_break=None,
129
- encoding='utf-8', explicit_start=None, explicit_end=None,
130
- version=None, tags=None):
131
- """
132
- Serialize a sequence of representation trees into a YAML stream.
133
- If stream is None, return the produced string instead.
134
- """
135
- getvalue = None
136
- if stream is None:
137
- if encoding is None:
138
- from StringIO import StringIO
139
- else:
140
- from cStringIO import StringIO
141
- stream = StringIO()
142
- getvalue = stream.getvalue
143
- dumper = Dumper(stream, canonical=canonical, indent=indent, width=width,
144
- allow_unicode=allow_unicode, line_break=line_break,
145
- encoding=encoding, version=version, tags=tags,
146
- explicit_start=explicit_start, explicit_end=explicit_end)
147
- try:
148
- dumper.open()
149
- for node in nodes:
150
- dumper.serialize(node)
151
- dumper.close()
152
- finally:
153
- dumper.dispose()
154
- if getvalue:
155
- return getvalue()
156
-
157
-def serialize(node, stream=None, Dumper=Dumper, **kwds):
158
- """
159
- Serialize a representation tree into a YAML stream.
160
- If stream is None, return the produced string instead.
161
- """
162
- return serialize_all([node], stream, Dumper=Dumper, **kwds)
163
-
164
-def dump_all(documents, stream=None, Dumper=Dumper,
165
- default_style=None, default_flow_style=None,
166
- canonical=None, indent=None, width=None,
167
- allow_unicode=None, line_break=None,
168
- encoding='utf-8', explicit_start=None, explicit_end=None,
169
- version=None, tags=None):
170
- """
171
- Serialize a sequence of Python objects into a YAML stream.
172
- If stream is None, return the produced string instead.
173
- """
174
- getvalue = None
175
- if stream is None:
176
- if encoding is None:
177
- from StringIO import StringIO
178
- else:
179
- from cStringIO import StringIO
180
- stream = StringIO()
181
- getvalue = stream.getvalue
182
- dumper = Dumper(stream, default_style=default_style,
183
- default_flow_style=default_flow_style,
184
- canonical=canonical, indent=indent, width=width,
185
- allow_unicode=allow_unicode, line_break=line_break,
186
- encoding=encoding, version=version, tags=tags,
187
- explicit_start=explicit_start, explicit_end=explicit_end)
188
- try:
189
- dumper.open()
190
- for data in documents:
191
- dumper.represent(data)
192
- dumper.close()
193
- finally:
194
- dumper.dispose()
195
- if getvalue:
196
- return getvalue()
197
-
198
-def dump(data, stream=None, Dumper=Dumper, **kwds):
199
- """
200
- Serialize a Python object into a YAML stream.
201
- If stream is None, return the produced string instead.
202
- """
203
- return dump_all([data], stream, Dumper=Dumper, **kwds)
204
-
205
-def safe_dump_all(documents, stream=None, **kwds):
206
- """
207
- Serialize a sequence of Python objects into a YAML stream.
208
- Produce only basic YAML tags.
209
- If stream is None, return the produced string instead.
210
- """
211
- return dump_all(documents, stream, Dumper=SafeDumper, **kwds)
212
-
213
-def safe_dump(data, stream=None, **kwds):
214
- """
215
- Serialize a Python object into a YAML stream.
216
- Produce only basic YAML tags.
217
- If stream is None, return the produced string instead.
218
- """
219
- return dump_all([data], stream, Dumper=SafeDumper, **kwds)
220
-
221
-def add_implicit_resolver(tag, regexp, first=None,
222
- Loader=Loader, Dumper=Dumper):
223
- """
224
- Add an implicit scalar detector.
225
- If an implicit scalar value matches the given regexp,
226
- the corresponding tag is assigned to the scalar.
227
- first is a sequence of possible initial characters or None.
228
- """
229
- Loader.add_implicit_resolver(tag, regexp, first)
230
- Dumper.add_implicit_resolver(tag, regexp, first)
231
-
232
-def add_path_resolver(tag, path, kind=None, Loader=Loader, Dumper=Dumper):
233
- """
234
- Add a path based resolver for the given tag.
235
- A path is a list of keys that forms a path
236
- to a node in the representation tree.
237
- Keys can be string values, integers, or None.
238
- """
239
- Loader.add_path_resolver(tag, path, kind)
240
- Dumper.add_path_resolver(tag, path, kind)
241
-
242
-def add_constructor(tag, constructor, Loader=Loader):
243
- """
244
- Add a constructor for the given tag.
245
- Constructor is a function that accepts a Loader instance
246
- and a node object and produces the corresponding Python object.
247
- """
248
- Loader.add_constructor(tag, constructor)
249
-
250
-def add_multi_constructor(tag_prefix, multi_constructor, Loader=Loader):
251
- """
252
- Add a multi-constructor for the given tag prefix.
253
- Multi-constructor is called for a node if its tag starts with tag_prefix.
254
- Multi-constructor accepts a Loader instance, a tag suffix,
255
- and a node object and produces the corresponding Python object.
256
- """
257
- Loader.add_multi_constructor(tag_prefix, multi_constructor)
258
-
259
-def add_representer(data_type, representer, Dumper=Dumper):
260
- """
261
- Add a representer for the given type.
262
- Representer is a function accepting a Dumper instance
263
- and an instance of the given data type
264
- and producing the corresponding representation node.
265
- """
266
- Dumper.add_representer(data_type, representer)
267
-
268
-def add_multi_representer(data_type, multi_representer, Dumper=Dumper):
269
- """
270
- Add a representer for the given type.
271
- Multi-representer is a function accepting a Dumper instance
272
- and an instance of the given data type or subtype
273
- and producing the corresponding representation node.
274
- """
275
- Dumper.add_multi_representer(data_type, multi_representer)
276
-
277
-class YAMLObjectMetaclass(type):
278
- """
279
- The metaclass for YAMLObject.
280
- """
281
- def __init__(cls, name, bases, kwds):
282
- super(YAMLObjectMetaclass, cls).__init__(name, bases, kwds)
283
- if 'yaml_tag' in kwds and kwds['yaml_tag'] is not None:
284
- cls.yaml_loader.add_constructor(cls.yaml_tag, cls.from_yaml)
285
- cls.yaml_dumper.add_representer(cls, cls.to_yaml)
286
-
287
-class YAMLObject(object):
288
- """
289
- An object that can dump itself to a YAML stream
290
- and load itself from a YAML stream.
291
- """
292
-
293
- __metaclass__ = YAMLObjectMetaclass
294
- __slots__ = () # no direct instantiation, so allow immutable subclasses
295
-
296
- yaml_loader = Loader
297
- yaml_dumper = Dumper
298
-
299
- yaml_tag = None
300
- yaml_flow_style = None
301
-
302
- def from_yaml(cls, loader, node):
303
- """
304
- Convert a representation node to a Python object.
305
- """
306
- return loader.construct_yaml_object(node, cls)
307
- from_yaml = classmethod(from_yaml)
308
-
309
- def to_yaml(cls, dumper, data):
310
- """
311
- Convert a Python object to a representation node.
312
- """
313
- return dumper.represent_yaml_object(cls.yaml_tag, data, cls,
314
- flow_style=cls.yaml_flow_style)
315
- to_yaml = classmethod(to_yaml)
316
-
src/collectors/python.d.plugin/python_modules/pyyaml2/composer.py
deleted
-140
@@ -1,140 +0,0 @@
1
-# SPDX-License-Identifier: MIT
2
-
3
-__all__ = ['Composer', 'ComposerError']
4
-
5
-from error import MarkedYAMLError
6
-from events import *
7
-from nodes import *
8
-
9
-class ComposerError(MarkedYAMLError):
10
- pass
11
-
12
-class Composer(object):
13
-
14
- def __init__(self):
15
- self.anchors = {}
16
-
17
- def check_node(self):
18
- # Drop the STREAM-START event.
19
- if self.check_event(StreamStartEvent):
20
- self.get_event()
21
-
22
- # If there are more documents available?
23
- return not self.check_event(StreamEndEvent)
24
-
25
- def get_node(self):
26
- # Get the root node of the next document.
27
- if not self.check_event(StreamEndEvent):
28
- return self.compose_document()
29
-
30
- def get_single_node(self):
31
- # Drop the STREAM-START event.
32
- self.get_event()
33
-
34
- # Compose a document if the stream is not empty.
35
- document = None
36
- if not self.check_event(StreamEndEvent):
37
- document = self.compose_document()
38
-
39
- # Ensure that the stream contains no more documents.
40
- if not self.check_event(StreamEndEvent):
41
- event = self.get_event()
42
- raise ComposerError("expected a single document in the stream",
43
- document.start_mark, "but found another document",
44
- event.start_mark)
45
-
46
- # Drop the STREAM-END event.
47
- self.get_event()
48
-
49
- return document
50
-
51
- def compose_document(self):
52
- # Drop the DOCUMENT-START event.
53
- self.get_event()
54
-
55
- # Compose the root node.
56
- node = self.compose_node(None, None)
57
-
58
- # Drop the DOCUMENT-END event.
59
- self.get_event()
60
-
61
- self.anchors = {}
62
- return node
63
-
64
- def compose_node(self, parent, index):
65
- if self.check_event(AliasEvent):
66
- event = self.get_event()
67
- anchor = event.anchor
68
- if anchor not in self.anchors:
69
- raise ComposerError(None, None, "found undefined alias %r"
70
- % anchor.encode('utf-8'), event.start_mark)
71
- return self.anchors[anchor]
72
- event = self.peek_event()
73
- anchor = event.anchor
74
- if anchor is not None:
75
- if anchor in self.anchors:
76
- raise ComposerError("found duplicate anchor %r; first occurence"
77
- % anchor.encode('utf-8'), self.anchors[anchor].start_mark,
78
- "second occurence", event.start_mark)
79
- self.descend_resolver(parent, index)
80
- if self.check_event(ScalarEvent):
81
- node = self.compose_scalar_node(anchor)
82
- elif self.check_event(SequenceStartEvent):
83
- node = self.compose_sequence_node(anchor)
84
- elif self.check_event(MappingStartEvent):
85
- node = self.compose_mapping_node(anchor)
86
- self.ascend_resolver()
87
- return node
88
-
89
- def compose_scalar_node(self, anchor):
90
- event = self.get_event()
91
- tag = event.tag
92
- if tag is None or tag == u'!':
93
- tag = self.resolve(ScalarNode, event.value, event.implicit)
94
- node = ScalarNode(tag, event.value,
95
- event.start_mark, event.end_mark, style=event.style)
96
- if anchor is not None:
97
- self.anchors[anchor] = node
98
- return node
99
-
100
- def compose_sequence_node(self, anchor):
101
- start_event = self.get_event()
102
- tag = start_event.tag
103
- if tag is None or tag == u'!':
104
- tag = self.resolve(SequenceNode, None, start_event.implicit)
105
- node = SequenceNode(tag, [],
106
- start_event.start_mark, None,
107
- flow_style=start_event.flow_style)
108
- if anchor is not None:
109
- self.anchors[anchor] = node
110
- index = 0
111
- while not self.check_event(SequenceEndEvent):
112
- node.value.append(self.compose_node(node, index))
113
- index += 1
114
- end_event = self.get_event()
115
- node.end_mark = end_event.end_mark
116
- return node
117
-
118
- def compose_mapping_node(self, anchor):
119
- start_event = self.get_event()
120
- tag = start_event.tag
121
- if tag is None or tag == u'!':
122
- tag = self.resolve(MappingNode, None, start_event.implicit)
123
- node = MappingNode(tag, [],
124
- start_event.start_mark, None,
125
- flow_style=start_event.flow_style)
126
- if anchor is not None:
127
- self.anchors[anchor] = node
128
- while not self.check_event(MappingEndEvent):
129
- #key_event = self.peek_event()
130
- item_key = self.compose_node(node, None)
131
- #if item_key in node.value:
132
- # raise ComposerError("while composing a mapping", start_event.start_mark,
133
- # "found duplicate key", key_event.start_mark)
134
- item_value = self.compose_node(node, item_key)
135
- #node.value[item_key] = item_value
136
- node.value.append((item_key, item_value))
137
- end_event = self.get_event()
138
- node.end_mark = end_event.end_mark
139
- return node
140
-
src/collectors/python.d.plugin/python_modules/pyyaml2/constructor.py
deleted
-676
@@ -1,676 +0,0 @@
1
-# SPDX-License-Identifier: MIT
2
-
3
-__all__ = ['BaseConstructor', 'SafeConstructor', 'Constructor',
4
- 'ConstructorError']
5
-
6
-from error import *
7
-from nodes import *
8
-
9
-import datetime
10
-
11
-import binascii, re, sys, types
12
-
13
-class ConstructorError(MarkedYAMLError):
14
- pass
15
-
16
-class BaseConstructor(object):
17
-
18
- yaml_constructors = {}
19
- yaml_multi_constructors = {}
20
-
21
- def __init__(self):
22
- self.constructed_objects = {}
23
- self.recursive_objects = {}
24
- self.state_generators = []
25
- self.deep_construct = False
26
-
27
- def check_data(self):
28
- # If there are more documents available?
29
- return self.check_node()
30
-
31
- def get_data(self):
32
- # Construct and return the next document.
33
- if self.check_node():
34
- return self.construct_document(self.get_node())
35
-
36
- def get_single_data(self):
37
- # Ensure that the stream contains a single document and construct it.
38
- node = self.get_single_node()
39
- if node is not None:
40
- return self.construct_document(node)
41
- return None
42
-
43
- def construct_document(self, node):
44
- data = self.construct_object(node)
45
- while self.state_generators:
46
- state_generators = self.state_generators
47
- self.state_generators = []
48
- for generator in state_generators:
49
- for dummy in generator:
50
- pass
51
- self.constructed_objects = {}
52
- self.recursive_objects = {}
53
- self.deep_construct = False
54
- return data
55
-
56
- def construct_object(self, node, deep=False):
57
- if node in self.constructed_objects:
58
- return self.constructed_objects[node]
59
- if deep:
60
- old_deep = self.deep_construct
61
- self.deep_construct = True
62
- if node in self.recursive_objects:
63
- raise ConstructorError(None, None,
64
- "found unconstructable recursive node", node.start_mark)
65
- self.recursive_objects[node] = None
66
- constructor = None
67
- tag_suffix = None
68
- if node.tag in self.yaml_constructors:
69
- constructor = self.yaml_constructors[node.tag]
70
- else:
71
- for tag_prefix in self.yaml_multi_constructors:
72
- if node.tag.startswith(tag_prefix):
73
- tag_suffix = node.tag[len(tag_prefix):]
74
- constructor = self.yaml_multi_constructors[tag_prefix]
75
- break
76
- else:
77
- if None in self.yaml_multi_constructors:
78
- tag_suffix = node.tag
79
- constructor = self.yaml_multi_constructors[None]
80
- elif None in self.yaml_constructors:
81
- constructor = self.yaml_constructors[None]
82
- elif isinstance(node, ScalarNode):
83
- constructor = self.__class__.construct_scalar
84
- elif isinstance(node, SequenceNode):
85
- constructor = self.__class__.construct_sequence
86
- elif isinstance(node, MappingNode):
87
- constructor = self.__class__.construct_mapping
88
- if tag_suffix is None:
89
- data = constructor(self, node)
90
- else:
91
- data = constructor(self, tag_suffix, node)
92
- if isinstance(data, types.GeneratorType):
93
- generator = data
94
- data = generator.next()
95
- if self.deep_construct:
96
- for dummy in generator:
97
- pass
98
- else:
99
- self.state_generators.append(generator)
100
- self.constructed_objects[node] = data
101
- del self.recursive_objects[node]
102
- if deep:
103
- self.deep_construct = old_deep
104
- return data
105
-
106
- def construct_scalar(self, node):
107
- if not isinstance(node, ScalarNode):
108
- raise ConstructorError(None, None,
109
- "expected a scalar node, but found %s" % node.id,
110
- node.start_mark)
111
- return node.value
112
-
113
- def construct_sequence(self, node, deep=False):
114
- if not isinstance(node, SequenceNode):
115
- raise ConstructorError(None, None,
116
- "expected a sequence node, but found %s" % node.id,
117
- node.start_mark)
118
- return [self.construct_object(child, deep=deep)
119
- for child in node.value]
120
-
121
- def construct_mapping(self, node, deep=False):
122
- if not isinstance(node, MappingNode):
123
- raise ConstructorError(None, None,
124
- "expected a mapping node, but found %s" % node.id,
125
- node.start_mark)
126
- mapping = {}
127
- for key_node, value_node in node.value:
128
- key = self.construct_object(key_node, deep=deep)
129
- try:
130
- hash(key)
131
- except TypeError, exc:
132
- raise ConstructorError("while constructing a mapping", node.start_mark,
133
- "found unacceptable key (%s)" % exc, key_node.start_mark)
134
- value = self.construct_object(value_node, deep=deep)
135
- mapping[key] = value
136
- return mapping
137
-
138
- def construct_pairs(self, node, deep=False):
139
- if not isinstance(node, MappingNode):
140
- raise ConstructorError(None, None,
141
- "expected a mapping node, but found %s" % node.id,
142
- node.start_mark)
143
- pairs = []
144
- for key_node, value_node in node.value:
145
- key = self.construct_object(key_node, deep=deep)
146
- value = self.construct_object(value_node, deep=deep)
147
- pairs.append((key, value))
148
- return pairs
149
-
150
- def add_constructor(cls, tag, constructor):
151
- if not 'yaml_constructors' in cls.__dict__:
152
- cls.yaml_constructors = cls.yaml_constructors.copy()
153
- cls.yaml_constructors[tag] = constructor
154
- add_constructor = classmethod(add_constructor)
155
-
156
- def add_multi_constructor(cls, tag_prefix, multi_constructor):
157
- if not 'yaml_multi_constructors' in cls.__dict__:
158
- cls.yaml_multi_constructors = cls.yaml_multi_constructors.copy()
159
- cls.yaml_multi_constructors[tag_prefix] = multi_constructor
160
- add_multi_constructor = classmethod(add_multi_constructor)
161
-
162
-class SafeConstructor(BaseConstructor):
163
-
164
- def construct_scalar(self, node):
165
- if isinstance(node, MappingNode):
166
- for key_node, value_node in node.value:
167
- if key_node.tag == u'tag:yaml.org,2002:value':
168
- return self.construct_scalar(value_node)
169
- return BaseConstructor.construct_scalar(self, node)
170
-
171
- def flatten_mapping(self, node):
172
- merge = []
173
- index = 0
174
- while index < len(node.value):
175
- key_node, value_node = node.value[index]
176
- if key_node.tag == u'tag:yaml.org,2002:merge':
177
- del node.value[index]
178
- if isinstance(value_node, MappingNode):
179
- self.flatten_mapping(value_node)
180
- merge.extend(value_node.value)
181
- elif isinstance(value_node, SequenceNode):
182
- submerge = []
183
- for subnode in value_node.value:
184
- if not isinstance(subnode, MappingNode):
185
- raise ConstructorError("while constructing a mapping",
186
- node.start_mark,
187
- "expected a mapping for merging, but found %s"
188
- % subnode.id, subnode.start_mark)
189
- self.flatten_mapping(subnode)
190
- submerge.append(subnode.value)
191
- submerge.reverse()
192
- for value in submerge:
193
- merge.extend(value)
194
- else:
195
- raise ConstructorError("while constructing a mapping", node.start_mark,
196
- "expected a mapping or list of mappings for merging, but found %s"
197
- % value_node.id, value_node.start_mark)
198
- elif key_node.tag == u'tag:yaml.org,2002:value':
199
- key_node.tag = u'tag:yaml.org,2002:str'
200
- index += 1
201
- else:
202
- index += 1
203
- if merge:
204
- node.value = merge + node.value
205
-
206
- def construct_mapping(self, node, deep=False):
207
- if isinstance(node, MappingNode):
208
- self.flatten_mapping(node)
209
- return BaseConstructor.construct_mapping(self, node, deep=deep)
210
-
211
- def construct_yaml_null(self, node):
212
- self.construct_scalar(node)
213
- return None
214
-
215
- bool_values = {
216
- u'yes': True,
217
- u'no': False,
218
- u'true': True,
219
- u'false': False,
220
- u'on': True,
221
- u'off': False,
222
- }
223
-
224
- def construct_yaml_bool(self, node):
225
- value = self.construct_scalar(node)
226
- return self.bool_values[value.lower()]
227
-
228
- def construct_yaml_int(self, node):
229
- value = str(self.construct_scalar(node))
230
- value = value.replace('_', '')
231
- sign = +1
232
- if value[0] == '-':
233
- sign = -1
234
- if value[0] in '+-':
235
- value = value[1:]
236
- if value == '0':
237
- return 0
238
- elif value.startswith('0b'):
239
- return sign*int(value[2:], 2)
240
- elif value.startswith('0x'):
241
- return sign*int(value[2:], 16)
242
- elif value[0] == '0':
243
- return sign*int(value, 8)
244
- elif ':' in value:
245
- digits = [int(part) for part in value.split(':')]
246
- digits.reverse()
247
- base = 1
248
- value = 0
249
- for digit in digits:
250
- value += digit*base
251
- base *= 60
252
- return sign*value
253
- else:
254
- return sign*int(value)
255
-
256
- inf_value = 1e300
257
- while inf_value != inf_value*inf_value:
258
- inf_value *= inf_value
259
- nan_value = -inf_value/inf_value # Trying to make a quiet NaN (like C99).
260
-
261
- def construct_yaml_float(self, node):
262
- value = str(self.construct_scalar(node))
263
- value = value.replace('_', '').lower()
264
- sign = +1
265
- if value[0] == '-':
266
- sign = -1
267
- if value[0] in '+-':
268
- value = value[1:]
269
- if value == '.inf':
270
- return sign*self.inf_value
271
- elif value == '.nan':
272
- return self.nan_value
273
- elif ':' in value:
274
- digits = [float(part) for part in value.split(':')]
275
- digits.reverse()
276
- base = 1
277
- value = 0.0
278
- for digit in digits:
279
- value += digit*base
280
- base *= 60
281
- return sign*value
282
- else:
283
- return sign*float(value)
284
-
285
- def construct_yaml_binary(self, node):
286
- value = self.construct_scalar(node)
287
- try:
288
- return str(value).decode('base64')
289
- except (binascii.Error, UnicodeEncodeError), exc:
290
- raise ConstructorError(None, None,
291
- "failed to decode base64 data: %s" % exc, node.start_mark)
292
-
293
- timestamp_regexp = re.compile(
294
- ur'''^(?P<year>[0-9][0-9][0-9][0-9])
295
- -(?P<month>[0-9][0-9]?)
296
- -(?P<day>[0-9][0-9]?)
297
- (?:(?:[Tt]|[ \t]+)
298
- (?P<hour>[0-9][0-9]?)
299
- :(?P<minute>[0-9][0-9])
300
- :(?P<second>[0-9][0-9])
301
- (?:\.(?P<fraction>[0-9]*))?
302
- (?:[ \t]*(?P<tz>Z|(?P<tz_sign>[-+])(?P<tz_hour>[0-9][0-9]?)
303
- (?::(?P<tz_minute>[0-9][0-9]))?))?)?$''', re.X)
304
-
305
- def construct_yaml_timestamp(self, node):
306
- value = self.construct_scalar(node)
307
- match = self.timestamp_regexp.match(node.value)
308
- values = match.groupdict()
309
- year = int(values['year'])
310
- month = int(values['month'])
311
- day = int(values['day'])
312
- if not values['hour']:
313
- return datetime.date(year, month, day)
314
- hour = int(values['hour'])
315
- minute = int(values['minute'])
316
- second = int(values['second'])
317
- fraction = 0
318
- if values['fraction']:
319
- fraction = values['fraction'][:6]
320
- while len(fraction) < 6:
321
- fraction += '0'
322
- fraction = int(fraction)
323
- delta = None
324
- if values['tz_sign']:
325
- tz_hour = int(values['tz_hour'])
326
- tz_minute = int(values['tz_minute'] or 0)
327
- delta = datetime.timedelta(hours=tz_hour, minutes=tz_minute)
328
- if values['tz_sign'] == '-':
329
- delta = -delta
330
- data = datetime.datetime(year, month, day, hour, minute, second, fraction)
331
- if delta:
332
- data -= delta
333
- return data
334
-
335
- def construct_yaml_omap(self, node):
336
- # Note: we do not check for duplicate keys, because it's too
337
- # CPU-expensive.
338
- omap = []
339
- yield omap
340
- if not isinstance(node, SequenceNode):
341
- raise ConstructorError("while constructing an ordered map", node.start_mark,
342
- "expected a sequence, but found %s" % node.id, node.start_mark)
343
- for subnode in node.value:
344
- if not isinstance(subnode, MappingNode):
345
- raise ConstructorError("while constructing an ordered map", node.start_mark,
346
- "expected a mapping of length 1, but found %s" % subnode.id,
347
- subnode.start_mark)
348
- if len(subnode.value) != 1:
349
- raise ConstructorError("while constructing an ordered map", node.start_mark,
350
- "expected a single mapping item, but found %d items" % len(subnode.value),
351
- subnode.start_mark)
352
- key_node, value_node = subnode.value[0]
353
- key = self.construct_object(key_node)
354
- value = self.construct_object(value_node)
355
- omap.append((key, value))
356
-
357
- def construct_yaml_pairs(self, node):
358
- # Note: the same code as `construct_yaml_omap`.
359
- pairs = []
360
- yield pairs
361
- if not isinstance(node, SequenceNode):
362
- raise ConstructorError("while constructing pairs", node.start_mark,
363
- "expected a sequence, but found %s" % node.id, node.start_mark)
364
- for subnode in node.value:
365
- if not isinstance(subnode, MappingNode):
366
- raise ConstructorError("while constructing pairs", node.start_mark,
367
- "expected a mapping of length 1, but found %s" % subnode.id,
368
- subnode.start_mark)
369
- if len(subnode.value) != 1:
370
- raise ConstructorError("while constructing pairs", node.start_mark,
371
- "expected a single mapping item, but found %d items" % len(subnode.value),
372
- subnode.start_mark)
373
- key_node, value_node = subnode.value[0]
374
- key = self.construct_object(key_node)
375
- value = self.construct_object(value_node)
376
- pairs.append((key, value))
377
-
378
- def construct_yaml_set(self, node):
379
- data = set()
380
- yield data
381
- value = self.construct_mapping(node)
382
- data.update(value)
383
-
384
- def construct_yaml_str(self, node):
385
- value = self.construct_scalar(node)
386
- try:
387
- return value.encode('ascii')
388
- except UnicodeEncodeError:
389
- return value
390
-
391
- def construct_yaml_seq(self, node):
392
- data = []
393
- yield data
394
- data.extend(self.construct_sequence(node))
395
-
396
- def construct_yaml_map(self, node):
397
- data = {}
398
- yield data
399
- value = self.construct_mapping(node)
400
- data.update(value)
401
-
402
- def construct_yaml_object(self, node, cls):
403
- data = cls.__new__(cls)
404
- yield data
405
- if hasattr(data, '__setstate__'):
406
- state = self.construct_mapping(node, deep=True)
407
- data.__setstate__(state)
408
- else:
409
- state = self.construct_mapping(node)
410
- data.__dict__.update(state)
411
-
412
- def construct_undefined(self, node):
413
- raise ConstructorError(None, None,
414
- "could not determine a constructor for the tag %r" % node.tag.encode('utf-8'),
415
- node.start_mark)
416
-
417
-SafeConstructor.add_constructor(
418
- u'tag:yaml.org,2002:null',
419
- SafeConstructor.construct_yaml_null)
420
-
421
-SafeConstructor.add_constructor(
422
- u'tag:yaml.org,2002:bool',
423
- SafeConstructor.construct_yaml_bool)
424
-
425
-SafeConstructor.add_constructor(
426
- u'tag:yaml.org,2002:int',
427
- SafeConstructor.construct_yaml_int)
428
-
429
-SafeConstructor.add_constructor(
430
- u'tag:yaml.org,2002:float',
431
- SafeConstructor.construct_yaml_float)
432
-
433
-SafeConstructor.add_constructor(
434
- u'tag:yaml.org,2002:binary',
435
- SafeConstructor.construct_yaml_binary)
436
-
437
-SafeConstructor.add_constructor(
438
- u'tag:yaml.org,2002:timestamp',
439
- SafeConstructor.construct_yaml_timestamp)
440
-
441
-SafeConstructor.add_constructor(
442
- u'tag:yaml.org,2002:omap',
443
- SafeConstructor.construct_yaml_omap)
444
-
445
-SafeConstructor.add_constructor(
446
- u'tag:yaml.org,2002:pairs',
447
- SafeConstructor.construct_yaml_pairs)
448
-
449
-SafeConstructor.add_constructor(
450
- u'tag:yaml.org,2002:set',
451
- SafeConstructor.construct_yaml_set)
452
-
453
-SafeConstructor.add_constructor(
454
- u'tag:yaml.org,2002:str',
455
- SafeConstructor.construct_yaml_str)
456
-
457
-SafeConstructor.add_constructor(
458
- u'tag:yaml.org,2002:seq',
459
- SafeConstructor.construct_yaml_seq)
460
-
461
-SafeConstructor.add_constructor(
462
- u'tag:yaml.org,2002:map',
463
- SafeConstructor.construct_yaml_map)
464
-
465
-SafeConstructor.add_constructor(None,
466
- SafeConstructor.construct_undefined)
467
-
468
-class Constructor(SafeConstructor):
469
-
470
- def construct_python_str(self, node):
471
- return self.construct_scalar(node).encode('utf-8')
472
-
473
- def construct_python_unicode(self, node):
474
- return self.construct_scalar(node)
475
-
476
- def construct_python_long(self, node):
477
- return long(self.construct_yaml_int(node))
478
-
479
- def construct_python_complex(self, node):
480
- return complex(self.construct_scalar(node))
481
-
482
- def construct_python_tuple(self, node):
483
- return tuple(self.construct_sequence(node))
484
-
485
- def find_python_module(self, name, mark):
486
- if not name:
487
- raise ConstructorError("while constructing a Python module", mark,
488
- "expected non-empty name appended to the tag", mark)
489
- try:
490
- __import__(name)
491
- except ImportError, exc:
492
- raise ConstructorError("while constructing a Python module", mark,
493
- "cannot find module %r (%s)" % (name.encode('utf-8'), exc), mark)
494
- return sys.modules[name]
495
-
496
- def find_python_name(self, name, mark):
497
- if not name:
498
- raise ConstructorError("while constructing a Python object", mark,
499
- "expected non-empty name appended to the tag", mark)
500
- if u'.' in name:
501
- module_name, object_name = name.rsplit('.', 1)
502
- else:
503
- module_name = '__builtin__'
504
- object_name = name
505
- try:
506
- __import__(module_name)
507
- except ImportError, exc:
508
- raise ConstructorError("while constructing a Python object", mark,
509
- "cannot find module %r (%s)" % (module_name.encode('utf-8'), exc), mark)
510
- module = sys.modules[module_name]
511
- if not hasattr(module, object_name):
512
- raise ConstructorError("while constructing a Python object", mark,
513
- "cannot find %r in the module %r" % (object_name.encode('utf-8'),
514
- module.__name__), mark)
515
- return getattr(module, object_name)
516
-
517
- def construct_python_name(self, suffix, node):
518
- value = self.construct_scalar(node)
519
- if value:
520
- raise ConstructorError("while constructing a Python name", node.start_mark,
521
- "expected the empty value, but found %r" % value.encode('utf-8'),
522
- node.start_mark)
523
- return self.find_python_name(suffix, node.start_mark)
524
-
525
- def construct_python_module(self, suffix, node):
526
- value = self.construct_scalar(node)
527
- if value:
528
- raise ConstructorError("while constructing a Python module", node.start_mark,
529
- "expected the empty value, but found %r" % value.encode('utf-8'),
530
- node.start_mark)
531
- return self.find_python_module(suffix, node.start_mark)
532
-
533
- class classobj: pass
534
-
535
- def make_python_instance(self, suffix, node,
536
- args=None, kwds=None, newobj=False):
537
- if not args:
538
- args = []
539
- if not kwds:
540
- kwds = {}
541
- cls = self.find_python_name(suffix, node.start_mark)
542
- if newobj and isinstance(cls, type(self.classobj)) \
543
- and not args and not kwds:
544
- instance = self.classobj()
545
- instance.__class__ = cls
546
- return instance
547
- elif newobj and isinstance(cls, type):
548
- return cls.__new__(cls, *args, **kwds)
549
- else:
550
- return cls(*args, **kwds)
551
-
552
- def set_python_instance_state(self, instance, state):
553
- if hasattr(instance, '__setstate__'):
554
- instance.__setstate__(state)
555
- else:
556
- slotstate = {}
557
- if isinstance(state, tuple) and len(state) == 2:
558
- state, slotstate = state
559
- if hasattr(instance, '__dict__'):
560
- instance.__dict__.update(state)
561
- elif state:
562
- slotstate.update(state)
563
- for key, value in slotstate.items():
564
- setattr(object, key, value)
565
-
566
- def construct_python_object(self, suffix, node):
567
- # Format:
568
- # !!python/object:module.name { ... state ... }
569
- instance = self.make_python_instance(suffix, node, newobj=True)
570
- yield instance
571
- deep = hasattr(instance, '__setstate__')
572
- state = self.construct_mapping(node, deep=deep)
573
- self.set_python_instance_state(instance, state)
574
-
575
- def construct_python_object_apply(self, suffix, node, newobj=False):
576
- # Format:
577
- # !!python/object/apply # (or !!python/object/new)
578
- # args: [ ... arguments ... ]
579
- # kwds: { ... keywords ... }
580
- # state: ... state ...
581
- # listitems: [ ... listitems ... ]
582
- # dictitems: { ... dictitems ... }
583
- # or short format:
584
- # !!python/object/apply [ ... arguments ... ]
585
- # The difference between !!python/object/apply and !!python/object/new
586
- # is how an object is created, check make_python_instance for details.
587
- if isinstance(node, SequenceNode):
588
- args = self.construct_sequence(node, deep=True)
589
- kwds = {}
590
- state = {}
591
- listitems = []
592
- dictitems = {}
593
- else:
594
- value = self.construct_mapping(node, deep=True)
595
- args = value.get('args', [])
596
- kwds = value.get('kwds', {})
597
- state = value.get('state', {})
598
- listitems = value.get('listitems', [])
599
- dictitems = value.get('dictitems', {})
600
- instance = self.make_python_instance(suffix, node, args, kwds, newobj)
601
- if state:
602
- self.set_python_instance_state(instance, state)
603
- if listitems:
604
- instance.extend(listitems)
605
- if dictitems:
606
- for key in dictitems:
607
- instance[key] = dictitems[key]
608
- return instance
609
-
610
- def construct_python_object_new(self, suffix, node):
611
- return self.construct_python_object_apply(suffix, node, newobj=True)
612
-
613
-Constructor.add_constructor(
614
- u'tag:yaml.org,2002:python/none',
615
- Constructor.construct_yaml_null)
616
-
617
-Constructor.add_constructor(
618
- u'tag:yaml.org,2002:python/bool',
619
- Constructor.construct_yaml_bool)
620
-
621
-Constructor.add_constructor(
622
- u'tag:yaml.org,2002:python/str',
623
- Constructor.construct_python_str)
624
-
625
-Constructor.add_constructor(
626
- u'tag:yaml.org,2002:python/unicode',
627
- Constructor.construct_python_unicode)
628
-
629
-Constructor.add_constructor(
630
- u'tag:yaml.org,2002:python/int',
631
- Constructor.construct_yaml_int)
632
-
633
-Constructor.add_constructor(
634
- u'tag:yaml.org,2002:python/long',
635
- Constructor.construct_python_long)
636
-
637
-Constructor.add_constructor(
638
- u'tag:yaml.org,2002:python/float',
639
- Constructor.construct_yaml_float)
640
-
641
-Constructor.add_constructor(
642
- u'tag:yaml.org,2002:python/complex',
643
- Constructor.construct_python_complex)
644
-
645
-Constructor.add_constructor(
646
- u'tag:yaml.org,2002:python/list',
647
- Constructor.construct_yaml_seq)
648
-
649
-Constructor.add_constructor(
650
- u'tag:yaml.org,2002:python/tuple',
651
- Constructor.construct_python_tuple)
652
-
653
-Constructor.add_constructor(
654
- u'tag:yaml.org,2002:python/dict',
655
- Constructor.construct_yaml_map)
656
-
657
-Constructor.add_multi_constructor(
658
- u'tag:yaml.org,2002:python/name:',
659
- Constructor.construct_python_name)
660
-
661
-Constructor.add_multi_constructor(
662
- u'tag:yaml.org,2002:python/module:',
663
- Constructor.construct_python_module)
664
-
665
-Constructor.add_multi_constructor(
666
- u'tag:yaml.org,2002:python/object:',
667
- Constructor.construct_python_object)
668
-
669
-Constructor.add_multi_constructor(
670
- u'tag:yaml.org,2002:python/object/apply:',
671
- Constructor.construct_python_object_apply)
672
-
673
-Constructor.add_multi_constructor(
674
- u'tag:yaml.org,2002:python/object/new:',
675
- Constructor.construct_python_object_new)
676
-
src/collectors/python.d.plugin/python_modules/pyyaml2/cyaml.py
deleted
-86
@@ -1,86 +0,0 @@
1
-# SPDX-License-Identifier: MIT
2
-
3
-__all__ = ['CBaseLoader', 'CSafeLoader', 'CLoader',
4
- 'CBaseDumper', 'CSafeDumper', 'CDumper']
5
-
6
-from _yaml import CParser, CEmitter
7
-
8
-from constructor import *
9
-
10
-from serializer import *
11
-from representer import *
12
-
13
-from resolver import *
14
-
15
-class CBaseLoader(CParser, BaseConstructor, BaseResolver):
16
-
17
- def __init__(self, stream):
18
- CParser.__init__(self, stream)
19
- BaseConstructor.__init__(self)
20
- BaseResolver.__init__(self)
21
-
22
-class CSafeLoader(CParser, SafeConstructor, Resolver):
23
-
24
- def __init__(self, stream):
25
- CParser.__init__(self, stream)
26
- SafeConstructor.__init__(self)
27
- Resolver.__init__(self)
28
-
29
-class CLoader(CParser, Constructor, Resolver):
30
-
31
- def __init__(self, stream):
32
- CParser.__init__(self, stream)
33
- Constructor.__init__(self)
34
- Resolver.__init__(self)
35
-
36
-class CBaseDumper(CEmitter, BaseRepresenter, BaseResolver):
37
-
38
- def __init__(self, stream,
39
- default_style=None, default_flow_style=None,
40
- canonical=None, indent=None, width=None,
41
- allow_unicode=None, line_break=None,
42
- encoding=None, explicit_start=None, explicit_end=None,
43
- version=None, tags=None):
44
- CEmitter.__init__(self, stream, canonical=canonical,
45
- indent=indent, width=width, encoding=encoding,
46
- allow_unicode=allow_unicode, line_break=line_break,
47
- explicit_start=explicit_start, explicit_end=explicit_end,
48
- version=version, tags=tags)
49
- Representer.__init__(self, default_style=default_style,
50
- default_flow_style=default_flow_style)
51
- Resolver.__init__(self)
52
-
53
-class CSafeDumper(CEmitter, SafeRepresenter, Resolver):
54
-
55
- def __init__(self, stream,
56
- default_style=None, default_flow_style=None,
57
- canonical=None, indent=None, width=None,
58
- allow_unicode=None, line_break=None,
59
- encoding=None, explicit_start=None, explicit_end=None,
60
- version=None, tags=None):
61
- CEmitter.__init__(self, stream, canonical=canonical,
62
- indent=indent, width=width, encoding=encoding,
63
- allow_unicode=allow_unicode, line_break=line_break,
64
- explicit_start=explicit_start, explicit_end=explicit_end,
65
- version=version, tags=tags)
66
- SafeRepresenter.__init__(self, default_style=default_style,
67
- default_flow_style=default_flow_style)
68
- Resolver.__init__(self)
69
-
70
-class CDumper(CEmitter, Serializer, Representer, Resolver):
71
-
72
- def __init__(self, stream,
73
- default_style=None, default_flow_style=None,
74
- canonical=None, indent=None, width=None,
75
- allow_unicode=None, line_break=None,
76
- encoding=None, explicit_start=None, explicit_end=None,
77
- version=None, tags=None):
78
- CEmitter.__init__(self, stream, canonical=canonical,
79
- indent=indent, width=width, encoding=encoding,
80
- allow_unicode=allow_unicode, line_break=line_break,
81
- explicit_start=explicit_start, explicit_end=explicit_end,
82
- version=version, tags=tags)
83
- Representer.__init__(self, default_style=default_style,
84
- default_flow_style=default_flow_style)
85
- Resolver.__init__(self)
86
-
src/collectors/python.d.plugin/python_modules/pyyaml2/dumper.py
deleted
-63
@@ -1,63 +0,0 @@
1
-# SPDX-License-Identifier: MIT
2
-
3
-__all__ = ['BaseDumper', 'SafeDumper', 'Dumper']
4
-
5
-from emitter import *
6
-from serializer import *
7
-from representer import *
8
-from resolver import *
9
-
10
-class BaseDumper(Emitter, Serializer, BaseRepresenter, BaseResolver):
11
-
12
- def __init__(self, stream,
13
- default_style=None, default_flow_style=None,
14
- canonical=None, indent=None, width=None,
15
- allow_unicode=None, line_break=None,
16
- encoding=None, explicit_start=None, explicit_end=None,
17
- version=None, tags=None):
18
- Emitter.__init__(self, stream, canonical=canonical,
19
- indent=indent, width=width,
20
- allow_unicode=allow_unicode, line_break=line_break)
21
- Serializer.__init__(self, encoding=encoding,
22
- explicit_start=explicit_start, explicit_end=explicit_end,
23
- version=version, tags=tags)
24
- Representer.__init__(self, default_style=default_style,
25
- default_flow_style=default_flow_style)
26
- Resolver.__init__(self)
27
-
28
-class SafeDumper(Emitter, Serializer, SafeRepresenter, Resolver):
29
-
30
- def __init__(self, stream,
31
- default_style=None, default_flow_style=None,
32
- canonical=None, indent=None, width=None,
33
- allow_unicode=None, line_break=None,
34
- encoding=None, explicit_start=None, explicit_end=None,
35
- version=None, tags=None):
36
- Emitter.__init__(self, stream, canonical=canonical,
37
- indent=indent, width=width,
38
- allow_unicode=allow_unicode, line_break=line_break)
39
- Serializer.__init__(self, encoding=encoding,
40
- explicit_start=explicit_start, explicit_end=explicit_end,
41
- version=version, tags=tags)
42
- SafeRepresenter.__init__(self, default_style=default_style,
43
- default_flow_style=default_flow_style)
44
- Resolver.__init__(self)
45
-
46
-class Dumper(Emitter, Serializer, Representer, Resolver):
47
-
48
- def __init__(self, stream,
49
- default_style=None, default_flow_style=None,
50
- canonical=None, indent=None, width=None,
51
- allow_unicode=None, line_break=None,
52
- encoding=None, explicit_start=None, explicit_end=None,
53
- version=None, tags=None):
54
- Emitter.__init__(self, stream, canonical=canonical,
55
- indent=indent, width=width,
56
- allow_unicode=allow_unicode, line_break=line_break)
57
- Serializer.__init__(self, encoding=encoding,
58
- explicit_start=explicit_start, explicit_end=explicit_end,
59
- version=version, tags=tags)
60
- Representer.__init__(self, default_style=default_style,
61
- default_flow_style=default_flow_style)
62
- Resolver.__init__(self)
63
-
src/collectors/python.d.plugin/python_modules/pyyaml2/emitter.py
deleted
-1141
@@ -1,1141 +0,0 @@
1
-# SPDX-License-Identifier: MIT
2
-
3
-# Emitter expects events obeying the following grammar:
4
-# stream ::= STREAM-START document* STREAM-END
5
-# document ::= DOCUMENT-START node DOCUMENT-END
6
-# node ::= SCALAR | sequence | mapping
7
-# sequence ::= SEQUENCE-START node* SEQUENCE-END
8
-# mapping ::= MAPPING-START (node node)* MAPPING-END
9
-
10
-__all__ = ['Emitter', 'EmitterError']
11
-
12
-from error import YAMLError
13
-from events import *
14
-
15
-class EmitterError(YAMLError):
16
- pass
17
-
18
-class ScalarAnalysis(object):
19
- def __init__(self, scalar, empty, multiline,
20
- allow_flow_plain, allow_block_plain,
21
- allow_single_quoted, allow_double_quoted,
22
- allow_block):
23
- self.scalar = scalar
24
- self.empty = empty
25
- self.multiline = multiline
26
- self.allow_flow_plain = allow_flow_plain
27
- self.allow_block_plain = allow_block_plain
28
- self.allow_single_quoted = allow_single_quoted
29
- self.allow_double_quoted = allow_double_quoted
30
- self.allow_block = allow_block
31
-
32
-class Emitter(object):
33
-
34
- DEFAULT_TAG_PREFIXES = {
35
- u'!' : u'!',
36
- u'tag:yaml.org,2002:' : u'!!',
37
- }
38
-
39
- def __init__(self, stream, canonical=None, indent=None, width=None,
40
- allow_unicode=None, line_break=None):
41
-
42
- # The stream should have the methods `write` and possibly `flush`.
43
- self.stream = stream
44
-
45
- # Encoding can be overriden by STREAM-START.
46
- self.encoding = None
47
-
48
- # Emitter is a state machine with a stack of states to handle nested
49
- # structures.
50
- self.states = []
51
- self.state = self.expect_stream_start
52
-
53
- # Current event and the event queue.
54
- self.events = []
55
- self.event = None
56
-
57
- # The current indentation level and the stack of previous indents.
58
- self.indents = []
59
- self.indent = None
60
-
61
- # Flow level.
62
- self.flow_level = 0
63
-
64
- # Contexts.
65
- self.root_context = False
66
- self.sequence_context = False
67
- self.mapping_context = False
68
- self.simple_key_context = False
69
-
70
- # Characteristics of the last emitted character:
71
- # - current position.
72
- # - is it a whitespace?
73
- # - is it an indention character
74
- # (indentation space, '-', '?', or ':')?
75
- self.line = 0
76
- self.column = 0
77
- self.whitespace = True
78
- self.indention = True
79
-
80
- # Whether the document requires an explicit document indicator
81
- self.open_ended = False
82
-
83
- # Formatting details.
84
- self.canonical = canonical
85
- self.allow_unicode = allow_unicode
86
- self.best_indent = 2
87
- if indent and 1 < indent < 10:
88
- self.best_indent = indent
89
- self.best_width = 80
90
- if width and width > self.best_indent*2:
91
- self.best_width = width
92
- self.best_line_break = u'\n'
93
- if line_break in [u'\r', u'\n', u'\r\n']:
94
- self.best_line_break = line_break
95
-
96
- # Tag prefixes.
97
- self.tag_prefixes = None
98
-
99
- # Prepared anchor and tag.
100
- self.prepared_anchor = None
101
- self.prepared_tag = None
102
-
103
- # Scalar analysis and style.
104
- self.analysis = None
105
- self.style = None
106
-
107
- def dispose(self):
108
- # Reset the state attributes (to clear self-references)
109
- self.states = []
110
- self.state = None
111
-
112
- def emit(self, event):
113
- self.events.append(event)
114
- while not self.need_more_events():
115
- self.event = self.events.pop(0)
116
- self.state()
117
- self.event = None
118
-
119
- # In some cases, we wait for a few next events before emitting.
120
-
121
- def need_more_events(self):
122
- if not self.events:
123
- return True
124
- event = self.events[0]
125
- if isinstance(event, DocumentStartEvent):
126
- return self.need_events(1)
127
- elif isinstance(event, SequenceStartEvent):
128
- return self.need_events(2)
129
- elif isinstance(event, MappingStartEvent):
130
- return self.need_events(3)
131
- else:
132
- return False
133
-
134
- def need_events(self, count):
135
- level = 0
136
- for event in self.events[1:]:
137
- if isinstance(event, (DocumentStartEvent, CollectionStartEvent)):
138
- level += 1
139
- elif isinstance(event, (DocumentEndEvent, CollectionEndEvent)):
140
- level -= 1
141
- elif isinstance(event, StreamEndEvent):
142
- level = -1
143
- if level < 0:
144
- return False
145
- return (len(self.events) < count+1)
146
-
147
- def increase_indent(self, flow=False, indentless=False):
148
- self.indents.append(self.indent)
149
- if self.indent is None:
150
- if flow:
151
- self.indent = self.best_indent
152
- else:
153
- self.indent = 0
154
- elif not indentless:
155
- self.indent += self.best_indent
156
-
157
- # States.
158
-
159
- # Stream handlers.
160
-
161
- def expect_stream_start(self):
162
- if isinstance(self.event, StreamStartEvent):
163
- if self.event.encoding and not getattr(self.stream, 'encoding', None):
164
- self.encoding = self.event.encoding
165
- self.write_stream_start()
166
- self.state = self.expect_first_document_start
167
- else:
168
- raise EmitterError("expected StreamStartEvent, but got %s"
169
- % self.event)
170
-
171
- def expect_nothing(self):
172
- raise EmitterError("expected nothing, but got %s" % self.event)
173
-
174
- # Document handlers.
175
-
176
- def expect_first_document_start(self):
177
- return self.expect_document_start(first=True)
178
-
179
- def expect_document_start(self, first=False):
180
- if isinstance(self.event, DocumentStartEvent):
181
- if (self.event.version or self.event.tags) and self.open_ended:
182
- self.write_indicator(u'...', True)
183
- self.write_indent()
184
- if self.event.version:
185
- version_text = self.prepare_version(self.event.version)
186
- self.write_version_directive(version_text)
187
- self.tag_prefixes = self.DEFAULT_TAG_PREFIXES.copy()
188
- if self.event.tags:
189
- handles = self.event.tags.keys()
190
- handles.sort()
191
- for handle in handles:
192
- prefix = self.event.tags[handle]
193
- self.tag_prefixes[prefix] = handle
194
- handle_text = self.prepare_tag_handle(handle)
195
- prefix_text = self.prepare_tag_prefix(prefix)
196
- self.write_tag_directive(handle_text, prefix_text)
197
- implicit = (first and not self.event.explicit and not self.canonical
198
- and not self.event.version and not self.event.tags
199
- and not self.check_empty_document())
200
- if not implicit:
201
- self.write_indent()
202
- self.write_indicator(u'---', True)
203
- if self.canonical:
204
- self.write_indent()
205
- self.state = self.expect_document_root
206
- elif isinstance(self.event, StreamEndEvent):
207
- if self.open_ended:
208
- self.write_indicator(u'...', True)
209
- self.write_indent()
210
- self.write_stream_end()
211
- self.state = self.expect_nothing
212
- else:
213
- raise EmitterError("expected DocumentStartEvent, but got %s"
214
- % self.event)
215
-
216
- def expect_document_end(self):
217
- if isinstance(self.event, DocumentEndEvent):
218
- self.write_indent()
219
- if self.event.explicit:
220
- self.write_indicator(u'...', True)
221
- self.write_indent()
222
- self.flush_stream()
223
- self.state = self.expect_document_start
224
- else:
225
- raise EmitterError("expected DocumentEndEvent, but got %s"
226
- % self.event)
227
-
228
- def expect_document_root(self):
229
- self.states.append(self.expect_document_end)
230
- self.expect_node(root=True)
231
-
232
- # Node handlers.
233
-
234
- def expect_node(self, root=False, sequence=False, mapping=False,
235
- simple_key=False):
236
- self.root_context = root
237
- self.sequence_context = sequence
238
- self.mapping_context = mapping
239
- self.simple_key_context = simple_key
240
- if isinstance(self.event, AliasEvent):
241
- self.expect_alias()
242
- elif isinstance(self.event, (ScalarEvent, CollectionStartEvent)):
243
- self.process_anchor(u'&')
244
- self.process_tag()
245
- if isinstance(self.event, ScalarEvent):
246
- self.expect_scalar()
247
- elif isinstance(self.event, SequenceStartEvent):
248
- if self.flow_level or self.canonical or self.event.flow_style \
249
- or self.check_empty_sequence():
250
- self.expect_flow_sequence()
251
- else:
252
- self.expect_block_sequence()
253
- elif isinstance(self.event, MappingStartEvent):
254
- if self.flow_level or self.canonical or self.event.flow_style \
255
- or self.check_empty_mapping():
256
- self.expect_flow_mapping()
257
- else:
258
- self.expect_block_mapping()
259
- else:
260
- raise EmitterError("expected NodeEvent, but got %s" % self.event)
261
-
262
- def expect_alias(self):
263
- if self.event.anchor is None:
264
- raise EmitterError("anchor is not specified for alias")
265
- self.process_anchor(u'*')
266
- self.state = self.states.pop()
267
-
268
- def expect_scalar(self):
269
- self.increase_indent(flow=True)
270
- self.process_scalar()
271
- self.indent = self.indents.pop()
272
- self.state = self.states.pop()
273
-
274
- # Flow sequence handlers.
275
-
276
- def expect_flow_sequence(self):
277
- self.write_indicator(u'[', True, whitespace=True)
278
- self.flow_level += 1
279
- self.increase_indent(flow=True)
280
- self.state = self.expect_first_flow_sequence_item
281
-
282
- def expect_first_flow_sequence_item(self):
283
- if isinstance(self.event, SequenceEndEvent):
284
- self.indent = self.indents.pop()
285
- self.flow_level -= 1
286
- self.write_indicator(u']', False)
287
- self.state = self.states.pop()
288
- else:
289
- if self.canonical or self.column > self.best_width:
290
- self.write_indent()
291
- self.states.append(self.expect_flow_sequence_item)
292
- self.expect_node(sequence=True)
293
-
294
- def expect_flow_sequence_item(self):
295
- if isinstance(self.event, SequenceEndEvent):
296
- self.indent = self.indents.pop()
297
- self.flow_level -= 1
298
- if self.canonical:
299
- self.write_indicator(u',', False)
300
- self.write_indent()
301
- self.write_indicator(u']', False)
302
- self.state = self.states.pop()
303
- else:
304
- self.write_indicator(u',', False)
305
- if self.canonical or self.column > self.best_width:
306
- self.write_indent()
307
- self.states.append(self.expect_flow_sequence_item)
308
- self.expect_node(sequence=True)
309
-
310
- # Flow mapping handlers.
311
-
312
- def expect_flow_mapping(self):
313
- self.write_indicator(u'{', True, whitespace=True)
314
- self.flow_level += 1
315
- self.increase_indent(flow=True)
316
- self.state = self.expect_first_flow_mapping_key
317
-
318
- def expect_first_flow_mapping_key(self):
319
- if isinstance(self.event, MappingEndEvent):
320
- self.indent = self.indents.pop()
321
- self.flow_level -= 1
322
- self.write_indicator(u'}', False)
323
- self.state = self.states.pop()
324
- else:
325
- if self.canonical or self.column > self.best_width:
326
- self.write_indent()
327
- if not self.canonical and self.check_simple_key():
328
- self.states.append(self.expect_flow_mapping_simple_value)
329
- self.expect_node(mapping=True, simple_key=True)
330
- else:
331
- self.write_indicator(u'?', True)
332
- self.states.append(self.expect_flow_mapping_value)
333
- self.expect_node(mapping=True)
334
-
335
- def expect_flow_mapping_key(self):
336
- if isinstance(self.event, MappingEndEvent):
337
- self.indent = self.indents.pop()
338
- self.flow_level -= 1
339
- if self.canonical:
340
- self.write_indicator(u',', False)
341
- self.write_indent()
342
- self.write_indicator(u'}', False)
343
- self.state = self.states.pop()
344
- else:
345
- self.write_indicator(u',', False)
346
- if self.canonical or self.column > self.best_width:
347
- self.write_indent()
348
- if not self.canonical and self.check_simple_key():
349
- self.states.append(self.expect_flow_mapping_simple_value)
350
- self.expect_node(mapping=True, simple_key=True)
351
- else:
352
- self.write_indicator(u'?', True)
353
- self.states.append(self.expect_flow_mapping_value)
354
- self.expect_node(mapping=True)
355
-
356
- def expect_flow_mapping_simple_value(self):
357
- self.write_indicator(u':', False)
358
- self.states.append(self.expect_flow_mapping_key)
359
- self.expect_node(mapping=True)
360
-
361
- def expect_flow_mapping_value(self):
362
- if self.canonical or self.column > self.best_width:
363
- self.write_indent()
364
- self.write_indicator(u':', True)
365
- self.states.append(self.expect_flow_mapping_key)
366
- self.expect_node(mapping=True)
367
-
368
- # Block sequence handlers.
369
-
370
- def expect_block_sequence(self):
371
- indentless = (self.mapping_context and not self.indention)
372
- self.increase_indent(flow=False, indentless=indentless)
373
- self.state = self.expect_first_block_sequence_item
374
-
375
- def expect_first_block_sequence_item(self):
376
- return self.expect_block_sequence_item(first=True)
377
-
378
- def expect_block_sequence_item(self, first=False):
379
- if not first and isinstance(self.event, SequenceEndEvent):
380
- self.indent = self.indents.pop()
381
- self.state = self.states.pop()
382
- else:
383
- self.write_indent()
384
- self.write_indicator(u'-', True, indention=True)
385
- self.states.append(self.expect_block_sequence_item)
386
- self.expect_node(sequence=True)
387
-
388
- # Block mapping handlers.
389
-
390
- def expect_block_mapping(self):
391
- self.increase_indent(flow=False)
392
- self.state = self.expect_first_block_mapping_key
393
-
394
- def expect_first_block_mapping_key(self):
395
- return self.expect_block_mapping_key(first=True)
396
-
397
- def expect_block_mapping_key(self, first=False):
398
- if not first and isinstance(self.event, MappingEndEvent):
399
- self.indent = self.indents.pop()
400
- self.state = self.states.pop()
401
- else:
402
- self.write_indent()
403
- if self.check_simple_key():
404
- self.states.append(self.expect_block_mapping_simple_value)
405
- self.expect_node(mapping=True, simple_key=True)
406
- else:
407
- self.write_indicator(u'?', True, indention=True)
408
- self.states.append(self.expect_block_mapping_value)
409
- self.expect_node(mapping=True)
410
-
411
- def expect_block_mapping_simple_value(self):
412
- self.write_indicator(u':', False)
413
- self.states.append(self.expect_block_mapping_key)
414
- self.expect_node(mapping=True)
415
-
416
- def expect_block_mapping_value(self):
417
- self.write_indent()
418
- self.write_indicator(u':', True, indention=True)
419
- self.states.append(self.expect_block_mapping_key)
420
- self.expect_node(mapping=True)
421
-
422
- # Checkers.
423
-
424
- def check_empty_sequence(self):
425
- return (isinstance(self.event, SequenceStartEvent) and self.events
426
- and isinstance(self.events[0], SequenceEndEvent))
427
-
428
- def check_empty_mapping(self):
429
- return (isinstance(self.event, MappingStartEvent) and self.events
430
- and isinstance(self.events[0], MappingEndEvent))
431
-
432
- def check_empty_document(self):
433
- if not isinstance(self.event, DocumentStartEvent) or not self.events:
434
- return False
435
- event = self.events[0]
436
- return (isinstance(event, ScalarEvent) and event.anchor is None
437
- and event.tag is None and event.implicit and event.value == u'')
438
-
439
- def check_simple_key(self):
440
- length = 0
441
- if isinstance(self.event, NodeEvent) and self.event.anchor is not None:
442
- if self.prepared_anchor is None:
443
- self.prepared_anchor = self.prepare_anchor(self.event.anchor)
444
- length += len(self.prepared_anchor)
445
- if isinstance(self.event, (ScalarEvent, CollectionStartEvent)) \
446
- and self.event.tag is not None:
447
- if self.prepared_tag is None:
448
- self.prepared_tag = self.prepare_tag(self.event.tag)
449
- length += len(self.prepared_tag)
450
- if isinstance(self.event, ScalarEvent):
451
- if self.analysis is None:
452
- self.analysis = self.analyze_scalar(self.event.value)
453
- length += len(self.analysis.scalar)
454
- return (length < 128 and (isinstance(self.event, AliasEvent)
455
- or (isinstance(self.event, ScalarEvent)
456
- and not self.analysis.empty and not self.analysis.multiline)
457
- or self.check_empty_sequence() or self.check_empty_mapping()))
458
-
459
- # Anchor, Tag, and Scalar processors.
460
-
461
- def process_anchor(self, indicator):
462
- if self.event.anchor is None:
463
- self.prepared_anchor = None
464
- return
465
- if self.prepared_anchor is None:
466
- self.prepared_anchor = self.prepare_anchor(self.event.anchor)
467
- if self.prepared_anchor:
468
- self.write_indicator(indicator+self.prepared_anchor, True)
469
- self.prepared_anchor = None
470
-
471
- def process_tag(self):
472
- tag = self.event.tag
473
- if isinstance(self.event, ScalarEvent):
474
- if self.style is None:
475
- self.style = self.choose_scalar_style()
476
- if ((not self.canonical or tag is None) and
477
- ((self.style == '' and self.event.implicit[0])
478
- or (self.style != '' and self.event.implicit[1]))):
479
- self.prepared_tag = None
480
- return
481
- if self.event.implicit[0] and tag is None:
482
- tag = u'!'
483
- self.prepared_tag = None
484
- else:
485
- if (not self.canonical or tag is None) and self.event.implicit:
486
- self.prepared_tag = None
487
- return
488
- if tag is None:
489
- raise EmitterError("tag is not specified")
490
- if self.prepared_tag is None:
491
- self.prepared_tag = self.prepare_tag(tag)
492
- if self.prepared_tag:
493
- self.write_indicator(self.prepared_tag, True)
494
- self.prepared_tag = None
495
-
496
- def choose_scalar_style(self):
497
- if self.analysis is None:
498
- self.analysis = self.analyze_scalar(self.event.value)
499
- if self.event.style == '"' or self.canonical:
500
- return '"'
501
- if not self.event.style and self.event.implicit[0]:
502
- if (not (self.simple_key_context and
503
- (self.analysis.empty or self.analysis.multiline))
504
- and (self.flow_level and self.analysis.allow_flow_plain
505
- or (not self.flow_level and self.analysis.allow_block_plain))):
506
- return ''
507
- if self.event.style and self.event.style in '|>':
508
- if (not self.flow_level and not self.simple_key_context
509
- and self.analysis.allow_block):
510
- return self.event.style
511
- if not self.event.style or self.event.style == '\'':
512
- if (self.analysis.allow_single_quoted and
513
- not (self.simple_key_context and self.analysis.multiline)):
514
- return '\''
515
- return '"'
516
-
517
- def process_scalar(self):
518
- if self.analysis is None:
519
- self.analysis = self.analyze_scalar(self.event.value)
520
- if self.style is None:
521
- self.style = self.choose_scalar_style()
522
- split = (not self.simple_key_context)
523
- #if self.analysis.multiline and split \
524
- # and (not self.style or self.style in '\'\"'):
525
- # self.write_indent()
526
- if self.style == '"':
527
- self.write_double_quoted(self.analysis.scalar, split)
528
- elif self.style == '\'':
529
- self.write_single_quoted(self.analysis.scalar, split)
530
- elif self.style == '>':
531
- self.write_folded(self.analysis.scalar)
532
- elif self.style == '|':
533
- self.write_literal(self.analysis.scalar)
534
- else:
535
- self.write_plain(self.analysis.scalar, split)
536
- self.analysis = None
537
- self.style = None
538
-
539
- # Analyzers.
540
-
541
- def prepare_version(self, version):
542
- major, minor = version
543
- if major != 1:
544
- raise EmitterError("unsupported YAML version: %d.%d" % (major, minor))
545
- return u'%d.%d' % (major, minor)
546
-
547
- def prepare_tag_handle(self, handle):
548
- if not handle:
549
- raise EmitterError("tag handle must not be empty")
550
- if handle[0] != u'!' or handle[-1] != u'!':
551
- raise EmitterError("tag handle must start and end with '!': %r"
552
- % (handle.encode('utf-8')))
553
- for ch in handle[1:-1]:
554
- if not (u'0' <= ch <= u'9' or u'A' <= ch <= u'Z' or u'a' <= ch <= u'z' \
555
- or ch in u'-_'):
556
- raise EmitterError("invalid character %r in the tag handle: %r"
557
- % (ch.encode('utf-8'), handle.encode('utf-8')))
558
- return handle
559
-
560
- def prepare_tag_prefix(self, prefix):
561
- if not prefix:
562
- raise EmitterError("tag prefix must not be empty")
563
- chunks = []
564
- start = end = 0
565
- if prefix[0] == u'!':
566
- end = 1
567
- while end < len(prefix):
568
- ch = prefix[end]
569
- if u'0' <= ch <= u'9' or u'A' <= ch <= u'Z' or u'a' <= ch <= u'z' \
570
- or ch in u'-;/?!:@&=+$,_.~*\'()[]':
571
- end += 1
572
- else:
573
- if start < end:
574
- chunks.append(prefix[start:end])
575
- start = end = end+1
576
- data = ch.encode('utf-8')
577
- for ch in data:
578
- chunks.append(u'%%%02X' % ord(ch))
579
- if start < end:
580
- chunks.append(prefix[start:end])
581
- return u''.join(chunks)
582
-
583
- def prepare_tag(self, tag):
584
- if not tag:
585
- raise EmitterError("tag must not be empty")
586
- if tag == u'!':
587
- return tag
588
- handle = None
589
- suffix = tag
590
- prefixes = self.tag_prefixes.keys()
591
- prefixes.sort()
592
- for prefix in prefixes:
593
- if tag.startswith(prefix) \
594
- and (prefix == u'!' or len(prefix) < len(tag)):
595
- handle = self.tag_prefixes[prefix]
596
- suffix = tag[len(prefix):]
597
- chunks = []
598
- start = end = 0
599
- while end < len(suffix):
600
- ch = suffix[end]
601
- if u'0' <= ch <= u'9' or u'A' <= ch <= u'Z' or u'a' <= ch <= u'z' \
602
- or ch in u'-;/?:@&=+$,_.~*\'()[]' \
603
- or (ch == u'!' and handle != u'!'):
604
- end += 1
605
- else:
606
- if start < end:
607
- chunks.append(suffix[start:end])
608
- start = end = end+1
609
- data = ch.encode('utf-8')
610
- for ch in data:
611
- chunks.append(u'%%%02X' % ord(ch))
612
- if start < end:
613
- chunks.append(suffix[start:end])
614
- suffix_text = u''.join(chunks)
615
- if handle:
616
- return u'%s%s' % (handle, suffix_text)
617
- else:
618
- return u'!<%s>' % suffix_text
619
-
620
- def prepare_anchor(self, anchor):
621
- if not anchor:
622
- raise EmitterError("anchor must not be empty")
623
- for ch in anchor:
624
- if not (u'0' <= ch <= u'9' or u'A' <= ch <= u'Z' or u'a' <= ch <= u'z' \
625
- or ch in u'-_'):
626
- raise EmitterError("invalid character %r in the anchor: %r"
627
- % (ch.encode('utf-8'), anchor.encode('utf-8')))
628
- return anchor
629
-
630
- def analyze_scalar(self, scalar):
631
-
632
- # Empty scalar is a special case.
633
- if not scalar:
634
- return ScalarAnalysis(scalar=scalar, empty=True, multiline=False,
635
- allow_flow_plain=False, allow_block_plain=True,
636
- allow_single_quoted=True, allow_double_quoted=True,
637
- allow_block=False)
638
-
639
- # Indicators and special characters.
640
- block_indicators = False
641
- flow_indicators = False
642
- line_breaks = False
643
- special_characters = False
644
-
645
- # Important whitespace combinations.
646
- leading_space = False
647
- leading_break = False
648
- trailing_space = False
649
- trailing_break = False
650
- break_space = False
651
- space_break = False
652
-
653
- # Check document indicators.
654
- if scalar.startswith(u'---') or scalar.startswith(u'...'):
655
- block_indicators = True
656
- flow_indicators = True
657
-
658
- # First character or preceded by a whitespace.
659
- preceeded_by_whitespace = True
660
-
661
- # Last character or followed by a whitespace.
662
- followed_by_whitespace = (len(scalar) == 1 or
663
- scalar[1] in u'\0 \t\r\n\x85\u2028\u2029')
664
-
665
- # The previous character is a space.
666
- previous_space = False
667
-
668
- # The previous character is a break.
669
- previous_break = False
670
-
671
- index = 0
672
- while index < len(scalar):
673
- ch = scalar[index]
674
-
675
- # Check for indicators.
676
- if index == 0:
677
- # Leading indicators are special characters.
678
- if ch in u'#,[]{}&*!|>\'\"%@`':
679
- flow_indicators = True
680
- block_indicators = True
681
- if ch in u'?:':
682
- flow_indicators = True
683
- if followed_by_whitespace:
684
- block_indicators = True
685
- if ch == u'-' and followed_by_whitespace:
686
- flow_indicators = True
687
- block_indicators = True
688
- else:
689
- # Some indicators cannot appear within a scalar as well.
690
- if ch in u',?[]{}':
691
- flow_indicators = True
692
- if ch == u':':
693
- flow_indicators = True
694
- if followed_by_whitespace:
695
- block_indicators = True
696
- if ch == u'#' and preceeded_by_whitespace:
697
- flow_indicators = True
698
- block_indicators = True
699
-
700
- # Check for line breaks, special, and unicode characters.
701
- if ch in u'\n\x85\u2028\u2029':
702
- line_breaks = True
703
- if not (ch == u'\n' or u'\x20' <= ch <= u'\x7E'):
704
- if (ch == u'\x85' or u'\xA0' <= ch <= u'\uD7FF'
705
- or u'\uE000' <= ch <= u'\uFFFD') and ch != u'\uFEFF':
706
- unicode_characters = True
707
- if not self.allow_unicode:
708
- special_characters = True
709
- else:
710
- special_characters = True
711
-
712
- # Detect important whitespace combinations.
713
- if ch == u' ':
714
- if index == 0:
715
- leading_space = True
716
- if index == len(scalar)-1:
717
- trailing_space = True
718
- if previous_break:
719
- break_space = True
720
- previous_space = True
721
- previous_break = False
722
- elif ch in u'\n\x85\u2028\u2029':
723
- if index == 0:
724
- leading_break = True
725
- if index == len(scalar)-1:
726
- trailing_break = True
727
- if previous_space:
728
- space_break = True
729
- previous_space = False
730
- previous_break = True
731
- else:
732
- previous_space = False
733
- previous_break = False
734
-
735
- # Prepare for the next character.
736
- index += 1
737
- preceeded_by_whitespace = (ch in u'\0 \t\r\n\x85\u2028\u2029')
738
- followed_by_whitespace = (index+1 >= len(scalar) or
739
- scalar[index+1] in u'\0 \t\r\n\x85\u2028\u2029')
740
-
741
- # Let's decide what styles are allowed.
742
- allow_flow_plain = True
743
- allow_block_plain = True
744
- allow_single_quoted = True
745
- allow_double_quoted = True
746
- allow_block = True
747
-
748
- # Leading and trailing whitespaces are bad for plain scalars.
749
- if (leading_space or leading_break
750
- or trailing_space or trailing_break):
751
- allow_flow_plain = allow_block_plain = False
752
-
753
- # We do not permit trailing spaces for block scalars.
754
- if trailing_space:
755
- allow_block = False
756
-
757
- # Spaces at the beginning of a new line are only acceptable for block
758
- # scalars.
759
- if break_space:
760
- allow_flow_plain = allow_block_plain = allow_single_quoted = False
761
-
762
- # Spaces followed by breaks, as well as special character are only
763
- # allowed for double quoted scalars.
764
- if space_break or special_characters:
765
- allow_flow_plain = allow_block_plain = \
766
- allow_single_quoted = allow_block = False
767
-
768
- # Although the plain scalar writer supports breaks, we never emit
769
- # multiline plain scalars.
770
- if line_breaks:
771
- allow_flow_plain = allow_block_plain = False
772
-
773
- # Flow indicators are forbidden for flow plain scalars.
774
- if flow_indicators:
775
- allow_flow_plain = False
776
-
777
- # Block indicators are forbidden for block plain scalars.
778
- if block_indicators:
779
- allow_block_plain = False
780
-
781
- return ScalarAnalysis(scalar=scalar,
782
- empty=False, multiline=line_breaks,
783
- allow_flow_plain=allow_flow_plain,
784
- allow_block_plain=allow_block_plain,
785
- allow_single_quoted=allow_single_quoted,
786
- allow_double_quoted=allow_double_quoted,
787
- allow_block=allow_block)
788
-
789
- # Writers.
790
-
791
- def flush_stream(self):
792
- if hasattr(self.stream, 'flush'):
793
- self.stream.flush()
794
-
795
- def write_stream_start(self):
796
- # Write BOM if needed.
797
- if self.encoding and self.encoding.startswith('utf-16'):
798
- self.stream.write(u'\uFEFF'.encode(self.encoding))
799
-
800
- def write_stream_end(self):
801
- self.flush_stream()
802
-
803
- def write_indicator(self, indicator, need_whitespace,
804
- whitespace=False, indention=False):
805
- if self.whitespace or not need_whitespace:
806
- data = indicator
807
- else:
808
- data = u' '+indicator
809
- self.whitespace = whitespace
810
- self.indention = self.indention and indention
811
- self.column += len(data)
812
- self.open_ended = False
813
- if self.encoding:
814
- data = data.encode(self.encoding)
815
- self.stream.write(data)
816
-
817
- def write_indent(self):
818
- indent = self.indent or 0
819
- if not self.indention or self.column > indent \
820
- or (self.column == indent and not self.whitespace):
821
- self.write_line_break()
822
- if self.column < indent:
823
- self.whitespace = True
824
- data = u' '*(indent-self.column)
825
- self.column = indent
826
- if self.encoding:
827
- data = data.encode(self.encoding)
828
- self.stream.write(data)
829
-
830
- def write_line_break(self, data=None):
831
- if data is None:
832
- data = self.best_line_break
833
- self.whitespace = True
834
- self.indention = True
835
- self.line += 1
836
- self.column = 0
837
- if self.encoding:
838
- data = data.encode(self.encoding)
839
- self.stream.write(data)
840
-
841
- def write_version_directive(self, version_text):
842
- data = u'%%YAML %s' % version_text
843
- if self.encoding:
844
- data = data.encode(self.encoding)
845
- self.stream.write(data)
846
- self.write_line_break()
847
-
848
- def write_tag_directive(self, handle_text, prefix_text):
849
- data = u'%%TAG %s %s' % (handle_text, prefix_text)
850
- if self.encoding:
851
- data = data.encode(self.encoding)
852
- self.stream.write(data)
853
- self.write_line_break()
854
-
855
- # Scalar streams.
856
-
857
- def write_single_quoted(self, text, split=True):
858
- self.write_indicator(u'\'', True)
859
- spaces = False
860
- breaks = False
861
- start = end = 0
862
- while end <= len(text):
863
- ch = None
864
- if end < len(text):
865
- ch = text[end]
866
- if spaces:
867
- if ch is None or ch != u' ':
868
- if start+1 == end and self.column > self.best_width and split \
869
- and start != 0 and end != len(text):
870
- self.write_indent()
871
- else:
872
- data = text[start:end]
873
- self.column += len(data)
874
- if self.encoding:
875
- data = data.encode(self.encoding)
876
- self.stream.write(data)
877
- start = end
878
- elif breaks:
879
- if ch is None or ch not in u'\n\x85\u2028\u2029':
880
- if text[start] == u'\n':
881
- self.write_line_break()
882
- for br in text[start:end]:
883
- if br == u'\n':
884
- self.write_line_break()
885
- else:
886
- self.write_line_break(br)
887
- self.write_indent()
888
- start = end
889
- else:
890
- if ch is None or ch in u' \n\x85\u2028\u2029' or ch == u'\'':
891
- if start < end:
892
- data = text[start:end]
893
- self.column += len(data)
894
- if self.encoding:
895
- data = data.encode(self.encoding)
896
- self.stream.write(data)
897
- start = end
898
- if ch == u'\'':
899
- data = u'\'\''
900
- self.column += 2
901
- if self.encoding:
902
- data = data.encode(self.encoding)
903
- self.stream.write(data)
904
- start = end + 1
905
- if ch is not None:
906
- spaces = (ch == u' ')
907
- breaks = (ch in u'\n\x85\u2028\u2029')
908
- end += 1
909
- self.write_indicator(u'\'', False)
910
-
911
- ESCAPE_REPLACEMENTS = {
912
- u'\0': u'0',
913
- u'\x07': u'a',
914
- u'\x08': u'b',
915
- u'\x09': u't',
916
- u'\x0A': u'n',
917
- u'\x0B': u'v',
918
- u'\x0C': u'f',
919
- u'\x0D': u'r',
920
- u'\x1B': u'e',
921
- u'\"': u'\"',
922
- u'\\': u'\\',
923
- u'\x85': u'N',
924
- u'\xA0': u'_',
925
- u'\u2028': u'L',
926
- u'\u2029': u'P',
927
- }
928
-
929
- def write_double_quoted(self, text, split=True):
930
- self.write_indicator(u'"', True)
931
- start = end = 0
932
- while end <= len(text):
933
- ch = None
934
- if end < len(text):
935
- ch = text[end]
936
- if ch is None or ch in u'"\\\x85\u2028\u2029\uFEFF' \
937
- or not (u'\x20' <= ch <= u'\x7E'
938
- or (self.allow_unicode
939
- and (u'\xA0' <= ch <= u'\uD7FF'
940
- or u'\uE000' <= ch <= u'\uFFFD'))):
941
- if start < end:
942
- data = text[start:end]
943
- self.column += len(data)
944
- if self.encoding:
945
- data = data.encode(self.encoding)
946
- self.stream.write(data)
947
- start = end
948
- if ch is not None:
949
- if ch in self.ESCAPE_REPLACEMENTS:
950
- data = u'\\'+self.ESCAPE_REPLACEMENTS[ch]
951
- elif ch <= u'\xFF':
952
- data = u'\\x%02X' % ord(ch)
953
- elif ch <= u'\uFFFF':
954
- data = u'\\u%04X' % ord(ch)
955
- else:
956
- data = u'\\U%08X' % ord(ch)
957
- self.column += len(data)
958
- if self.encoding:
959
- data = data.encode(self.encoding)
960
- self.stream.write(data)
961
- start = end+1
962
- if 0 < end < len(text)-1 and (ch == u' ' or start >= end) \
963
- and self.column+(end-start) > self.best_width and split:
964
- data = text[start:end]+u'\\'
965
- if start < end:
966
- start = end
967
- self.column += len(data)
968
- if self.encoding:
969
- data = data.encode(self.encoding)
970
- self.stream.write(data)
971
- self.write_indent()
972
- self.whitespace = False
973
- self.indention = False
974
- if text[start] == u' ':
975
- data = u'\\'
976
- self.column += len(data)
977
- if self.encoding:
978
- data = data.encode(self.encoding)
979
- self.stream.write(data)
980
- end += 1
981
- self.write_indicator(u'"', False)
982
-
983
- def determine_block_hints(self, text):
984
- hints = u''
985
- if text:
986
- if text[0] in u' \n\x85\u2028\u2029':
987
- hints += unicode(self.best_indent)
988
- if text[-1] not in u'\n\x85\u2028\u2029':
989
- hints += u'-'
990
- elif len(text) == 1 or text[-2] in u'\n\x85\u2028\u2029':
991
- hints += u'+'
992
- return hints
993
-
994
- def write_folded(self, text):
995
- hints = self.determine_block_hints(text)
996
- self.write_indicator(u'>'+hints, True)
997
- if hints[-1:] == u'+':
998
- self.open_ended = True
999
- self.write_line_break()
1000
- leading_space = True
1001
- spaces = False
1002
- breaks = True
1003
- start = end = 0
1004
- while end <= len(text):
1005
- ch = None
1006
- if end < len(text):
1007
- ch = text[end]
1008
- if breaks:
1009
- if ch is None or ch not in u'\n\x85\u2028\u2029':
1010
- if not leading_space and ch is not None and ch != u' ' \
1011
- and text[start] == u'\n':
1012
- self.write_line_break()
1013
- leading_space = (ch == u' ')
1014
- for br in text[start:end]:
1015
- if br == u'\n':
1016
- self.write_line_break()
1017
- else:
1018
- self.write_line_break(br)
1019
- if ch is not None:
1020
- self.write_indent()
1021
- start = end
1022
- elif spaces:
1023
- if ch != u' ':
1024
- if start+1 == end and self.column > self.best_width:
1025
- self.write_indent()
1026
- else:
1027
- data = text[start:end]
1028
- self.column += len(data)
1029
- if self.encoding:
1030
- data = data.encode(self.encoding)
1031
- self.stream.write(data)
1032
- start = end
1033
- else:
1034
- if ch is None or ch in u' \n\x85\u2028\u2029':
1035
- data = text[start:end]
1036
- self.column += len(data)
1037
- if self.encoding:
1038
- data = data.encode(self.encoding)
1039
- self.stream.write(data)
1040
- if ch is None:
1041
- self.write_line_break()
1042
- start = end
1043
- if ch is not None:
1044
- breaks = (ch in u'\n\x85\u2028\u2029')
1045
- spaces = (ch == u' ')
1046
- end += 1
1047
-
1048
- def write_literal(self, text):
1049
- hints = self.determine_block_hints(text)
1050
- self.write_indicator(u'|'+hints, True)
1051
- if hints[-1:] == u'+':
1052
- self.open_ended = True
1053
- self.write_line_break()
1054
- breaks = True
1055
- start = end = 0
1056
- while end <= len(text):
1057
- ch = None
1058
- if end < len(text):
1059
- ch = text[end]
1060
- if breaks:
1061
- if ch is None or ch not in u'\n\x85\u2028\u2029':
1062
- for br in text[start:end]:
1063
- if br == u'\n':
1064
- self.write_line_break()
1065
- else:
1066
- self.write_line_break(br)
1067
- if ch is not None:
1068
- self.write_indent()
1069
- start = end
1070
- else:
1071
- if ch is None or ch in u'\n\x85\u2028\u2029':
1072
- data = text[start:end]
1073
- if self.encoding:
1074
- data = data.encode(self.encoding)
1075
- self.stream.write(data)
1076
- if ch is None:
1077
- self.write_line_break()
1078
- start = end
1079
- if ch is not None:
1080
- breaks = (ch in u'\n\x85\u2028\u2029')
1081
- end += 1
1082
-
1083
- def write_plain(self, text, split=True):
1084
- if self.root_context:
1085
- self.open_ended = True
1086
- if not text:
1087
- return
1088
- if not self.whitespace:
1089
- data = u' '
1090
- self.column += len(data)
1091
- if self.encoding:
1092
- data = data.encode(self.encoding)
1093
- self.stream.write(data)
1094
- self.whitespace = False
1095
- self.indention = False
1096
- spaces = False
1097
- breaks = False
1098
- start = end = 0
1099
- while end <= len(text):
1100
- ch = None
1101
- if end < len(text):
1102
- ch = text[end]
1103
- if spaces:
1104
- if ch != u' ':
1105
- if start+1 == end and self.column > self.best_width and split:
1106
- self.write_indent()
1107
- self.whitespace = False
1108
- self.indention = False
1109
- else:
1110
- data = text[start:end]
1111
- self.column += len(data)
1112
- if self.encoding:
1113
- data = data.encode(self.encoding)
1114
- self.stream.write(data)
1115
- start = end
1116
- elif breaks:
1117
- if ch not in u'\n\x85\u2028\u2029':
1118
- if text[start] == u'\n':
1119
- self.write_line_break()
1120
- for br in text[start:end]:
1121
- if br == u'\n':
1122
- self.write_line_break()
1123
- else:
1124
- self.write_line_break(br)
1125
- self.write_indent()
1126
- self.whitespace = False
1127
- self.indention = False
1128
- start = end
1129
- else:
1130
- if ch is None or ch in u' \n\x85\u2028\u2029':
1131
- data = text[start:end]
1132
- self.column += len(data)
1133
- if self.encoding:
1134
- data = data.encode(self.encoding)
1135
- self.stream.write(data)
1136
- start = end
1137
- if ch is not None:
1138
- spaces = (ch == u' ')
1139
- breaks = (ch in u'\n\x85\u2028\u2029')
1140
- end += 1
1141
-
src/collectors/python.d.plugin/python_modules/pyyaml2/error.py
deleted
-76
@@ -1,76 +0,0 @@
1
-# SPDX-License-Identifier: MIT
2
-
3
-__all__ = ['Mark', 'YAMLError', 'MarkedYAMLError']
4
-
5
-class Mark(object):
6
-
7
- def __init__(self, name, index, line, column, buffer, pointer):
8
- self.name = name
9
- self.index = index
10
- self.line = line
11
- self.column = column
12
- self.buffer = buffer
13
- self.pointer = pointer
14
-
15
- def get_snippet(self, indent=4, max_length=75):
16
- if self.buffer is None:
17
- return None
18
- head = ''
19
- start = self.pointer
20
- while start > 0 and self.buffer[start-1] not in u'\0\r\n\x85\u2028\u2029':
21
- start -= 1
22
- if self.pointer-start > max_length/2-1:
23
- head = ' ... '
24
- start += 5
25
- break
26
- tail = ''
27
- end = self.pointer
28
- while end < len(self.buffer) and self.buffer[end] not in u'\0\r\n\x85\u2028\u2029':
29
- end += 1
30
- if end-self.pointer > max_length/2-1:
31
- tail = ' ... '
32
- end -= 5
33
- break
34
- snippet = self.buffer[start:end].encode('utf-8')
35
- return ' '*indent + head + snippet + tail + '\n' \
36
- + ' '*(indent+self.pointer-start+len(head)) + '^'
37
-
38
- def __str__(self):
39
- snippet = self.get_snippet()
40
- where = " in \"%s\", line %d, column %d" \
41
- % (self.name, self.line+1, self.column+1)
42
- if snippet is not None:
43
- where += ":\n"+snippet
44
- return where
45
-
46
-class YAMLError(Exception):
47
- pass
48
-
49
-class MarkedYAMLError(YAMLError):
50
-
51
- def __init__(self, context=None, context_mark=None,
52
- problem=None, problem_mark=None, note=None):
53
- self.context = context
54
- self.context_mark = context_mark
55
- self.problem = problem
56
- self.problem_mark = problem_mark
57
- self.note = note
58
-
59
- def __str__(self):
60
- lines = []
61
- if self.context is not None:
62
- lines.append(self.context)
63
- if self.context_mark is not None \
64
- and (self.problem is None or self.problem_mark is None
65
- or self.context_mark.name != self.problem_mark.name
66
- or self.context_mark.line != self.problem_mark.line
67
- or self.context_mark.column != self.problem_mark.column):
68
- lines.append(str(self.context_mark))
69
- if self.problem is not None:
70
- lines.append(self.problem)
71
- if self.problem_mark is not None:
72
- lines.append(str(self.problem_mark))
73
- if self.note is not None:
74
- lines.append(self.note)
75
- return '\n'.join(lines)
76
-
src/collectors/python.d.plugin/python_modules/pyyaml2/events.py
deleted
-87
@@ -1,87 +0,0 @@
1
-# SPDX-License-Identifier: MIT
2
-
3
-# Abstract classes.
4
-
5
-class Event(object):
6
- def __init__(self, start_mark=None, end_mark=None):
7
- self.start_mark = start_mark
8
- self.end_mark = end_mark
9
- def __repr__(self):
10
- attributes = [key for key in ['anchor', 'tag', 'implicit', 'value']
11
- if hasattr(self, key)]
12
- arguments = ', '.join(['%s=%r' % (key, getattr(self, key))
13
- for key in attributes])
14
- return '%s(%s)' % (self.__class__.__name__, arguments)
15
-
16
-class NodeEvent(Event):
17
- def __init__(self, anchor, start_mark=None, end_mark=None):
18
- self.anchor = anchor
19
- self.start_mark = start_mark
20
- self.end_mark = end_mark
21
-
22
-class CollectionStartEvent(NodeEvent):
23
- def __init__(self, anchor, tag, implicit, start_mark=None, end_mark=None,
24
- flow_style=None):
25
- self.anchor = anchor
26
- self.tag = tag
27
- self.implicit = implicit
28
- self.start_mark = start_mark
29
- self.end_mark = end_mark
30
- self.flow_style = flow_style
31
-
32
-class CollectionEndEvent(Event):
33
- pass
34
-
35
-# Implementations.
36
-
37
-class StreamStartEvent(Event):
38
- def __init__(self, start_mark=None, end_mark=None, encoding=None):
39
- self.start_mark = start_mark
40
- self.end_mark = end_mark
41
- self.encoding = encoding
42
-
43
-class StreamEndEvent(Event):
44
- pass
45
-
46
-class DocumentStartEvent(Event):
47
- def __init__(self, start_mark=None, end_mark=None,
48
- explicit=None, version=None, tags=None):
49
- self.start_mark = start_mark
50
- self.end_mark = end_mark
51
- self.explicit = explicit
52
- self.version = version
53
- self.tags = tags
54
-
55
-class DocumentEndEvent(Event):
56
- def __init__(self, start_mark=None, end_mark=None,
57
- explicit=None):
58
- self.start_mark = start_mark
59
- self.end_mark = end_mark
60
- self.explicit = explicit
61
-
62
-class AliasEvent(NodeEvent):
63
- pass
64
-
65
-class ScalarEvent(NodeEvent):
66
- def __init__(self, anchor, tag, implicit, value,
67
- start_mark=None, end_mark=None, style=None):
68
- self.anchor = anchor
69
- self.tag = tag
70
- self.implicit = implicit
71
- self.value = value
72
- self.start_mark = start_mark
73
- self.end_mark = end_mark
74
- self.style = style
75
-
76
-class SequenceStartEvent(CollectionStartEvent):
77
- pass
78
-
79
-class SequenceEndEvent(CollectionEndEvent):
80
- pass
81
-
82
-class MappingStartEvent(CollectionStartEvent):
83
- pass
84
-
85
-class MappingEndEvent(CollectionEndEvent):
86
- pass
87
-
src/collectors/python.d.plugin/python_modules/pyyaml2/loader.py
deleted
-41
@@ -1,41 +0,0 @@
1
-# SPDX-License-Identifier: MIT
2
-
3
-__all__ = ['BaseLoader', 'SafeLoader', 'Loader']
4
-
5
-from reader import *
6
-from scanner import *
7
-from parser import *
8
-from composer import *
9
-from constructor import *
10
-from resolver import *
11
-
12
-class BaseLoader(Reader, Scanner, Parser, Composer, BaseConstructor, BaseResolver):
13
-
14
- def __init__(self, stream):
15
- Reader.__init__(self, stream)
16
- Scanner.__init__(self)
17
- Parser.__init__(self)
18
- Composer.__init__(self)
19
- BaseConstructor.__init__(self)
20
- BaseResolver.__init__(self)
21
-
22
-class SafeLoader(Reader, Scanner, Parser, Composer, SafeConstructor, Resolver):
23
-
24
- def __init__(self, stream):
25
- Reader.__init__(self, stream)
26
- Scanner.__init__(self)
27
- Parser.__init__(self)
28
- Composer.__init__(self)
29
- SafeConstructor.__init__(self)
30
- Resolver.__init__(self)
31
-
32
-class Loader(Reader, Scanner, Parser, Composer, Constructor, Resolver):
33
-
34
- def __init__(self, stream):
35
- Reader.__init__(self, stream)
36
- Scanner.__init__(self)
37
- Parser.__init__(self)
38
- Composer.__init__(self)
39
- Constructor.__init__(self)
40
- Resolver.__init__(self)
41
-
src/collectors/python.d.plugin/python_modules/pyyaml2/nodes.py
deleted
-50
@@ -1,50 +0,0 @@
1
-# SPDX-License-Identifier: MIT
2
-
3
-class Node(object):
4
- def __init__(self, tag, value, start_mark, end_mark):
5
- self.tag = tag
6
- self.value = value
7
- self.start_mark = start_mark
8
- self.end_mark = end_mark
9
- def __repr__(self):
10
- value = self.value
11
- #if isinstance(value, list):
12
- # if len(value) == 0:
13
- # value = '<empty>'
14
- # elif len(value) == 1:
15
- # value = '<1 item>'
16
- # else:
17
- # value = '<%d items>' % len(value)
18
- #else:
19
- # if len(value) > 75:
20
- # value = repr(value[:70]+u' ... ')
21
- # else:
22
- # value = repr(value)
23
- value = repr(value)
24
- return '%s(tag=%r, value=%s)' % (self.__class__.__name__, self.tag, value)
25
-
26
-class ScalarNode(Node):
27
- id = 'scalar'
28
- def __init__(self, tag, value,
29
- start_mark=None, end_mark=None, style=None):
30
- self.tag = tag
31
- self.value = value
32
- self.start_mark = start_mark
33
- self.end_mark = end_mark
34
- self.style = style
35
-
36
-class CollectionNode(Node):
37
- def __init__(self, tag, value,
38
- start_mark=None, end_mark=None, flow_style=None):
39
- self.tag = tag
40
- self.value = value
41
- self.start_mark = start_mark
42
- self.end_mark = end_mark
43
- self.flow_style = flow_style
44
-
45
-class SequenceNode(CollectionNode):
46
- id = 'sequence'
47
-
48
-class MappingNode(CollectionNode):
49
- id = 'mapping'
50
-
src/collectors/python.d.plugin/python_modules/pyyaml2/parser.py
deleted
-590
@@ -1,590 +0,0 @@
1
-# SPDX-License-Identifier: MIT
2
-
3
-# The following YAML grammar is LL(1) and is parsed by a recursive descent
4
-# parser.
5
-#
6
-# stream ::= STREAM-START implicit_document? explicit_document* STREAM-END
7
-# implicit_document ::= block_node DOCUMENT-END*
8
-# explicit_document ::= DIRECTIVE* DOCUMENT-START block_node? DOCUMENT-END*
9
-# block_node_or_indentless_sequence ::=
10
-# ALIAS
11
-# | properties (block_content | indentless_block_sequence)?
12
-# | block_content
13
-# | indentless_block_sequence
14
-# block_node ::= ALIAS
15
-# | properties block_content?
16
-# | block_content
17
-# flow_node ::= ALIAS
18
-# | properties flow_content?
19
-# | flow_content
20
-# properties ::= TAG ANCHOR? | ANCHOR TAG?
21
-# block_content ::= block_collection | flow_collection | SCALAR
22
-# flow_content ::= flow_collection | SCALAR
23
-# block_collection ::= block_sequence | block_mapping
24
-# flow_collection ::= flow_sequence | flow_mapping
25
-# block_sequence ::= BLOCK-SEQUENCE-START (BLOCK-ENTRY block_node?)* BLOCK-END
26
-# indentless_sequence ::= (BLOCK-ENTRY block_node?)+
27
-# block_mapping ::= BLOCK-MAPPING_START
28
-# ((KEY block_node_or_indentless_sequence?)?
29
-# (VALUE block_node_or_indentless_sequence?)?)*
30
-# BLOCK-END
31
-# flow_sequence ::= FLOW-SEQUENCE-START
32
-# (flow_sequence_entry FLOW-ENTRY)*
33
-# flow_sequence_entry?
34
-# FLOW-SEQUENCE-END
35
-# flow_sequence_entry ::= flow_node | KEY flow_node? (VALUE flow_node?)?
36
-# flow_mapping ::= FLOW-MAPPING-START
37
-# (flow_mapping_entry FLOW-ENTRY)*
38
-# flow_mapping_entry?
39
-# FLOW-MAPPING-END
40
-# flow_mapping_entry ::= flow_node | KEY flow_node? (VALUE flow_node?)?
41
-#
42
-# FIRST sets:
43
-#
44
-# stream: { STREAM-START }
45
-# explicit_document: { DIRECTIVE DOCUMENT-START }
46
-# implicit_document: FIRST(block_node)
47
-# block_node: { ALIAS TAG ANCHOR SCALAR BLOCK-SEQUENCE-START BLOCK-MAPPING-START FLOW-SEQUENCE-START FLOW-MAPPING-START }
48
-# flow_node: { ALIAS ANCHOR TAG SCALAR FLOW-SEQUENCE-START FLOW-MAPPING-START }
49
-# block_content: { BLOCK-SEQUENCE-START BLOCK-MAPPING-START FLOW-SEQUENCE-START FLOW-MAPPING-START SCALAR }
50
-# flow_content: { FLOW-SEQUENCE-START FLOW-MAPPING-START SCALAR }
51
-# block_collection: { BLOCK-SEQUENCE-START BLOCK-MAPPING-START }
52
-# flow_collection: { FLOW-SEQUENCE-START FLOW-MAPPING-START }
53
-# block_sequence: { BLOCK-SEQUENCE-START }
54
-# block_mapping: { BLOCK-MAPPING-START }
55
-# block_node_or_indentless_sequence: { ALIAS ANCHOR TAG SCALAR BLOCK-SEQUENCE-START BLOCK-MAPPING-START FLOW-SEQUENCE-START FLOW-MAPPING-START BLOCK-ENTRY }
56
-# indentless_sequence: { ENTRY }
57
-# flow_collection: { FLOW-SEQUENCE-START FLOW-MAPPING-START }
58
-# flow_sequence: { FLOW-SEQUENCE-START }
59
-# flow_mapping: { FLOW-MAPPING-START }
60
-# flow_sequence_entry: { ALIAS ANCHOR TAG SCALAR FLOW-SEQUENCE-START FLOW-MAPPING-START KEY }
61
-# flow_mapping_entry: { ALIAS ANCHOR TAG SCALAR FLOW-SEQUENCE-START FLOW-MAPPING-START KEY }
62
-
63
-__all__ = ['Parser', 'ParserError']
64
-
65
-from error import MarkedYAMLError
66
-from tokens import *
67
-from events import *
68
-from scanner import *
69
-
70
-class ParserError(MarkedYAMLError):
71
- pass
72
-
73
-class Parser(object):
74
- # Since writing a recursive-descendant parser is a straightforward task, we
75
- # do not give many comments here.
76
-
77
- DEFAULT_TAGS = {
78
- u'!': u'!',
79
- u'!!': u'tag:yaml.org,2002:',
80
- }
81
-
82
- def __init__(self):
83
- self.current_event = None
84
- self.yaml_version = None
85
- self.tag_handles = {}
86
- self.states = []
87
- self.marks = []
88
- self.state = self.parse_stream_start
89
-
90
- def dispose(self):
91
- # Reset the state attributes (to clear self-references)
92
- self.states = []
93
- self.state = None
94
-
95
- def check_event(self, *choices):
96
- # Check the type of the next event.
97
- if self.current_event is None:
98
- if self.state:
99
- self.current_event = self.state()
100
- if self.current_event is not None:
101
- if not choices:
102
- return True
103
- for choice in choices:
104
- if isinstance(self.current_event, choice):
105
- return True
106
- return False
107
-
108
- def peek_event(self):
109
- # Get the next event.
110
- if self.current_event is None:
111
- if self.state:
112
- self.current_event = self.state()
113
- return self.current_event
114
-
115
- def get_event(self):
116
- # Get the next event and proceed further.
117
- if self.current_event is None:
118
- if self.state:
119
- self.current_event = self.state()
120
- value = self.current_event
121
- self.current_event = None
122
- return value
123
-
124
- # stream ::= STREAM-START implicit_document? explicit_document* STREAM-END
125
- # implicit_document ::= block_node DOCUMENT-END*
126
- # explicit_document ::= DIRECTIVE* DOCUMENT-START block_node? DOCUMENT-END*
127
-
128
- def parse_stream_start(self):
129
-
130
- # Parse the stream start.
131
- token = self.get_token()
132
- event = StreamStartEvent(token.start_mark, token.end_mark,
133
- encoding=token.encoding)
134
-
135
- # Prepare the next state.
136
- self.state = self.parse_implicit_document_start
137
-
138
- return event
139
-
140
- def parse_implicit_document_start(self):
141
-
142
- # Parse an implicit document.
143
- if not self.check_token(DirectiveToken, DocumentStartToken,
144
- StreamEndToken):
145
- self.tag_handles = self.DEFAULT_TAGS
146
- token = self.peek_token()
147
- start_mark = end_mark = token.start_mark
148
- event = DocumentStartEvent(start_mark, end_mark,
149
- explicit=False)
150
-
151
- # Prepare the next state.
152
- self.states.append(self.parse_document_end)
153
- self.state = self.parse_block_node
154
-
155
- return event
156
-
157
- else:
158
- return self.parse_document_start()
159
-
160
- def parse_document_start(self):
161
-
162
- # Parse any extra document end indicators.
163
- while self.check_token(DocumentEndToken):
164
- self.get_token()
165
-
166
- # Parse an explicit document.
167
- if not self.check_token(StreamEndToken):
168
- token = self.peek_token()
169
- start_mark = token.start_mark
170
- version, tags = self.process_directives()
171
- if not self.check_token(DocumentStartToken):
172
- raise ParserError(None, None,
173
- "expected '<document start>', but found %r"
174
- % self.peek_token().id,
175
- self.peek_token().start_mark)
176
- token = self.get_token()
177
- end_mark = token.end_mark
178
- event = DocumentStartEvent(start_mark, end_mark,
179
- explicit=True, version=version, tags=tags)
180
- self.states.append(self.parse_document_end)
181
- self.state = self.parse_document_content
182
- else:
183
- # Parse the end of the stream.
184
- token = self.get_token()
185
- event = StreamEndEvent(token.start_mark, token.end_mark)
186
- assert not self.states
187
- assert not self.marks
188
- self.state = None
189
- return event
190
-
191
- def parse_document_end(self):
192
-
193
- # Parse the document end.
194
- token = self.peek_token()
195
- start_mark = end_mark = token.start_mark
196
- explicit = False
197
- if self.check_token(DocumentEndToken):
198
- token = self.get_token()
199
- end_mark = token.end_mark
200
- explicit = True
201
- event = DocumentEndEvent(start_mark, end_mark,
202
- explicit=explicit)
203
-
204
- # Prepare the next state.
205
- self.state = self.parse_document_start
206
-
207
- return event
208
-
209
- def parse_document_content(self):
210
- if self.check_token(DirectiveToken,
211
- DocumentStartToken, DocumentEndToken, StreamEndToken):
212
- event = self.process_empty_scalar(self.peek_token().start_mark)
213
- self.state = self.states.pop()
214
- return event
215
- else:
216
- return self.parse_block_node()
217
-
218
- def process_directives(self):
219
- self.yaml_version = None
220
- self.tag_handles = {}
221
- while self.check_token(DirectiveToken):
222
- token = self.get_token()
223
- if token.name == u'YAML':
224
- if self.yaml_version is not None:
225
- raise ParserError(None, None,
226
- "found duplicate YAML directive", token.start_mark)
227
- major, minor = token.value
228
- if major != 1:
229
- raise ParserError(None, None,
230
- "found incompatible YAML document (version 1.* is required)",
231
- token.start_mark)
232
- self.yaml_version = token.value
233
- elif token.name == u'TAG':
234
- handle, prefix = token.value
235
- if handle in self.tag_handles:
236
- raise ParserError(None, None,
237
- "duplicate tag handle %r" % handle.encode('utf-8'),
238
- token.start_mark)
239
- self.tag_handles[handle] = prefix
240
- if self.tag_handles:
241
- value = self.yaml_version, self.tag_handles.copy()
242
- else:
243
- value = self.yaml_version, None
244
- for key in self.DEFAULT_TAGS:
245
- if key not in self.tag_handles:
246
- self.tag_handles[key] = self.DEFAULT_TAGS[key]
247
- return value
248
-
249
- # block_node_or_indentless_sequence ::= ALIAS
250
- # | properties (block_content | indentless_block_sequence)?
251
- # | block_content
252
- # | indentless_block_sequence
253
- # block_node ::= ALIAS
254
- # | properties block_content?
255
- # | block_content
256
- # flow_node ::= ALIAS
257
- # | properties flow_content?
258
- # | flow_content
259
- # properties ::= TAG ANCHOR? | ANCHOR TAG?
260
- # block_content ::= block_collection | flow_collection | SCALAR
261
- # flow_content ::= flow_collection | SCALAR
262
- # block_collection ::= block_sequence | block_mapping
263
- # flow_collection ::= flow_sequence | flow_mapping
264
-
265
- def parse_block_node(self):
266
- return self.parse_node(block=True)
267
-
268
- def parse_flow_node(self):
269
- return self.parse_node()
270
-
271
- def parse_block_node_or_indentless_sequence(self):
272
- return self.parse_node(block=True, indentless_sequence=True)
273
-
274
- def parse_node(self, block=False, indentless_sequence=False):
275
- if self.check_token(AliasToken):
276
- token = self.get_token()
277
- event = AliasEvent(token.value, token.start_mark, token.end_mark)
278
- self.state = self.states.pop()
279
- else:
280
- anchor = None
281
- tag = None
282
- start_mark = end_mark = tag_mark = None
283
- if self.check_token(AnchorToken):
284
- token = self.get_token()
285
- start_mark = token.start_mark
286
- end_mark = token.end_mark
287
- anchor = token.value
288
- if self.check_token(TagToken):
289
- token = self.get_token()
290
- tag_mark = token.start_mark
291
- end_mark = token.end_mark
292
- tag = token.value
293
- elif self.check_token(TagToken):
294
- token = self.get_token()
295
- start_mark = tag_mark = token.start_mark
296
- end_mark = token.end_mark
297
- tag = token.value
298
- if self.check_token(AnchorToken):
299
- token = self.get_token()
300
- end_mark = token.end_mark
301
- anchor = token.value
302
- if tag is not None:
303
- handle, suffix = tag
304
- if handle is not None:
305
- if handle not in self.tag_handles:
306
- raise ParserError("while parsing a node", start_mark,
307
- "found undefined tag handle %r" % handle.encode('utf-8'),
308
- tag_mark)
309
- tag = self.tag_handles[handle]+suffix
310
- else:
311
- tag = suffix
312
- #if tag == u'!':
313
- # raise ParserError("while parsing a node", start_mark,
314
- # "found non-specific tag '!'", tag_mark,
315
- # "Please check 'http://pyyaml.org/wiki/YAMLNonSpecificTag' and share your opinion.")
316
- if start_mark is None:
317
- start_mark = end_mark = self.peek_token().start_mark
318
- event = None
319
- implicit = (tag is None or tag == u'!')
320
- if indentless_sequence and self.check_token(BlockEntryToken):
321
- end_mark = self.peek_token().end_mark
322
- event = SequenceStartEvent(anchor, tag, implicit,
323
- start_mark, end_mark)
324
- self.state = self.parse_indentless_sequence_entry
325
- else:
326
- if self.check_token(ScalarToken):
327
- token = self.get_token()
328
- end_mark = token.end_mark
329
- if (token.plain and tag is None) or tag == u'!':
330
- implicit = (True, False)
331
- elif tag is None:
332
- implicit = (False, True)
333
- else:
334
- implicit = (False, False)
335
- event = ScalarEvent(anchor, tag, implicit, token.value,
336
- start_mark, end_mark, style=token.style)
337
- self.state = self.states.pop()
338
- elif self.check_token(FlowSequenceStartToken):
339
- end_mark = self.peek_token().end_mark
340
- event = SequenceStartEvent(anchor, tag, implicit,
341
- start_mark, end_mark, flow_style=True)
342
- self.state = self.parse_flow_sequence_first_entry
343
- elif self.check_token(FlowMappingStartToken):
344
- end_mark = self.peek_token().end_mark
345
- event = MappingStartEvent(anchor, tag, implicit,
346
- start_mark, end_mark, flow_style=True)
347
- self.state = self.parse_flow_mapping_first_key
348
- elif block and self.check_token(BlockSequenceStartToken):
349
- end_mark = self.peek_token().start_mark
350
- event = SequenceStartEvent(anchor, tag, implicit,
351
- start_mark, end_mark, flow_style=False)
352
- self.state = self.parse_block_sequence_first_entry
353
- elif block and self.check_token(BlockMappingStartToken):
354
- end_mark = self.peek_token().start_mark
355
- event = MappingStartEvent(anchor, tag, implicit,
356
- start_mark, end_mark, flow_style=False)
357
- self.state = self.parse_block_mapping_first_key
358
- elif anchor is not None or tag is not None:
359
- # Empty scalars are allowed even if a tag or an anchor is
360
- # specified.
361
- event = ScalarEvent(anchor, tag, (implicit, False), u'',
362
- start_mark, end_mark)
363
- self.state = self.states.pop()
364
- else:
365
- if block:
366
- node = 'block'
367
- else:
368
- node = 'flow'
369
- token = self.peek_token()
370
- raise ParserError("while parsing a %s node" % node, start_mark,
371
- "expected the node content, but found %r" % token.id,
372
- token.start_mark)
373
- return event
374
-
375
- # block_sequence ::= BLOCK-SEQUENCE-START (BLOCK-ENTRY block_node?)* BLOCK-END
376
-
377
- def parse_block_sequence_first_entry(self):
378
- token = self.get_token()
379
- self.marks.append(token.start_mark)
380
- return self.parse_block_sequence_entry()
381
-
382
- def parse_block_sequence_entry(self):
383
- if self.check_token(BlockEntryToken):
384
- token = self.get_token()
385
- if not self.check_token(BlockEntryToken, BlockEndToken):
386
- self.states.append(self.parse_block_sequence_entry)
387
- return self.parse_block_node()
388
- else:
389
- self.state = self.parse_block_sequence_entry
390
- return self.process_empty_scalar(token.end_mark)
391
- if not self.check_token(BlockEndToken):
392
- token = self.peek_token()
393
- raise ParserError("while parsing a block collection", self.marks[-1],
394
- "expected <block end>, but found %r" % token.id, token.start_mark)
395
- token = self.get_token()
396
- event = SequenceEndEvent(token.start_mark, token.end_mark)
397
- self.state = self.states.pop()
398
- self.marks.pop()
399
- return event
400
-
401
- # indentless_sequence ::= (BLOCK-ENTRY block_node?)+
402
-
403
- def parse_indentless_sequence_entry(self):
404
- if self.check_token(BlockEntryToken):
405
- token = self.get_token()
406
- if not self.check_token(BlockEntryToken,
407
- KeyToken, ValueToken, BlockEndToken):
408
- self.states.append(self.parse_indentless_sequence_entry)
409
- return self.parse_block_node()
410
- else:
411
- self.state = self.parse_indentless_sequence_entry
412
- return self.process_empty_scalar(token.end_mark)
413
- token = self.peek_token()
414
- event = SequenceEndEvent(token.start_mark, token.start_mark)
415
- self.state = self.states.pop()
416
- return event
417
-
418
- # block_mapping ::= BLOCK-MAPPING_START
419
- # ((KEY block_node_or_indentless_sequence?)?
420
- # (VALUE block_node_or_indentless_sequence?)?)*
421
- # BLOCK-END
422
-
423
- def parse_block_mapping_first_key(self):
424
- token = self.get_token()
425
- self.marks.append(token.start_mark)
426
- return self.parse_block_mapping_key()
427
-
428
- def parse_block_mapping_key(self):
429
- if self.check_token(KeyToken):
430
- token = self.get_token()
431
- if not self.check_token(KeyToken, ValueToken, BlockEndToken):
432
- self.states.append(self.parse_block_mapping_value)
433
- return self.parse_block_node_or_indentless_sequence()
434
- else:
435
- self.state = self.parse_block_mapping_value
436
- return self.process_empty_scalar(token.end_mark)
437
- if not self.check_token(BlockEndToken):
438
- token = self.peek_token()
439
- raise ParserError("while parsing a block mapping", self.marks[-1],
440
- "expected <block end>, but found %r" % token.id, token.start_mark)
441
- token = self.get_token()
442
- event = MappingEndEvent(token.start_mark, token.end_mark)
443
- self.state = self.states.pop()
444
- self.marks.pop()
445
- return event
446
-
447
- def parse_block_mapping_value(self):
448
- if self.check_token(ValueToken):
449
- token = self.get_token()
450
- if not self.check_token(KeyToken, ValueToken, BlockEndToken):
451
- self.states.append(self.parse_block_mapping_key)
452
- return self.parse_block_node_or_indentless_sequence()
453
- else:
454
- self.state = self.parse_block_mapping_key
455
- return self.process_empty_scalar(token.end_mark)
456
- else:
457
- self.state = self.parse_block_mapping_key
458
- token = self.peek_token()
459
- return self.process_empty_scalar(token.start_mark)
460
-
461
- # flow_sequence ::= FLOW-SEQUENCE-START
462
- # (flow_sequence_entry FLOW-ENTRY)*
463
- # flow_sequence_entry?
464
- # FLOW-SEQUENCE-END
465
- # flow_sequence_entry ::= flow_node | KEY flow_node? (VALUE flow_node?)?
466
- #
467
- # Note that while production rules for both flow_sequence_entry and
468
- # flow_mapping_entry are equal, their interpretations are different.
469
- # For `flow_sequence_entry`, the part `KEY flow_node? (VALUE flow_node?)?`
470
- # generate an inline mapping (set syntax).
471
-
472
- def parse_flow_sequence_first_entry(self):
473
- token = self.get_token()
474
- self.marks.append(token.start_mark)
475
- return self.parse_flow_sequence_entry(first=True)
476
-
477
- def parse_flow_sequence_entry(self, first=False):
478
- if not self.check_token(FlowSequenceEndToken):
479
- if not first:
480
- if self.check_token(FlowEntryToken):
481
- self.get_token()
482
- else:
483
- token = self.peek_token()
484
- raise ParserError("while parsing a flow sequence", self.marks[-1],
485
- "expected ',' or ']', but got %r" % token.id, token.start_mark)
486
-
487
- if self.check_token(KeyToken):
488
- token = self.peek_token()
489
- event = MappingStartEvent(None, None, True,
490
- token.start_mark, token.end_mark,
491
- flow_style=True)
492
- self.state = self.parse_flow_sequence_entry_mapping_key
493
- return event
494
- elif not self.check_token(FlowSequenceEndToken):
495
- self.states.append(self.parse_flow_sequence_entry)
496
- return self.parse_flow_node()
497
- token = self.get_token()
498
- event = SequenceEndEvent(token.start_mark, token.end_mark)
499
- self.state = self.states.pop()
500
- self.marks.pop()
501
- return event
502
-
503
- def parse_flow_sequence_entry_mapping_key(self):
504
- token = self.get_token()
505
- if not self.check_token(ValueToken,
506
- FlowEntryToken, FlowSequenceEndToken):
507
- self.states.append(self.parse_flow_sequence_entry_mapping_value)
508
- return self.parse_flow_node()
509
- else:
510
- self.state = self.parse_flow_sequence_entry_mapping_value
511
- return self.process_empty_scalar(token.end_mark)
512
-
513
- def parse_flow_sequence_entry_mapping_value(self):
514
- if self.check_token(ValueToken):
515
- token = self.get_token()
516
- if not self.check_token(FlowEntryToken, FlowSequenceEndToken):
517
- self.states.append(self.parse_flow_sequence_entry_mapping_end)
518
- return self.parse_flow_node()
519
- else:
520
- self.state = self.parse_flow_sequence_entry_mapping_end
521
- return self.process_empty_scalar(token.end_mark)
522
- else:
523
- self.state = self.parse_flow_sequence_entry_mapping_end
524
- token = self.peek_token()
525
- return self.process_empty_scalar(token.start_mark)
526
-
527
- def parse_flow_sequence_entry_mapping_end(self):
528
- self.state = self.parse_flow_sequence_entry
529
- token = self.peek_token()
530
- return MappingEndEvent(token.start_mark, token.start_mark)
531
-
532
- # flow_mapping ::= FLOW-MAPPING-START
533
- # (flow_mapping_entry FLOW-ENTRY)*
534
- # flow_mapping_entry?
535
- # FLOW-MAPPING-END
536
- # flow_mapping_entry ::= flow_node | KEY flow_node? (VALUE flow_node?)?
537
-
538
- def parse_flow_mapping_first_key(self):
539
- token = self.get_token()
540
- self.marks.append(token.start_mark)
541
- return self.parse_flow_mapping_key(first=True)
542
-
543
- def parse_flow_mapping_key(self, first=False):
544
- if not self.check_token(FlowMappingEndToken):
545
- if not first:
546
- if self.check_token(FlowEntryToken):
547
- self.get_token()
548
- else:
549
- token = self.peek_token()
550
- raise ParserError("while parsing a flow mapping", self.marks[-1],
551
- "expected ',' or '}', but got %r" % token.id, token.start_mark)
552
- if self.check_token(KeyToken):
553
- token = self.get_token()
554
- if not self.check_token(ValueToken,
555
- FlowEntryToken, FlowMappingEndToken):
556
- self.states.append(self.parse_flow_mapping_value)
557
- return self.parse_flow_node()
558
- else:
559
- self.state = self.parse_flow_mapping_value
560
- return self.process_empty_scalar(token.end_mark)
561
- elif not self.check_token(FlowMappingEndToken):
562
- self.states.append(self.parse_flow_mapping_empty_value)
563
- return self.parse_flow_node()
564
- token = self.get_token()
565
- event = MappingEndEvent(token.start_mark, token.end_mark)
566
- self.state = self.states.pop()
567
- self.marks.pop()
568
- return event
569
-
570
- def parse_flow_mapping_value(self):
571
- if self.check_token(ValueToken):
572
- token = self.get_token()
573
- if not self.check_token(FlowEntryToken, FlowMappingEndToken):
574
- self.states.append(self.parse_flow_mapping_key)
575
- return self.parse_flow_node()
576
- else:
577
- self.state = self.parse_flow_mapping_key
578
- return self.process_empty_scalar(token.end_mark)
579
- else:
580
- self.state = self.parse_flow_mapping_key
581
- token = self.peek_token()
582
- return self.process_empty_scalar(token.start_mark)
583
-
584
- def parse_flow_mapping_empty_value(self):
585
- self.state = self.parse_flow_mapping_key
586
- return self.process_empty_scalar(self.peek_token().start_mark)
587
-
588
- def process_empty_scalar(self, mark):
589
- return ScalarEvent(None, None, (True, False), u'', mark, mark)
590
-
src/collectors/python.d.plugin/python_modules/pyyaml2/reader.py
deleted
-191
@@ -1,191 +0,0 @@
1
-# SPDX-License-Identifier: MIT
2
-# This module contains abstractions for the input stream. You don't have to
3
-# looks further, there are no pretty code.
4
-#
5
-# We define two classes here.
6
-#
7
-# Mark(source, line, column)
8
-# It's just a record and its only use is producing nice error messages.
9
-# Parser does not use it for any other purposes.
10
-#
11
-# Reader(source, data)
12
-# Reader determines the encoding of `data` and converts it to unicode.
13
-# Reader provides the following methods and attributes:
14
-# reader.peek(length=1) - return the next `length` characters
15
-# reader.forward(length=1) - move the current position to `length` characters.
16
-# reader.index - the number of the current character.
17
-# reader.line, stream.column - the line and the column of the current character.
18
-
19
-__all__ = ['Reader', 'ReaderError']
20
-
21
-from error import YAMLError, Mark
22
-
23
-import codecs, re
24
-
25
-class ReaderError(YAMLError):
26
-
27
- def __init__(self, name, position, character, encoding, reason):
28
- self.name = name
29
- self.character = character
30
- self.position = position
31
- self.encoding = encoding
32
- self.reason = reason
33
-
34
- def __str__(self):
35
- if isinstance(self.character, str):
36
- return "'%s' codec can't decode byte #x%02x: %s\n" \
37
- " in \"%s\", position %d" \
38
- % (self.encoding, ord(self.character), self.reason,
39
- self.name, self.position)
40
- else:
41
- return "unacceptable character #x%04x: %s\n" \
42
- " in \"%s\", position %d" \
43
- % (self.character, self.reason,
44
- self.name, self.position)
45
-
46
-class Reader(object):
47
- # Reader:
48
- # - determines the data encoding and converts it to unicode,
49
- # - checks if characters are in allowed range,
50
- # - adds '\0' to the end.
51
-
52
- # Reader accepts
53
- # - a `str` object,
54
- # - a `unicode` object,
55
- # - a file-like object with its `read` method returning `str`,
56
- # - a file-like object with its `read` method returning `unicode`.
57
-
58
- # Yeah, it's ugly and slow.
59
-
60
- def __init__(self, stream):
61
- self.name = None
62
- self.stream = None
63
- self.stream_pointer = 0
64
- self.eof = True
65
- self.buffer = u''
66
- self.pointer = 0
67
- self.raw_buffer = None
68
- self.raw_decode = None
69
- self.encoding = None
70
- self.index = 0
71
- self.line = 0
72
- self.column = 0
73
- if isinstance(stream, unicode):
74
- self.name = "<unicode string>"
75
- self.check_printable(stream)
76
- self.buffer = stream+u'\0'
77
- elif isinstance(stream, str):
78
- self.name = "<string>"
79
- self.raw_buffer = stream
80
- self.determine_encoding()
81
- else:
82
- self.stream = stream
83
- self.name = getattr(stream, 'name', "<file>")
84
- self.eof = False
85
- self.raw_buffer = ''
86
- self.determine_encoding()
87
-
88
- def peek(self, index=0):
89
- try:
90
- return self.buffer[self.pointer+index]
91
- except IndexError:
92
- self.update(index+1)
93
- return self.buffer[self.pointer+index]
94
-
95
- def prefix(self, length=1):
96
- if self.pointer+length >= len(self.buffer):
97
- self.update(length)
98
- return self.buffer[self.pointer:self.pointer+length]
99
-
100
- def forward(self, length=1):
101
- if self.pointer+length+1 >= len(self.buffer):
102
- self.update(length+1)
103
- while length:
104
- ch = self.buffer[self.pointer]
105
- self.pointer += 1
106
- self.index += 1
107
- if ch in u'\n\x85\u2028\u2029' \
108
- or (ch == u'\r' and self.buffer[self.pointer] != u'\n'):
109
- self.line += 1
110
- self.column = 0
111
- elif ch != u'\uFEFF':
112
- self.column += 1
113
- length -= 1
114
-
115
- def get_mark(self):
116
- if self.stream is None:
117
- return Mark(self.name, self.index, self.line, self.column,
118
- self.buffer, self.pointer)
119
- else:
120
- return Mark(self.name, self.index, self.line, self.column,
121
- None, None)
122
-
123
- def determine_encoding(self):
124
- while not self.eof and len(self.raw_buffer) < 2:
125
- self.update_raw()
126
- if not isinstance(self.raw_buffer, unicode):
127
- if self.raw_buffer.startswith(codecs.BOM_UTF16_LE):
128
- self.raw_decode = codecs.utf_16_le_decode
129
- self.encoding = 'utf-16-le'
130
- elif self.raw_buffer.startswith(codecs.BOM_UTF16_BE):
131
- self.raw_decode = codecs.utf_16_be_decode
132
- self.encoding = 'utf-16-be'
133
- else:
134
- self.raw_decode = codecs.utf_8_decode
135
- self.encoding = 'utf-8'
136
- self.update(1)
137
-
138
- NON_PRINTABLE = re.compile(u'[^\x09\x0A\x0D\x20-\x7E\x85\xA0-\uD7FF\uE000-\uFFFD]')
139
- def check_printable(self, data):
140
- match = self.NON_PRINTABLE.search(data)
141
- if match:
142
- character = match.group()
143
- position = self.index+(len(self.buffer)-self.pointer)+match.start()
144
- raise ReaderError(self.name, position, ord(character),
145
- 'unicode', "special characters are not allowed")
146
-
147
- def update(self, length):
148
- if self.raw_buffer is None:
149
- return
150
- self.buffer = self.buffer[self.pointer:]
151
- self.pointer = 0
152
- while len(self.buffer) < length:
153
- if not self.eof:
154
- self.update_raw()
155
- if self.raw_decode is not None:
156
- try:
157
- data, converted = self.raw_decode(self.raw_buffer,
158
- 'strict', self.eof)
159
- except UnicodeDecodeError, exc:
160
- character = exc.object[exc.start]
161
- if self.stream is not None:
162
- position = self.stream_pointer-len(self.raw_buffer)+exc.start
163
- else:
164
- position = exc.start
165
- raise ReaderError(self.name, position, character,
166
- exc.encoding, exc.reason)
167
- else:
168
- data = self.raw_buffer
169
- converted = len(data)
170
- self.check_printable(data)
171
- self.buffer += data
172
- self.raw_buffer = self.raw_buffer[converted:]
173
- if self.eof:
174
- self.buffer += u'\0'
175
- self.raw_buffer = None
176
- break
177
-
178
- def update_raw(self, size=1024):
179
- data = self.stream.read(size)
180
- if data:
181
- self.raw_buffer += data
182
- self.stream_pointer += len(data)
183
- else:
184
- self.eof = True
185
-
186
-#try:
187
-# import psyco
188
-# psyco.bind(Reader)
189
-#except ImportError:
190
-# pass
191
-
src/collectors/python.d.plugin/python_modules/pyyaml2/representer.py
deleted
-485
@@ -1,485 +0,0 @@
1
-# SPDX-License-Identifier: MIT
2
-
3
-__all__ = ['BaseRepresenter', 'SafeRepresenter', 'Representer',
4
- 'RepresenterError']
5
-
6
-from error import *
7
-from nodes import *
8
-
9
-import datetime
10
-
11
-import sys, copy_reg, types
12
-
13
-class RepresenterError(YAMLError):
14
- pass
15
-
16
-class BaseRepresenter(object):
17
-
18
- yaml_representers = {}
19
- yaml_multi_representers = {}
20
-
21
- def __init__(self, default_style=None, default_flow_style=None):
22
- self.default_style = default_style
23
- self.default_flow_style = default_flow_style
24
- self.represented_objects = {}
25
- self.object_keeper = []
26
- self.alias_key = None
27
-
28
- def represent(self, data):
29
- node = self.represent_data(data)
30
- self.serialize(node)
31
- self.represented_objects = {}
32
- self.object_keeper = []
33
- self.alias_key = None
34
-
35
- def get_classobj_bases(self, cls):
36
- bases = [cls]
37
- for base in cls.__bases__:
38
- bases.extend(self.get_classobj_bases(base))
39
- return bases
40
-
41
- def represent_data(self, data):
42
- if self.ignore_aliases(data):
43
- self.alias_key = None
44
- else:
45
- self.alias_key = id(data)
46
- if self.alias_key is not None:
47
- if self.alias_key in self.represented_objects:
48
- node = self.represented_objects[self.alias_key]
49
- #if node is None:
50
- # raise RepresenterError("recursive objects are not allowed: %r" % data)
51
- return node
52
- #self.represented_objects[alias_key] = None
53
- self.object_keeper.append(data)
54
- data_types = type(data).__mro__
55
- if type(data) is types.InstanceType:
56
- data_types = self.get_classobj_bases(data.__class__)+list(data_types)
57
- if data_types[0] in self.yaml_representers:
58
- node = self.yaml_representers[data_types[0]](self, data)
59
- else:
60
- for data_type in data_types:
61
- if data_type in self.yaml_multi_representers:
62
- node = self.yaml_multi_representers[data_type](self, data)
63
- break
64
- else:
65
- if None in self.yaml_multi_representers:
66
- node = self.yaml_multi_representers[None](self, data)
67
- elif None in self.yaml_representers:
68
- node = self.yaml_representers[None](self, data)
69
- else:
70
- node = ScalarNode(None, unicode(data))
71
- #if alias_key is not None:
72
- # self.represented_objects[alias_key] = node
73
- return node
74
-
75
- def add_representer(cls, data_type, representer):
76
- if not 'yaml_representers' in cls.__dict__:
77
- cls.yaml_representers = cls.yaml_representers.copy()
78
- cls.yaml_representers[data_type] = representer
79
- add_representer = classmethod(add_representer)
80
-
81
- def add_multi_representer(cls, data_type, representer):
82
- if not 'yaml_multi_representers' in cls.__dict__:
83
- cls.yaml_multi_representers = cls.yaml_multi_representers.copy()
84
- cls.yaml_multi_representers[data_type] = representer
85
- add_multi_representer = classmethod(add_multi_representer)
86
-
87
- def represent_scalar(self, tag, value, style=None):
88
- if style is None:
89
- style = self.default_style
90
- node = ScalarNode(tag, value, style=style)
91
- if self.alias_key is not None:
92
- self.represented_objects[self.alias_key] = node
93
- return node
94
-
95
- def represent_sequence(self, tag, sequence, flow_style=None):
96
- value = []
97
- node = SequenceNode(tag, value, flow_style=flow_style)
98
- if self.alias_key is not None:
99
- self.represented_objects[self.alias_key] = node
100
- best_style = True
101
- for item in sequence:
102
- node_item = self.represent_data(item)
103
- if not (isinstance(node_item, ScalarNode) and not node_item.style):
104
- best_style = False
105
- value.append(node_item)
106
- if flow_style is None:
107
- if self.default_flow_style is not None:
108
- node.flow_style = self.default_flow_style
109
- else:
110
- node.flow_style = best_style
111
- return node
112
-
113
- def represent_mapping(self, tag, mapping, flow_style=None):
114
- value = []
115
- node = MappingNode(tag, value, flow_style=flow_style)
116
- if self.alias_key is not None:
117
- self.represented_objects[self.alias_key] = node
118
- best_style = True
119
- if hasattr(mapping, 'items'):
120
- mapping = mapping.items()
121
- mapping.sort()
122
- for item_key, item_value in mapping:
123
- node_key = self.represent_data(item_key)
124
- node_value = self.represent_data(item_value)
125
- if not (isinstance(node_key, ScalarNode) and not node_key.style):
126
- best_style = False
127
- if not (isinstance(node_value, ScalarNode) and not node_value.style):
128
- best_style = False
129
- value.append((node_key, node_value))
130
- if flow_style is None:
131
- if self.default_flow_style is not None:
132
- node.flow_style = self.default_flow_style
133
- else:
134
- node.flow_style = best_style
135
- return node
136
-
137
- def ignore_aliases(self, data):
138
- return False
139
-
140
-class SafeRepresenter(BaseRepresenter):
141
-
142
- def ignore_aliases(self, data):
143
- if data in [None, ()]:
144
- return True
145
- if isinstance(data, (str, unicode, bool, int, float)):
146
- return True
147
-
148
- def represent_none(self, data):
149
- return self.represent_scalar(u'tag:yaml.org,2002:null',
150
- u'null')
151
-
152
- def represent_str(self, data):
153
- tag = None
154
- style = None
155
- try:
156
- data = unicode(data, 'ascii')
157
- tag = u'tag:yaml.org,2002:str'
158
- except UnicodeDecodeError:
159
- try:
160
- data = unicode(data, 'utf-8')
161
- tag = u'tag:yaml.org,2002:str'
162
- except UnicodeDecodeError:
163
- data = data.encode('base64')
164
- tag = u'tag:yaml.org,2002:binary'
165
- style = '|'
166
- return self.represent_scalar(tag, data, style=style)
167
-
168
- def represent_unicode(self, data):
169
- return self.represent_scalar(u'tag:yaml.org,2002:str', data)
170
-
171
- def represent_bool(self, data):
172
- if data:
173
- value = u'true'
174
- else:
175
- value = u'false'
176
- return self.represent_scalar(u'tag:yaml.org,2002:bool', value)
177
-
178
- def represent_int(self, data):
179
- return self.represent_scalar(u'tag:yaml.org,2002:int', unicode(data))
180
-
181
- def represent_long(self, data):
182
- return self.represent_scalar(u'tag:yaml.org,2002:int', unicode(data))
183
-
184
- inf_value = 1e300
185
- while repr(inf_value) != repr(inf_value*inf_value):
186
- inf_value *= inf_value
187
-
188
- def represent_float(self, data):
189
- if data != data or (data == 0.0 and data == 1.0):
190
- value = u'.nan'
191
- elif data == self.inf_value:
192
- value = u'.inf'
193
- elif data == -self.inf_value:
194
- value = u'-.inf'
195
- else:
196
- value = unicode(repr(data)).lower()
197
- # Note that in some cases `repr(data)` represents a float number
198
- # without the decimal parts. For instance:
199
- # >>> repr(1e17)
200
- # '1e17'
201
- # Unfortunately, this is not a valid float representation according
202
- # to the definition of the `!!float` tag. We fix this by adding
203
- # '.0' before the 'e' symbol.
204
- if u'.' not in value and u'e' in value:
205
- value = value.replace(u'e', u'.0e', 1)
206
- return self.represent_scalar(u'tag:yaml.org,2002:float', value)
207
-
208
- def represent_list(self, data):
209
- #pairs = (len(data) > 0 and isinstance(data, list))
210
- #if pairs:
211
- # for item in data:
212
- # if not isinstance(item, tuple) or len(item) != 2:
213
- # pairs = False
214
- # break
215
- #if not pairs:
216
- return self.represent_sequence(u'tag:yaml.org,2002:seq', data)
217
- #value = []
218
- #for item_key, item_value in data:
219
- # value.append(self.represent_mapping(u'tag:yaml.org,2002:map',
220
- # [(item_key, item_value)]))
221
- #return SequenceNode(u'tag:yaml.org,2002:pairs', value)
222
-
223
- def represent_dict(self, data):
224
- return self.represent_mapping(u'tag:yaml.org,2002:map', data)
225
-
226
- def represent_set(self, data):
227
- value = {}
228
- for key in data:
229
- value[key] = None
230
- return self.represent_mapping(u'tag:yaml.org,2002:set', value)
231
-
232
- def represent_date(self, data):
233
- value = unicode(data.isoformat())
234
- return self.represent_scalar(u'tag:yaml.org,2002:timestamp', value)
235
-
236
- def represent_datetime(self, data):
237
- value = unicode(data.isoformat(' '))
238
- return self.represent_scalar(u'tag:yaml.org,2002:timestamp', value)
239
-
240
- def represent_yaml_object(self, tag, data, cls, flow_style=None):
241
- if hasattr(data, '__getstate__'):
242
- state = data.__getstate__()
243
- else:
244
- state = data.__dict__.copy()
245
- return self.represent_mapping(tag, state, flow_style=flow_style)
246
-
247
- def represent_undefined(self, data):
248
- raise RepresenterError("cannot represent an object: %s" % data)
249
-
250
-SafeRepresenter.add_representer(type(None),
251
- SafeRepresenter.represent_none)
252
-
253
-SafeRepresenter.add_representer(str,
254
- SafeRepresenter.represent_str)
255
-
256
-SafeRepresenter.add_representer(unicode,
257
- SafeRepresenter.represent_unicode)
258
-
259
-SafeRepresenter.add_representer(bool,
260
- SafeRepresenter.represent_bool)
261
-
262
-SafeRepresenter.add_representer(int,
263
- SafeRepresenter.represent_int)
264
-
265
-SafeRepresenter.add_representer(long,
266
- SafeRepresenter.represent_long)
267
-
268
-SafeRepresenter.add_representer(float,
269
- SafeRepresenter.represent_float)
270
-
271
-SafeRepresenter.add_representer(list,
272
- SafeRepresenter.represent_list)
273
-
274
-SafeRepresenter.add_representer(tuple,
275
- SafeRepresenter.represent_list)
276
-
277
-SafeRepresenter.add_representer(dict,
278
- SafeRepresenter.represent_dict)
279
-
280
-SafeRepresenter.add_representer(set,
281
- SafeRepresenter.represent_set)
282
-
283
-SafeRepresenter.add_representer(datetime.date,
284
- SafeRepresenter.represent_date)
285
-
286
-SafeRepresenter.add_representer(datetime.datetime,
287
- SafeRepresenter.represent_datetime)
288
-
289
-SafeRepresenter.add_representer(None,
290
- SafeRepresenter.represent_undefined)
291
-
292
-class Representer(SafeRepresenter):
293
-
294
- def represent_str(self, data):
295
- tag = None
296
- style = None
297
- try:
298
- data = unicode(data, 'ascii')
299
- tag = u'tag:yaml.org,2002:str'
300
- except UnicodeDecodeError:
301
- try:
302
- data = unicode(data, 'utf-8')
303
- tag = u'tag:yaml.org,2002:python/str'
304
- except UnicodeDecodeError:
305
- data = data.encode('base64')
306
- tag = u'tag:yaml.org,2002:binary'
307
- style = '|'
308
- return self.represent_scalar(tag, data, style=style)
309
-
310
- def represent_unicode(self, data):
311
- tag = None
312
- try:
313
- data.encode('ascii')
314
- tag = u'tag:yaml.org,2002:python/unicode'
315
- except UnicodeEncodeError:
316
- tag = u'tag:yaml.org,2002:str'
317
- return self.represent_scalar(tag, data)
318
-
319
- def represent_long(self, data):
320
- tag = u'tag:yaml.org,2002:int'
321
- if int(data) is not data:
322
- tag = u'tag:yaml.org,2002:python/long'
323
- return self.represent_scalar(tag, unicode(data))
324
-
325
- def represent_complex(self, data):
326
- if data.imag == 0.0:
327
- data = u'%r' % data.real
328
- elif data.real == 0.0:
329
- data = u'%rj' % data.imag
330
- elif data.imag > 0:
331
- data = u'%r+%rj' % (data.real, data.imag)
332
- else:
333
- data = u'%r%rj' % (data.real, data.imag)
334
- return self.represent_scalar(u'tag:yaml.org,2002:python/complex', data)
335
-
336
- def represent_tuple(self, data):
337
- return self.represent_sequence(u'tag:yaml.org,2002:python/tuple', data)
338
-
339
- def represent_name(self, data):
340
- name = u'%s.%s' % (data.__module__, data.__name__)
341
- return self.represent_scalar(u'tag:yaml.org,2002:python/name:'+name, u'')
342
-
343
- def represent_module(self, data):
344
- return self.represent_scalar(
345
- u'tag:yaml.org,2002:python/module:'+data.__name__, u'')
346
-
347
- def represent_instance(self, data):
348
- # For instances of classic classes, we use __getinitargs__ and
349
- # __getstate__ to serialize the data.
350
-
351
- # If data.__getinitargs__ exists, the object must be reconstructed by
352
- # calling cls(**args), where args is a tuple returned by
353
- # __getinitargs__. Otherwise, the cls.__init__ method should never be
354
- # called and the class instance is created by instantiating a trivial
355
- # class and assigning to the instance's __class__ variable.
356
-
357
- # If data.__getstate__ exists, it returns the state of the object.
358
- # Otherwise, the state of the object is data.__dict__.
359
-
360
- # We produce either a !!python/object or !!python/object/new node.
361
- # If data.__getinitargs__ does not exist and state is a dictionary, we
362
- # produce a !!python/object node . Otherwise we produce a
363
- # !!python/object/new node.
364
-
365
- cls = data.__class__
366
- class_name = u'%s.%s' % (cls.__module__, cls.__name__)
367
- args = None
368
- state = None
369
- if hasattr(data, '__getinitargs__'):
370
- args = list(data.__getinitargs__())
371
- if hasattr(data, '__getstate__'):
372
- state = data.__getstate__()
373
- else:
374
- state = data.__dict__
375
- if args is None and isinstance(state, dict):
376
- return self.represent_mapping(
377
- u'tag:yaml.org,2002:python/object:'+class_name, state)
378
- if isinstance(state, dict) and not state:
379
- return self.represent_sequence(
380
- u'tag:yaml.org,2002:python/object/new:'+class_name, args)
381
- value = {}
382
- if args:
383
- value['args'] = args
384
- value['state'] = state
385
- return self.represent_mapping(
386
- u'tag:yaml.org,2002:python/object/new:'+class_name, value)
387
-
388
- def represent_object(self, data):
389
- # We use __reduce__ API to save the data. data.__reduce__ returns
390
- # a tuple of length 2-5:
391
- # (function, args, state, listitems, dictitems)
392
-
393
- # For reconstructing, we calls function(*args), then set its state,
394
- # listitems, and dictitems if they are not None.
395
-
396
- # A special case is when function.__name__ == '__newobj__'. In this
397
- # case we create the object with args[0].__new__(*args).
398
-
399
- # Another special case is when __reduce__ returns a string - we don't
400
- # support it.
401
-
402
- # We produce a !!python/object, !!python/object/new or
403
- # !!python/object/apply node.
404
-
405
- cls = type(data)
406
- if cls in copy_reg.dispatch_table:
407
- reduce = copy_reg.dispatch_table[cls](data)
408
- elif hasattr(data, '__reduce_ex__'):
409
- reduce = data.__reduce_ex__(2)
410
- elif hasattr(data, '__reduce__'):
411
- reduce = data.__reduce__()
412
- else:
413
- raise RepresenterError("cannot represent object: %r" % data)
414
- reduce = (list(reduce)+[None]*5)[:5]
415
- function, args, state, listitems, dictitems = reduce
416
- args = list(args)
417
- if state is None:
418
- state = {}
419
- if listitems is not None:
420
- listitems = list(listitems)
421
- if dictitems is not None:
422
- dictitems = dict(dictitems)
423
- if function.__name__ == '__newobj__':
424
- function = args[0]
425
- args = args[1:]
426
- tag = u'tag:yaml.org,2002:python/object/new:'
427
- newobj = True
428
- else:
429
- tag = u'tag:yaml.org,2002:python/object/apply:'
430
- newobj = False
431
- function_name = u'%s.%s' % (function.__module__, function.__name__)
432
- if not args and not listitems and not dictitems \
433
- and isinstance(state, dict) and newobj:
434
- return self.represent_mapping(
435
- u'tag:yaml.org,2002:python/object:'+function_name, state)
436
- if not listitems and not dictitems \
437
- and isinstance(state, dict) and not state:
438
- return self.represent_sequence(tag+function_name, args)
439
- value = {}
440
- if args:
441
- value['args'] = args
442
- if state or not isinstance(state, dict):
443
- value['state'] = state
444
- if listitems:
445
- value['listitems'] = listitems
446
- if dictitems:
447
- value['dictitems'] = dictitems
448
- return self.represent_mapping(tag+function_name, value)
449
-
450
-Representer.add_representer(str,
451
- Representer.represent_str)
452
-
453
-Representer.add_representer(unicode,
454
- Representer.represent_unicode)
455
-
456
-Representer.add_representer(long,
457
- Representer.represent_long)
458
-
459
-Representer.add_representer(complex,
460
- Representer.represent_complex)
461
-
462
-Representer.add_representer(tuple,
463
- Representer.represent_tuple)
464
-
465
-Representer.add_representer(type,
466
- Representer.represent_name)
467
-
468
-Representer.add_representer(types.ClassType,
469
- Representer.represent_name)
470
-
471
-Representer.add_representer(types.FunctionType,
472
- Representer.represent_name)
473
-
474
-Representer.add_representer(types.BuiltinFunctionType,
475
- Representer.represent_name)
476
-
477
-Representer.add_representer(types.ModuleType,
478
- Representer.represent_module)
479
-
480
-Representer.add_multi_representer(types.InstanceType,
481
- Representer.represent_instance)
482
-
483
-Representer.add_multi_representer(object,
484
- Representer.represent_object)
485
-
src/collectors/python.d.plugin/python_modules/pyyaml2/resolver.py
deleted
-225
@@ -1,225 +0,0 @@
1
-# SPDX-License-Identifier: MIT
2
-
3
-__all__ = ['BaseResolver', 'Resolver']
4
-
5
-from error import *
6
-from nodes import *
7
-
8
-import re
9
-
10
-class ResolverError(YAMLError):
11
- pass
12
-
13
-class BaseResolver(object):
14
-
15
- DEFAULT_SCALAR_TAG = u'tag:yaml.org,2002:str'
16
- DEFAULT_SEQUENCE_TAG = u'tag:yaml.org,2002:seq'
17
- DEFAULT_MAPPING_TAG = u'tag:yaml.org,2002:map'
18
-
19
- yaml_implicit_resolvers = {}
20
- yaml_path_resolvers = {}
21
-
22
- def __init__(self):
23
- self.resolver_exact_paths = []
24
- self.resolver_prefix_paths = []
25
-
26
- def add_implicit_resolver(cls, tag, regexp, first):
27
- if not 'yaml_implicit_resolvers' in cls.__dict__:
28
- cls.yaml_implicit_resolvers = cls.yaml_implicit_resolvers.copy()
29
- if first is None:
30
- first = [None]
31
- for ch in first:
32
- cls.yaml_implicit_resolvers.setdefault(ch, []).append((tag, regexp))
33
- add_implicit_resolver = classmethod(add_implicit_resolver)
34
-
35
- def add_path_resolver(cls, tag, path, kind=None):
36
- # Note: `add_path_resolver` is experimental. The API could be changed.
37
- # `new_path` is a pattern that is matched against the path from the
38
- # root to the node that is being considered. `node_path` elements are
39
- # tuples `(node_check, index_check)`. `node_check` is a node class:
40
- # `ScalarNode`, `SequenceNode`, `MappingNode` or `None`. `None`
41
- # matches any kind of a node. `index_check` could be `None`, a boolean
42
- # value, a string value, or a number. `None` and `False` match against
43
- # any _value_ of sequence and mapping nodes. `True` matches against
44
- # any _key_ of a mapping node. A string `index_check` matches against
45
- # a mapping value that corresponds to a scalar key which content is
46
- # equal to the `index_check` value. An integer `index_check` matches
47
- # against a sequence value with the index equal to `index_check`.
48
- if not 'yaml_path_resolvers' in cls.__dict__:
49
- cls.yaml_path_resolvers = cls.yaml_path_resolvers.copy()
50
- new_path = []
51
- for element in path:
52
- if isinstance(element, (list, tuple)):
53
- if len(element) == 2:
54
- node_check, index_check = element
55
- elif len(element) == 1:
56
- node_check = element[0]
57
- index_check = True
58
- else:
59
- raise ResolverError("Invalid path element: %s" % element)
60
- else:
61
- node_check = None
62
- index_check = element
63
- if node_check is str:
64
- node_check = ScalarNode
65
- elif node_check is list:
66
- node_check = SequenceNode
67
- elif node_check is dict:
68
- node_check = MappingNode
69
- elif node_check not in [ScalarNode, SequenceNode, MappingNode] \
70
- and not isinstance(node_check, basestring) \
71
- and node_check is not None:
72
- raise ResolverError("Invalid node checker: %s" % node_check)
73
- if not isinstance(index_check, (basestring, int)) \
74
- and index_check is not None:
75
- raise ResolverError("Invalid index checker: %s" % index_check)
76
- new_path.append((node_check, index_check))
77
- if kind is str:
78
- kind = ScalarNode
79
- elif kind is list:
80
- kind = SequenceNode
81
- elif kind is dict:
82
- kind = MappingNode
83
- elif kind not in [ScalarNode, SequenceNode, MappingNode] \
84
- and kind is not None:
85
- raise ResolverError("Invalid node kind: %s" % kind)
86
- cls.yaml_path_resolvers[tuple(new_path), kind] = tag
87
- add_path_resolver = classmethod(add_path_resolver)
88
-
89
- def descend_resolver(self, current_node, current_index):
90
- if not self.yaml_path_resolvers:
91
- return
92
- exact_paths = {}
93
- prefix_paths = []
94
- if current_node:
95
- depth = len(self.resolver_prefix_paths)
96
- for path, kind in self.resolver_prefix_paths[-1]:
97
- if self.check_resolver_prefix(depth, path, kind,
98
- current_node, current_index):
99
- if len(path) > depth:
100
- prefix_paths.append((path, kind))
101
- else:
102
- exact_paths[kind] = self.yaml_path_resolvers[path, kind]
103
- else:
104
- for path, kind in self.yaml_path_resolvers:
105
- if not path:
106
- exact_paths[kind] = self.yaml_path_resolvers[path, kind]
107
- else:
108
- prefix_paths.append((path, kind))
109
- self.resolver_exact_paths.append(exact_paths)
110
- self.resolver_prefix_paths.append(prefix_paths)
111
-
112
- def ascend_resolver(self):
113
- if not self.yaml_path_resolvers:
114
- return
115
- self.resolver_exact_paths.pop()
116
- self.resolver_prefix_paths.pop()
117
-
118
- def check_resolver_prefix(self, depth, path, kind,
119
- current_node, current_index):
120
- node_check, index_check = path[depth-1]
121
- if isinstance(node_check, basestring):
122
- if current_node.tag != node_check:
123
- return
124
- elif node_check is not None:
125
- if not isinstance(current_node, node_check):
126
- return
127
- if index_check is True and current_index is not None:
128
- return
129
- if (index_check is False or index_check is None) \
130
- and current_index is None:
131
- return
132
- if isinstance(index_check, basestring):
133
- if not (isinstance(current_index, ScalarNode)
134
- and index_check == current_index.value):
135
- return
136
- elif isinstance(index_check, int) and not isinstance(index_check, bool):
137
- if index_check != current_index:
138
- return
139
- return True
140
-
141
- def resolve(self, kind, value, implicit):
142
- if kind is ScalarNode and implicit[0]:
143
- if value == u'':
144
- resolvers = self.yaml_implicit_resolvers.get(u'', [])
145
- else:
146
- resolvers = self.yaml_implicit_resolvers.get(value[0], [])
147
- resolvers += self.yaml_implicit_resolvers.get(None, [])
148
- for tag, regexp in resolvers:
149
- if regexp.match(value):
150
- return tag
151
- implicit = implicit[1]
152
- if self.yaml_path_resolvers:
153
- exact_paths = self.resolver_exact_paths[-1]
154
- if kind in exact_paths:
155
- return exact_paths[kind]
156
- if None in exact_paths:
157
- return exact_paths[None]
158
- if kind is ScalarNode:
159
- return self.DEFAULT_SCALAR_TAG
160
- elif kind is SequenceNode:
161
- return self.DEFAULT_SEQUENCE_TAG
162
- elif kind is MappingNode:
163
- return self.DEFAULT_MAPPING_TAG
164
-
165
-class Resolver(BaseResolver):
166
- pass
167
-
168
-Resolver.add_implicit_resolver(
169
- u'tag:yaml.org,2002:bool',
170
- re.compile(ur'''^(?:yes|Yes|YES|no|No|NO
171
- |true|True|TRUE|false|False|FALSE
172
- |on|On|ON|off|Off|OFF)$''', re.X),
173
- list(u'yYnNtTfFoO'))
174
-
175
-Resolver.add_implicit_resolver(
176
- u'tag:yaml.org,2002:float',
177
- re.compile(ur'''^(?:[-+]?(?:[0-9][0-9_]*)\.[0-9_]*(?:[eE][-+][0-9]+)?
178
- |\.[0-9_]+(?:[eE][-+][0-9]+)?
179
- |[-+]?[0-9][0-9_]*(?::[0-5]?[0-9])+\.[0-9_]*
180
- |[-+]?\.(?:inf|Inf|INF)
181
- |\.(?:nan|NaN|NAN))$''', re.X),
182
- list(u'-+0123456789.'))
183
-
184
-Resolver.add_implicit_resolver(
185
- u'tag:yaml.org,2002:int',
186
- re.compile(ur'''^(?:[-+]?0b[0-1_]+
187
- |[-+]?0[0-7_]+
188
- |[-+]?(?:0|[1-9][0-9_]*)
189
- |[-+]?0x[0-9a-fA-F_]+
190
- |[-+]?[1-9][0-9_]*(?::[0-5]?[0-9])+)$''', re.X),
191
- list(u'-+0123456789'))
192
-
193
-Resolver.add_implicit_resolver(
194
- u'tag:yaml.org,2002:merge',
195
- re.compile(ur'^(?:<<)$'),
196
- [u'<'])
197
-
198
-Resolver.add_implicit_resolver(
199
- u'tag:yaml.org,2002:null',
200
- re.compile(ur'''^(?: ~
201
- |null|Null|NULL
202
- | )$''', re.X),
203
- [u'~', u'n', u'N', u''])
204
-
205
-Resolver.add_implicit_resolver(
206
- u'tag:yaml.org,2002:timestamp',
207
- re.compile(ur'''^(?:[0-9][0-9][0-9][0-9]-[0-9][0-9]-[0-9][0-9]
208
- |[0-9][0-9][0-9][0-9] -[0-9][0-9]? -[0-9][0-9]?
209
- (?:[Tt]|[ \t]+)[0-9][0-9]?
210
- :[0-9][0-9] :[0-9][0-9] (?:\.[0-9]*)?
211
- (?:[ \t]*(?:Z|[-+][0-9][0-9]?(?::[0-9][0-9])?))?)$''', re.X),
212
- list(u'0123456789'))
213
-
214
-Resolver.add_implicit_resolver(
215
- u'tag:yaml.org,2002:value',
216
- re.compile(ur'^(?:=)$'),
217
- [u'='])
218
-
219
-# The following resolver is only for documentation purposes. It cannot work
220
-# because plain scalars cannot start with '!', '&', or '*'.
221
-Resolver.add_implicit_resolver(
222
- u'tag:yaml.org,2002:yaml',
223
- re.compile(ur'^(?:!|&|\*)$'),
224
- list(u'!&*'))
225
-
src/collectors/python.d.plugin/python_modules/pyyaml2/scanner.py
deleted
-1458
@@ -1,1458 +0,0 @@
1
-# SPDX-License-Identifier: MIT
2
-
3
-# Scanner produces tokens of the following types:
4
-# STREAM-START
5
-# STREAM-END
6
-# DIRECTIVE(name, value)
7
-# DOCUMENT-START
8
-# DOCUMENT-END
9
-# BLOCK-SEQUENCE-START
10
-# BLOCK-MAPPING-START
11
-# BLOCK-END
12
-# FLOW-SEQUENCE-START
13
-# FLOW-MAPPING-START
14
-# FLOW-SEQUENCE-END
15
-# FLOW-MAPPING-END
16
-# BLOCK-ENTRY
17
-# FLOW-ENTRY
18
-# KEY
19
-# VALUE
20
-# ALIAS(value)
21
-# ANCHOR(value)
22
-# TAG(value)
23
-# SCALAR(value, plain, style)
24
-#
25
-# Read comments in the Scanner code for more details.
26
-#
27
-
28
-__all__ = ['Scanner', 'ScannerError']
29
-
30
-from error import MarkedYAMLError
31
-from tokens import *
32
-
33
-class ScannerError(MarkedYAMLError):
34
- pass
35
-
36
-class SimpleKey(object):
37
- # See below simple keys treatment.
38
-
39
- def __init__(self, token_number, required, index, line, column, mark):
40
- self.token_number = token_number
41
- self.required = required
42
- self.index = index
43
- self.line = line
44
- self.column = column
45
- self.mark = mark
46
-
47
-class Scanner(object):
48
-
49
- def __init__(self):
50
- """Initialize the scanner."""
51
- # It is assumed that Scanner and Reader will have a common descendant.
52
- # Reader do the dirty work of checking for BOM and converting the
53
- # input data to Unicode. It also adds NUL to the end.
54
- #
55
- # Reader supports the following methods
56
- # self.peek(i=0) # peek the next i-th character
57
- # self.prefix(l=1) # peek the next l characters
58
- # self.forward(l=1) # read the next l characters and move the pointer.
59
-
60
- # Had we reached the end of the stream?
61
- self.done = False
62
-
63
- # The number of unclosed '{' and '['. `flow_level == 0` means block
64
- # context.
65
- self.flow_level = 0
66
-
67
- # List of processed tokens that are not yet emitted.
68
- self.tokens = []
69
-
70
- # Add the STREAM-START token.
71
- self.fetch_stream_start()
72
-
73
- # Number of tokens that were emitted through the `get_token` method.
74
- self.tokens_taken = 0
75
-
76
- # The current indentation level.
77
- self.indent = -1
78
-
79
- # Past indentation levels.
80
- self.indents = []
81
-
82
- # Variables related to simple keys treatment.
83
-
84
- # A simple key is a key that is not denoted by the '?' indicator.
85
- # Example of simple keys:
86
- # ---
87
- # block simple key: value
88
- # ? not a simple key:
89
- # : { flow simple key: value }
90
- # We emit the KEY token before all keys, so when we find a potential
91
- # simple key, we try to locate the corresponding ':' indicator.
92
- # Simple keys should be limited to a single line and 1024 characters.
93
-
94
- # Can a simple key start at the current position? A simple key may
95
- # start:
96
- # - at the beginning of the line, not counting indentation spaces
97
- # (in block context),
98
- # - after '{', '[', ',' (in the flow context),
99
- # - after '?', ':', '-' (in the block context).
100
- # In the block context, this flag also signifies if a block collection
101
- # may start at the current position.
102
- self.allow_simple_key = True
103
-
104
- # Keep track of possible simple keys. This is a dictionary. The key
105
- # is `flow_level`; there can be no more that one possible simple key
106
- # for each level. The value is a SimpleKey record:
107
- # (token_number, required, index, line, column, mark)
108
- # A simple key may start with ALIAS, ANCHOR, TAG, SCALAR(flow),
109
- # '[', or '{' tokens.
110
- self.possible_simple_keys = {}
111
-
112
- # Public methods.
113
-
114
- def check_token(self, *choices):
115
- # Check if the next token is one of the given types.
116
- while self.need_more_tokens():
117
- self.fetch_more_tokens()
118
- if self.tokens:
119
- if not choices:
120
- return True
121
- for choice in choices:
122
- if isinstance(self.tokens[0], choice):
123
- return True
124
- return False
125
-
126
- def peek_token(self):
127
- # Return the next token, but do not delete if from the queue.
128
- while self.need_more_tokens():
129
- self.fetch_more_tokens()
130
- if self.tokens:
131
- return self.tokens[0]
132
-
133
- def get_token(self):
134
- # Return the next token.
135
- while self.need_more_tokens():
136
- self.fetch_more_tokens()
137
- if self.tokens:
138
- self.tokens_taken += 1
139
- return self.tokens.pop(0)
140
-
141
- # Private methods.
142
-
143
- def need_more_tokens(self):
144
- if self.done:
145
- return False
146
- if not self.tokens:
147
- return True
148
- # The current token may be a potential simple key, so we
149
- # need to look further.
150
- self.stale_possible_simple_keys()
151
- if self.next_possible_simple_key() == self.tokens_taken:
152
- return True
153
-
154
- def fetch_more_tokens(self):
155
-
156
- # Eat whitespaces and comments until we reach the next token.
157
- self.scan_to_next_token()
158
-
159
- # Remove obsolete possible simple keys.
160
- self.stale_possible_simple_keys()
161
-
162
- # Compare the current indentation and column. It may add some tokens
163
- # and decrease the current indentation level.
164
- self.unwind_indent(self.column)
165
-
166
- # Peek the next character.
167
- ch = self.peek()
168
-
169
- # Is it the end of stream?
170
- if ch == u'\0':
171
- return self.fetch_stream_end()
172
-
173
- # Is it a directive?
174
- if ch == u'%' and self.check_directive():
175
- return self.fetch_directive()
176
-
177
- # Is it the document start?
178
- if ch == u'-' and self.check_document_start():
179
- return self.fetch_document_start()
180
-
181
- # Is it the document end?
182
- if ch == u'.' and self.check_document_end():
183
- return self.fetch_document_end()
184
-
185
- # TODO: support for BOM within a stream.
186
- #if ch == u'\uFEFF':
187
- # return self.fetch_bom() <-- issue BOMToken
188
-
189
- # Note: the order of the following checks is NOT significant.
190
-
191
- # Is it the flow sequence start indicator?
192
- if ch == u'[':
193
- return self.fetch_flow_sequence_start()
194
-
195
- # Is it the flow mapping start indicator?
196
- if ch == u'{':
197
- return self.fetch_flow_mapping_start()
198
-
199
- # Is it the flow sequence end indicator?
200
- if ch == u']':
201
- return self.fetch_flow_sequence_end()
202
-
203
- # Is it the flow mapping end indicator?
204
- if ch == u'}':
205
- return self.fetch_flow_mapping_end()
206
-
207
- # Is it the flow entry indicator?
208
- if ch == u',':
209
- return self.fetch_flow_entry()
210
-
211
- # Is it the block entry indicator?
212
- if ch == u'-' and self.check_block_entry():
213
- return self.fetch_block_entry()
214
-
215
- # Is it the key indicator?
216
- if ch == u'?' and self.check_key():
217
- return self.fetch_key()
218
-
219
- # Is it the value indicator?
220
- if ch == u':' and self.check_value():
221
- return self.fetch_value()
222
-
223
- # Is it an alias?
224
- if ch == u'*':
225
- return self.fetch_alias()
226
-
227
- # Is it an anchor?
228
- if ch == u'&':
229
- return self.fetch_anchor()
230
-
231
- # Is it a tag?
232
- if ch == u'!':
233
- return self.fetch_tag()
234
-
235
- # Is it a literal scalar?
236
- if ch == u'|' and not self.flow_level:
237
- return self.fetch_literal()
238
-
239
- # Is it a folded scalar?
240
- if ch == u'>' and not self.flow_level:
241
- return self.fetch_folded()
242
-
243
- # Is it a single quoted scalar?
244
- if ch == u'\'':
245
- return self.fetch_single()
246
-
247
- # Is it a double quoted scalar?
248
- if ch == u'\"':
249
- return self.fetch_double()
250
-
251
- # It must be a plain scalar then.
252
- if self.check_plain():
253
- return self.fetch_plain()
254
-
255
- # No? It's an error. Let's produce a nice error message.
256
- raise ScannerError("while scanning for the next token", None,
257
- "found character %r that cannot start any token"
258
- % ch.encode('utf-8'), self.get_mark())
259
-
260
- # Simple keys treatment.
261
-
262
- def next_possible_simple_key(self):
263
- # Return the number of the nearest possible simple key. Actually we
264
- # don't need to loop through the whole dictionary. We may replace it
265
- # with the following code:
266
- # if not self.possible_simple_keys:
267
- # return None
268
- # return self.possible_simple_keys[
269
- # min(self.possible_simple_keys.keys())].token_number
270
- min_token_number = None
271
- for level in self.possible_simple_keys:
272
- key = self.possible_simple_keys[level]
273
- if min_token_number is None or key.token_number < min_token_number:
274
- min_token_number = key.token_number
275
- return min_token_number
276
-
277
- def stale_possible_simple_keys(self):
278
- # Remove entries that are no longer possible simple keys. According to
279
- # the YAML specification, simple keys
280
- # - should be limited to a single line,
281
- # - should be no longer than 1024 characters.
282
- # Disabling this procedure will allow simple keys of any length and
283
- # height (may cause problems if indentation is broken though).
284
- for level in self.possible_simple_keys.keys():
285
- key = self.possible_simple_keys[level]
286
- if key.line != self.line \
287
- or self.index-key.index > 1024:
288
- if key.required:
289
- raise ScannerError("while scanning a simple key", key.mark,
290
- "could not found expected ':'", self.get_mark())
291
- del self.possible_simple_keys[level]
292
-
293
- def save_possible_simple_key(self):
294
- # The next token may start a simple key. We check if it's possible
295
- # and save its position. This function is called for
296
- # ALIAS, ANCHOR, TAG, SCALAR(flow), '[', and '{'.
297
-
298
- # Check if a simple key is required at the current position.
299
- required = not self.flow_level and self.indent == self.column
300
-
301
- # A simple key is required only if it is the first token in the current
302
- # line. Therefore it is always allowed.
303
- assert self.allow_simple_key or not required
304
-
305
- # The next token might be a simple key. Let's save it's number and
306
- # position.
307
- if self.allow_simple_key:
308
- self.remove_possible_simple_key()
309
- token_number = self.tokens_taken+len(self.tokens)
310
- key = SimpleKey(token_number, required,
311
- self.index, self.line, self.column, self.get_mark())
312
- self.possible_simple_keys[self.flow_level] = key
313
-
314
- def remove_possible_simple_key(self):
315
- # Remove the saved possible key position at the current flow level.
316
- if self.flow_level in self.possible_simple_keys:
317
- key = self.possible_simple_keys[self.flow_level]
318
-
319
- if key.required:
320
- raise ScannerError("while scanning a simple key", key.mark,
321
- "could not found expected ':'", self.get_mark())
322
-
323
- del self.possible_simple_keys[self.flow_level]
324
-
325
- # Indentation functions.
326
-
327
- def unwind_indent(self, column):
328
-
329
- ## In flow context, tokens should respect indentation.
330
- ## Actually the condition should be `self.indent >= column` according to
331
- ## the spec. But this condition will prohibit intuitively correct
332
- ## constructions such as
333
- ## key : {
334
- ## }
335
- #if self.flow_level and self.indent > column:
336
- # raise ScannerError(None, None,
337
- # "invalid intendation or unclosed '[' or '{'",
338
- # self.get_mark())
339
-
340
- # In the flow context, indentation is ignored. We make the scanner less
341
- # restrictive then specification requires.
342
- if self.flow_level:
343
- return
344
-
345
- # In block context, we may need to issue the BLOCK-END tokens.
346
- while self.indent > column:
347
- mark = self.get_mark()
348
- self.indent = self.indents.pop()
349
- self.tokens.append(BlockEndToken(mark, mark))
350
-
351
- def add_indent(self, column):
352
- # Check if we need to increase indentation.
353
- if self.indent < column:
354
- self.indents.append(self.indent)
355
- self.indent = column
356
- return True
357
- return False
358
-
359
- # Fetchers.
360
-
361
- def fetch_stream_start(self):
362
- # We always add STREAM-START as the first token and STREAM-END as the
363
- # last token.
364
-
365
- # Read the token.
366
- mark = self.get_mark()
367
-
368
- # Add STREAM-START.
369
- self.tokens.append(StreamStartToken(mark, mark,
370
- encoding=self.encoding))
371
-
372
-
373
- def fetch_stream_end(self):
374
-
375
- # Set the current intendation to -1.
376
- self.unwind_indent(-1)
377
-
378
- # Reset simple keys.
379
- self.remove_possible_simple_key()
380
- self.allow_simple_key = False
381
- self.possible_simple_keys = {}
382
-
383
- # Read the token.
384
- mark = self.get_mark()
385
-
386
- # Add STREAM-END.
387
- self.tokens.append(StreamEndToken(mark, mark))
388
-
389
- # The steam is finished.
390
- self.done = True
391
-
392
- def fetch_directive(self):
393
-
394
- # Set the current intendation to -1.
395
- self.unwind_indent(-1)
396
-
397
- # Reset simple keys.
398
- self.remove_possible_simple_key()
399
- self.allow_simple_key = False
400
-
401
- # Scan and add DIRECTIVE.
402
- self.tokens.append(self.scan_directive())
403
-
404
- def fetch_document_start(self):
405
- self.fetch_document_indicator(DocumentStartToken)
406
-
407
- def fetch_document_end(self):
408
- self.fetch_document_indicator(DocumentEndToken)
409
-
410
- def fetch_document_indicator(self, TokenClass):
411
-
412
- # Set the current intendation to -1.
413
- self.unwind_indent(-1)
414
-
415
- # Reset simple keys. Note that there could not be a block collection
416
- # after '---'.
417
- self.remove_possible_simple_key()
418
- self.allow_simple_key = False
419
-
420
- # Add DOCUMENT-START or DOCUMENT-END.
421
- start_mark = self.get_mark()
422
- self.forward(3)
423
- end_mark = self.get_mark()
424
- self.tokens.append(TokenClass(start_mark, end_mark))
425
-
426
- def fetch_flow_sequence_start(self):
427
- self.fetch_flow_collection_start(FlowSequenceStartToken)
428
-
429
- def fetch_flow_mapping_start(self):
430
- self.fetch_flow_collection_start(FlowMappingStartToken)
431
-
432
- def fetch_flow_collection_start(self, TokenClass):
433
-
434
- # '[' and '{' may start a simple key.
435
- self.save_possible_simple_key()
436
-
437
- # Increase the flow level.
438
- self.flow_level += 1
439
-
440
- # Simple keys are allowed after '[' and '{'.
441
- self.allow_simple_key = True
442
-
443
- # Add FLOW-SEQUENCE-START or FLOW-MAPPING-START.
444
- start_mark = self.get_mark()
445
- self.forward()
446
- end_mark = self.get_mark()
447
- self.tokens.append(TokenClass(start_mark, end_mark))
448
-
449
- def fetch_flow_sequence_end(self):
450
- self.fetch_flow_collection_end(FlowSequenceEndToken)
451
-
452
- def fetch_flow_mapping_end(self):
453
- self.fetch_flow_collection_end(FlowMappingEndToken)
454
-
455
- def fetch_flow_collection_end(self, TokenClass):
456
-
457
- # Reset possible simple key on the current level.
458
- self.remove_possible_simple_key()
459
-
460
- # Decrease the flow level.
461
- self.flow_level -= 1
462
-
463
- # No simple keys after ']' or '}'.
464
- self.allow_simple_key = False
465
-
466
- # Add FLOW-SEQUENCE-END or FLOW-MAPPING-END.
467
- start_mark = self.get_mark()
468
- self.forward()
469
- end_mark = self.get_mark()
470
- self.tokens.append(TokenClass(start_mark, end_mark))
471
-
472
- def fetch_flow_entry(self):
473
-
474
- # Simple keys are allowed after ','.
475
- self.allow_simple_key = True
476
-
477
- # Reset possible simple key on the current level.
478
- self.remove_possible_simple_key()
479
-
480
- # Add FLOW-ENTRY.
481
- start_mark = self.get_mark()
482
- self.forward()
483
- end_mark = self.get_mark()
484
- self.tokens.append(FlowEntryToken(start_mark, end_mark))
485
-
486
- def fetch_block_entry(self):
487
-
488
- # Block context needs additional checks.
489
- if not self.flow_level:
490
-
491
- # Are we allowed to start a new entry?
492
- if not self.allow_simple_key:
493
- raise ScannerError(None, None,
494
- "sequence entries are not allowed here",
495
- self.get_mark())
496
-
497
- # We may need to add BLOCK-SEQUENCE-START.
498
- if self.add_indent(self.column):
499
- mark = self.get_mark()
500
- self.tokens.append(BlockSequenceStartToken(mark, mark))
501
-
502
- # It's an error for the block entry to occur in the flow context,
503
- # but we let the parser detect this.
504
- else:
505
- pass
506
-
507
- # Simple keys are allowed after '-'.
508
- self.allow_simple_key = True
509
-
510
- # Reset possible simple key on the current level.
511
- self.remove_possible_simple_key()
512
-
513
- # Add BLOCK-ENTRY.
514
- start_mark = self.get_mark()
515
- self.forward()
516
- end_mark = self.get_mark()
517
- self.tokens.append(BlockEntryToken(start_mark, end_mark))
518
-
519
- def fetch_key(self):
520
-
521
- # Block context needs additional checks.
522
- if not self.flow_level:
523
-
524
- # Are we allowed to start a key (not nessesary a simple)?
525
- if not self.allow_simple_key:
526
- raise ScannerError(None, None,
527
- "mapping keys are not allowed here",
528
- self.get_mark())
529
-
530
- # We may need to add BLOCK-MAPPING-START.
531
- if self.add_indent(self.column):
532
- mark = self.get_mark()
533
- self.tokens.append(BlockMappingStartToken(mark, mark))
534
-
535
- # Simple keys are allowed after '?' in the block context.
536
- self.allow_simple_key = not self.flow_level
537
-
538
- # Reset possible simple key on the current level.
539
- self.remove_possible_simple_key()
540
-
541
- # Add KEY.
542
- start_mark = self.get_mark()
543
- self.forward()
544
- end_mark = self.get_mark()
545
- self.tokens.append(KeyToken(start_mark, end_mark))
546
-
547
- def fetch_value(self):
548
-
549
- # Do we determine a simple key?
550
- if self.flow_level in self.possible_simple_keys:
551
-
552
- # Add KEY.
553
- key = self.possible_simple_keys[self.flow_level]
554
- del self.possible_simple_keys[self.flow_level]
555
- self.tokens.insert(key.token_number-self.tokens_taken,
556
- KeyToken(key.mark, key.mark))
557
-
558
- # If this key starts a new block mapping, we need to add
559
- # BLOCK-MAPPING-START.
560
- if not self.flow_level:
561
- if self.add_indent(key.column):
562
- self.tokens.insert(key.token_number-self.tokens_taken,
563
- BlockMappingStartToken(key.mark, key.mark))
564
-
565
- # There cannot be two simple keys one after another.
566
- self.allow_simple_key = False
567
-
568
- # It must be a part of a complex key.
569
- else:
570
-
571
- # Block context needs additional checks.
572
- # (Do we really need them? They will be catched by the parser
573
- # anyway.)
574
- if not self.flow_level:
575
-
576
- # We are allowed to start a complex value if and only if
577
- # we can start a simple key.
578
- if not self.allow_simple_key:
579
- raise ScannerError(None, None,
580
- "mapping values are not allowed here",
581
- self.get_mark())
582
-
583
- # If this value starts a new block mapping, we need to add
584
- # BLOCK-MAPPING-START. It will be detected as an error later by
585
- # the parser.
586
- if not self.flow_level:
587
- if self.add_indent(self.column):
588
- mark = self.get_mark()
589
- self.tokens.append(BlockMappingStartToken(mark, mark))
590
-
591
- # Simple keys are allowed after ':' in the block context.
592
- self.allow_simple_key = not self.flow_level
593
-
594
- # Reset possible simple key on the current level.
595
- self.remove_possible_simple_key()
596
-
597
- # Add VALUE.
598
- start_mark = self.get_mark()
599
- self.forward()
600
- end_mark = self.get_mark()
601
- self.tokens.append(ValueToken(start_mark, end_mark))
602
-
603
- def fetch_alias(self):
604
-
605
- # ALIAS could be a simple key.
606
- self.save_possible_simple_key()
607
-
608
- # No simple keys after ALIAS.
609
- self.allow_simple_key = False
610
-
611
- # Scan and add ALIAS.
612
- self.tokens.append(self.scan_anchor(AliasToken))
613
-
614
- def fetch_anchor(self):
615
-
616
- # ANCHOR could start a simple key.
617
- self.save_possible_simple_key()
618
-
619
- # No simple keys after ANCHOR.
620
- self.allow_simple_key = False
621
-
622
- # Scan and add ANCHOR.
623
- self.tokens.append(self.scan_anchor(AnchorToken))
624
-
625
- def fetch_tag(self):
626
-
627
- # TAG could start a simple key.
628
- self.save_possible_simple_key()
629
-
630
- # No simple keys after TAG.
631
- self.allow_simple_key = False
632
-
633
- # Scan and add TAG.
634
- self.tokens.append(self.scan_tag())
635
-
636
- def fetch_literal(self):
637
- self.fetch_block_scalar(style='|')
638
-
639
- def fetch_folded(self):
640
- self.fetch_block_scalar(style='>')
641
-
642
- def fetch_block_scalar(self, style):
643
-
644
- # A simple key may follow a block scalar.
645
- self.allow_simple_key = True
646
-
647
- # Reset possible simple key on the current level.
648
- self.remove_possible_simple_key()
649
-
650
- # Scan and add SCALAR.
651
- self.tokens.append(self.scan_block_scalar(style))
652
-
653
- def fetch_single(self):
654
- self.fetch_flow_scalar(style='\'')
655
-
656
- def fetch_double(self):
657
- self.fetch_flow_scalar(style='"')
658
-
659
- def fetch_flow_scalar(self, style):
660
-
661
- # A flow scalar could be a simple key.
662
- self.save_possible_simple_key()
663
-
664
- # No simple keys after flow scalars.
665
- self.allow_simple_key = False
666
-
667
- # Scan and add SCALAR.
668
- self.tokens.append(self.scan_flow_scalar(style))
669
-
670
- def fetch_plain(self):
671
-
672
- # A plain scalar could be a simple key.
673
- self.save_possible_simple_key()
674
-
675
- # No simple keys after plain scalars. But note that `scan_plain` will
676
- # change this flag if the scan is finished at the beginning of the
677
- # line.
678
- self.allow_simple_key = False
679
-
680
- # Scan and add SCALAR. May change `allow_simple_key`.
681
- self.tokens.append(self.scan_plain())
682
-
683
- # Checkers.
684
-
685
- def check_directive(self):
686
-
687
- # DIRECTIVE: ^ '%' ...
688
- # The '%' indicator is already checked.
689
- if self.column == 0:
690
- return True
691
-
692
- def check_document_start(self):
693
-
694
- # DOCUMENT-START: ^ '---' (' '|'\n')
695
- if self.column == 0:
696
- if self.prefix(3) == u'---' \
697
- and self.peek(3) in u'\0 \t\r\n\x85\u2028\u2029':
698
- return True
699
-
700
- def check_document_end(self):
701
-
702
- # DOCUMENT-END: ^ '...' (' '|'\n')
703
- if self.column == 0:
704
- if self.prefix(3) == u'...' \
705
- and self.peek(3) in u'\0 \t\r\n\x85\u2028\u2029':
706
- return True
707
-
708
- def check_block_entry(self):
709
-
710
- # BLOCK-ENTRY: '-' (' '|'\n')
711
- return self.peek(1) in u'\0 \t\r\n\x85\u2028\u2029'
712
-
713
- def check_key(self):
714
-
715
- # KEY(flow context): '?'
716
- if self.flow_level:
717
- return True
718
-
719
- # KEY(block context): '?' (' '|'\n')
720
- else:
721
- return self.peek(1) in u'\0 \t\r\n\x85\u2028\u2029'
722
-
723
- def check_value(self):
724
-
725
- # VALUE(flow context): ':'
726
- if self.flow_level:
727
- return True
728
-
729
- # VALUE(block context): ':' (' '|'\n')
730
- else:
731
- return self.peek(1) in u'\0 \t\r\n\x85\u2028\u2029'
732
-
733
- def check_plain(self):
734
-
735
- # A plain scalar may start with any non-space character except:
736
- # '-', '?', ':', ',', '[', ']', '{', '}',
737
- # '#', '&', '*', '!', '|', '>', '\'', '\"',
738
- # '%', '@', '`'.
739
- #
740
- # It may also start with
741
- # '-', '?', ':'
742
- # if it is followed by a non-space character.
743
- #
744
- # Note that we limit the last rule to the block context (except the
745
- # '-' character) because we want the flow context to be space
746
- # independent.
747
- ch = self.peek()
748
- return ch not in u'\0 \t\r\n\x85\u2028\u2029-?:,[]{}#&*!|>\'\"%@`' \
749
- or (self.peek(1) not in u'\0 \t\r\n\x85\u2028\u2029'
750
- and (ch == u'-' or (not self.flow_level and ch in u'?:')))
751
-
752
- # Scanners.
753
-
754
- def scan_to_next_token(self):
755
- # We ignore spaces, line breaks and comments.
756
- # If we find a line break in the block context, we set the flag
757
- # `allow_simple_key` on.
758
- # The byte order mark is stripped if it's the first character in the
759
- # stream. We do not yet support BOM inside the stream as the
760
- # specification requires. Any such mark will be considered as a part
761
- # of the document.
762
- #
763
- # TODO: We need to make tab handling rules more sane. A good rule is
764
- # Tabs cannot precede tokens
765
- # BLOCK-SEQUENCE-START, BLOCK-MAPPING-START, BLOCK-END,
766
- # KEY(block), VALUE(block), BLOCK-ENTRY
767
- # So the checking code is
768
- # if <TAB>:
769
- # self.allow_simple_keys = False
770
- # We also need to add the check for `allow_simple_keys == True` to
771
- # `unwind_indent` before issuing BLOCK-END.
772
- # Scanners for block, flow, and plain scalars need to be modified.
773
-
774
- if self.index == 0 and self.peek() == u'\uFEFF':
775
- self.forward()
776
- found = False
777
- while not found:
778
- while self.peek() == u' ':
779
- self.forward()
780
- if self.peek() == u'#':
781
- while self.peek() not in u'\0\r\n\x85\u2028\u2029':
782
- self.forward()
783
- if self.scan_line_break():
784
- if not self.flow_level:
785
- self.allow_simple_key = True
786
- else:
787
- found = True
788
-
789
- def scan_directive(self):
790
- # See the specification for details.
791
- start_mark = self.get_mark()
792
- self.forward()
793
- name = self.scan_directive_name(start_mark)
794
- value = None
795
- if name == u'YAML':
796
- value = self.scan_yaml_directive_value(start_mark)
797
- end_mark = self.get_mark()
798
- elif name == u'TAG':
799
- value = self.scan_tag_directive_value(start_mark)
800
- end_mark = self.get_mark()
801
- else:
802
- end_mark = self.get_mark()
803
- while self.peek() not in u'\0\r\n\x85\u2028\u2029':
804
- self.forward()
805
- self.scan_directive_ignored_line(start_mark)
806
- return DirectiveToken(name, value, start_mark, end_mark)
807
-
808
- def scan_directive_name(self, start_mark):
809
- # See the specification for details.
810
- length = 0
811
- ch = self.peek(length)
812
- while u'0' <= ch <= u'9' or u'A' <= ch <= u'Z' or u'a' <= ch <= u'z' \
813
- or ch in u'-_':
814
- length += 1
815
- ch = self.peek(length)
816
- if not length:
817
- raise ScannerError("while scanning a directive", start_mark,
818
- "expected alphabetic or numeric character, but found %r"
819
- % ch.encode('utf-8'), self.get_mark())
820
- value = self.prefix(length)
821
- self.forward(length)
822
- ch = self.peek()
823
- if ch not in u'\0 \r\n\x85\u2028\u2029':
824
- raise ScannerError("while scanning a directive", start_mark,
825
- "expected alphabetic or numeric character, but found %r"
826
- % ch.encode('utf-8'), self.get_mark())
827
- return value
828
-
829
- def scan_yaml_directive_value(self, start_mark):
830
- # See the specification for details.
831
- while self.peek() == u' ':
832
- self.forward()
833
- major = self.scan_yaml_directive_number(start_mark)
834
- if self.peek() != '.':
835
- raise ScannerError("while scanning a directive", start_mark,
836
- "expected a digit or '.', but found %r"
837
- % self.peek().encode('utf-8'),
838
- self.get_mark())
839
- self.forward()
840
- minor = self.scan_yaml_directive_number(start_mark)
841
- if self.peek() not in u'\0 \r\n\x85\u2028\u2029':
842
- raise ScannerError("while scanning a directive", start_mark,
843
- "expected a digit or ' ', but found %r"
844
- % self.peek().encode('utf-8'),
845
- self.get_mark())
846
- return (major, minor)
847
-
848
- def scan_yaml_directive_number(self, start_mark):
849
- # See the specification for details.
850
- ch = self.peek()
851
- if not (u'0' <= ch <= u'9'):
852
- raise ScannerError("while scanning a directive", start_mark,
853
- "expected a digit, but found %r" % ch.encode('utf-8'),
854
- self.get_mark())
855
- length = 0
856
- while u'0' <= self.peek(length) <= u'9':
857
- length += 1
858
- value = int(self.prefix(length))
859
- self.forward(length)
860
- return value
861
-
862
- def scan_tag_directive_value(self, start_mark):
863
- # See the specification for details.
864
- while self.peek() == u' ':
865
- self.forward()
866
- handle = self.scan_tag_directive_handle(start_mark)
867
- while self.peek() == u' ':
868
- self.forward()
869
- prefix = self.scan_tag_directive_prefix(start_mark)
870
- return (handle, prefix)
871
-
872
- def scan_tag_directive_handle(self, start_mark):
873
- # See the specification for details.
874
- value = self.scan_tag_handle('directive', start_mark)
875
- ch = self.peek()
876
- if ch != u' ':
877
- raise ScannerError("while scanning a directive", start_mark,
878
- "expected ' ', but found %r" % ch.encode('utf-8'),
879
- self.get_mark())
880
- return value
881
-
882
- def scan_tag_directive_prefix(self, start_mark):
883
- # See the specification for details.
884
- value = self.scan_tag_uri('directive', start_mark)
885
- ch = self.peek()
886
- if ch not in u'\0 \r\n\x85\u2028\u2029':
887
- raise ScannerError("while scanning a directive", start_mark,
888
- "expected ' ', but found %r" % ch.encode('utf-8'),
889
- self.get_mark())
890
- return value
891
-
892
- def scan_directive_ignored_line(self, start_mark):
893
- # See the specification for details.
894
- while self.peek() == u' ':
895
- self.forward()
896
- if self.peek() == u'#':
897
- while self.peek() not in u'\0\r\n\x85\u2028\u2029':
898
- self.forward()
899
- ch = self.peek()
900
- if ch not in u'\0\r\n\x85\u2028\u2029':
901
- raise ScannerError("while scanning a directive", start_mark,
902
- "expected a comment or a line break, but found %r"
903
- % ch.encode('utf-8'), self.get_mark())
904
- self.scan_line_break()
905
-
906
- def scan_anchor(self, TokenClass):
907
- # The specification does not restrict characters for anchors and
908
- # aliases. This may lead to problems, for instance, the document:
909
- # [ *alias, value ]
910
- # can be interpteted in two ways, as
911
- # [ "value" ]
912
- # and
913
- # [ *alias , "value" ]
914
- # Therefore we restrict aliases to numbers and ASCII letters.
915
- start_mark = self.get_mark()
916
- indicator = self.peek()
917
- if indicator == u'*':
918
- name = 'alias'
919
- else:
920
- name = 'anchor'
921
- self.forward()
922
- length = 0
923
- ch = self.peek(length)
924
- while u'0' <= ch <= u'9' or u'A' <= ch <= u'Z' or u'a' <= ch <= u'z' \
925
- or ch in u'-_':
926
- length += 1
927
- ch = self.peek(length)
928
- if not length:
929
- raise ScannerError("while scanning an %s" % name, start_mark,
930
- "expected alphabetic or numeric character, but found %r"
931
- % ch.encode('utf-8'), self.get_mark())
932
- value = self.prefix(length)
933
- self.forward(length)
934
- ch = self.peek()
935
- if ch not in u'\0 \t\r\n\x85\u2028\u2029?:,]}%@`':
936
- raise ScannerError("while scanning an %s" % name, start_mark,
937
- "expected alphabetic or numeric character, but found %r"
938
- % ch.encode('utf-8'), self.get_mark())
939
- end_mark = self.get_mark()
940
- return TokenClass(value, start_mark, end_mark)
941
-
942
- def scan_tag(self):
943
- # See the specification for details.
944
- start_mark = self.get_mark()
945
- ch = self.peek(1)
946
- if ch == u'<':
947
- handle = None
948
- self.forward(2)
949
- suffix = self.scan_tag_uri('tag', start_mark)
950
- if self.peek() != u'>':
951
- raise ScannerError("while parsing a tag", start_mark,
952
- "expected '>', but found %r" % self.peek().encode('utf-8'),
953
- self.get_mark())
954
- self.forward()
955
- elif ch in u'\0 \t\r\n\x85\u2028\u2029':
956
- handle = None
957
- suffix = u'!'
958
- self.forward()
959
- else:
960
- length = 1
961
- use_handle = False
962
- while ch not in u'\0 \r\n\x85\u2028\u2029':
963
- if ch == u'!':
964
- use_handle = True
965
- break
966
- length += 1
967
- ch = self.peek(length)
968
- handle = u'!'
969
- if use_handle:
970
- handle = self.scan_tag_handle('tag', start_mark)
971
- else:
972
- handle = u'!'
973
- self.forward()
974
- suffix = self.scan_tag_uri('tag', start_mark)
975
- ch = self.peek()
976
- if ch not in u'\0 \r\n\x85\u2028\u2029':
977
- raise ScannerError("while scanning a tag", start_mark,
978
- "expected ' ', but found %r" % ch.encode('utf-8'),
979
- self.get_mark())
980
- value = (handle, suffix)
981
- end_mark = self.get_mark()
982
- return TagToken(value, start_mark, end_mark)
983
-
984
- def scan_block_scalar(self, style):
985
- # See the specification for details.
986
-
987
- if style == '>':
988
- folded = True
989
- else:
990
- folded = False
991
-
992
- chunks = []
993
- start_mark = self.get_mark()
994
-
995
- # Scan the header.
996
- self.forward()
997
- chomping, increment = self.scan_block_scalar_indicators(start_mark)
998
- self.scan_block_scalar_ignored_line(start_mark)
999
-
1000
- # Determine the indentation level and go to the first non-empty line.
1001
- min_indent = self.indent+1
1002
- if min_indent < 1:
1003
- min_indent = 1
1004
- if increment is None:
1005
- breaks, max_indent, end_mark = self.scan_block_scalar_indentation()
1006
- indent = max(min_indent, max_indent)
1007
- else:
1008
- indent = min_indent+increment-1
1009
- breaks, end_mark = self.scan_block_scalar_breaks(indent)
1010
- line_break = u''
1011
-
1012
- # Scan the inner part of the block scalar.
1013
- while self.column == indent and self.peek() != u'\0':
1014
- chunks.extend(breaks)
1015
- leading_non_space = self.peek() not in u' \t'
1016
- length = 0
1017
- while self.peek(length) not in u'\0\r\n\x85\u2028\u2029':
1018
- length += 1
1019
- chunks.append(self.prefix(length))
1020
- self.forward(length)
1021
- line_break = self.scan_line_break()
1022
- breaks, end_mark = self.scan_block_scalar_breaks(indent)
1023
- if self.column == indent and self.peek() != u'\0':
1024
-
1025
- # Unfortunately, folding rules are ambiguous.
1026
- #
1027
- # This is the folding according to the specification:
1028
-
1029
- if folded and line_break == u'\n' \
1030
- and leading_non_space and self.peek() not in u' \t':
1031
- if not breaks:
1032
- chunks.append(u' ')
1033
- else:
1034
- chunks.append(line_break)
1035
-
1036
- # This is Clark Evans's interpretation (also in the spec
1037
- # examples):
1038
- #
1039
- #if folded and line_break == u'\n':
1040
- # if not breaks:
1041
- # if self.peek() not in ' \t':
1042
- # chunks.append(u' ')
1043
- # else:
1044
- # chunks.append(line_break)
1045
- #else:
1046
- # chunks.append(line_break)
1047
- else:
1048
- break
1049
-
1050
- # Chomp the tail.
1051
- if chomping is not False:
1052
- chunks.append(line_break)
1053
- if chomping is True:
1054
- chunks.extend(breaks)
1055
-
1056
- # We are done.
1057
- return ScalarToken(u''.join(chunks), False, start_mark, end_mark,
1058
- style)
1059
-
1060
- def scan_block_scalar_indicators(self, start_mark):
1061
- # See the specification for details.
1062
- chomping = None
1063
- increment = None
1064
- ch = self.peek()
1065
- if ch in u'+-':
1066
- if ch == '+':
1067
- chomping = True
1068
- else:
1069
- chomping = False
1070
- self.forward()
1071
- ch = self.peek()
1072
- if ch in u'0123456789':
1073
- increment = int(ch)
1074
- if increment == 0:
1075
- raise ScannerError("while scanning a block scalar", start_mark,
1076
- "expected indentation indicator in the range 1-9, but found 0",
1077
- self.get_mark())
1078
- self.forward()
1079
- elif ch in u'0123456789':
1080
- increment = int(ch)
1081
- if increment == 0:
1082
- raise ScannerError("while scanning a block scalar", start_mark,
1083
- "expected indentation indicator in the range 1-9, but found 0",
1084
- self.get_mark())
1085
- self.forward()
1086
- ch = self.peek()
1087
- if ch in u'+-':
1088
- if ch == '+':
1089
- chomping = True
1090
- else:
1091
- chomping = False
1092
- self.forward()
1093
- ch = self.peek()
1094
- if ch not in u'\0 \r\n\x85\u2028\u2029':
1095
- raise ScannerError("while scanning a block scalar", start_mark,
1096
- "expected chomping or indentation indicators, but found %r"
1097
- % ch.encode('utf-8'), self.get_mark())
1098
- return chomping, increment
1099
-
1100
- def scan_block_scalar_ignored_line(self, start_mark):
1101
- # See the specification for details.
1102
- while self.peek() == u' ':
1103
- self.forward()
1104
- if self.peek() == u'#':
1105
- while self.peek() not in u'\0\r\n\x85\u2028\u2029':
1106
- self.forward()
1107
- ch = self.peek()
1108
- if ch not in u'\0\r\n\x85\u2028\u2029':
1109
- raise ScannerError("while scanning a block scalar", start_mark,
1110
- "expected a comment or a line break, but found %r"
1111
- % ch.encode('utf-8'), self.get_mark())
1112
- self.scan_line_break()
1113
-
1114
- def scan_block_scalar_indentation(self):
1115
- # See the specification for details.
1116
- chunks = []
1117
- max_indent = 0
1118
- end_mark = self.get_mark()
1119
- while self.peek() in u' \r\n\x85\u2028\u2029':
1120
- if self.peek() != u' ':
1121
- chunks.append(self.scan_line_break())
1122
- end_mark = self.get_mark()
1123
- else:
1124
- self.forward()
1125
- if self.column > max_indent:
1126
- max_indent = self.column
1127
- return chunks, max_indent, end_mark
1128
-
1129
- def scan_block_scalar_breaks(self, indent):
1130
- # See the specification for details.
1131
- chunks = []
1132
- end_mark = self.get_mark()
1133
- while self.column < indent and self.peek() == u' ':
1134
- self.forward()
1135
- while self.peek() in u'\r\n\x85\u2028\u2029':
1136
- chunks.append(self.scan_line_break())
1137
- end_mark = self.get_mark()
1138
- while self.column < indent and self.peek() == u' ':
1139
- self.forward()
1140
- return chunks, end_mark
1141
-
1142
- def scan_flow_scalar(self, style):
1143
- # See the specification for details.
1144
- # Note that we loose indentation rules for quoted scalars. Quoted
1145
- # scalars don't need to adhere indentation because " and ' clearly
1146
- # mark the beginning and the end of them. Therefore we are less
1147
- # restrictive then the specification requires. We only need to check
1148
- # that document separators are not included in scalars.
1149
- if style == '"':
1150
- double = True
1151
- else:
1152
- double = False
1153
- chunks = []
1154
- start_mark = self.get_mark()
1155
- quote = self.peek()
1156
- self.forward()
1157
- chunks.extend(self.scan_flow_scalar_non_spaces(double, start_mark))
1158
- while self.peek() != quote:
1159
- chunks.extend(self.scan_flow_scalar_spaces(double, start_mark))
1160
- chunks.extend(self.scan_flow_scalar_non_spaces(double, start_mark))
1161
- self.forward()
1162
- end_mark = self.get_mark()
1163
- return ScalarToken(u''.join(chunks), False, start_mark, end_mark,
1164
- style)
1165
-
1166
- ESCAPE_REPLACEMENTS = {
1167
- u'0': u'\0',
1168
- u'a': u'\x07',
1169
- u'b': u'\x08',
1170
- u't': u'\x09',
1171
- u'\t': u'\x09',
1172
- u'n': u'\x0A',
1173
- u'v': u'\x0B',
1174
- u'f': u'\x0C',
1175
- u'r': u'\x0D',
1176
- u'e': u'\x1B',
1177
- u' ': u'\x20',
1178
- u'\"': u'\"',
1179
- u'\\': u'\\',
1180
- u'N': u'\x85',
1181
- u'_': u'\xA0',
1182
- u'L': u'\u2028',
1183
- u'P': u'\u2029',
1184
- }
1185
-
1186
- ESCAPE_CODES = {
1187
- u'x': 2,
1188
- u'u': 4,
1189
- u'U': 8,
1190
- }
1191
-
1192
- def scan_flow_scalar_non_spaces(self, double, start_mark):
1193
- # See the specification for details.
1194
- chunks = []
1195
- while True:
1196
- length = 0
1197
- while self.peek(length) not in u'\'\"\\\0 \t\r\n\x85\u2028\u2029':
1198
- length += 1
1199
- if length:
1200
- chunks.append(self.prefix(length))
1201
- self.forward(length)
1202
- ch = self.peek()
1203
- if not double and ch == u'\'' and self.peek(1) == u'\'':
1204
- chunks.append(u'\'')
1205
- self.forward(2)
1206
- elif (double and ch == u'\'') or (not double and ch in u'\"\\'):
1207
- chunks.append(ch)
1208
- self.forward()
1209
- elif double and ch == u'\\':
1210
- self.forward()
1211
- ch = self.peek()
1212
- if ch in self.ESCAPE_REPLACEMENTS:
1213
- chunks.append(self.ESCAPE_REPLACEMENTS[ch])
1214
- self.forward()
1215
- elif ch in self.ESCAPE_CODES:
1216
- length = self.ESCAPE_CODES[ch]
1217
- self.forward()
1218
- for k in range(length):
1219
- if self.peek(k) not in u'0123456789ABCDEFabcdef':
1220
- raise ScannerError("while scanning a double-quoted scalar", start_mark,
1221
- "expected escape sequence of %d hexdecimal numbers, but found %r" %
1222
- (length, self.peek(k).encode('utf-8')), self.get_mark())
1223
- code = int(self.prefix(length), 16)
1224
- chunks.append(unichr(code))
1225
- self.forward(length)
1226
- elif ch in u'\r\n\x85\u2028\u2029':
1227
- self.scan_line_break()
1228
- chunks.extend(self.scan_flow_scalar_breaks(double, start_mark))
1229
- else:
1230
- raise ScannerError("while scanning a double-quoted scalar", start_mark,
1231
- "found unknown escape character %r" % ch.encode('utf-8'), self.get_mark())
1232
- else:
1233
- return chunks
1234
-
1235
- def scan_flow_scalar_spaces(self, double, start_mark):
1236
- # See the specification for details.
1237
- chunks = []
1238
- length = 0
1239
- while self.peek(length) in u' \t':
1240
- length += 1
1241
- whitespaces = self.prefix(length)
1242
- self.forward(length)
1243
- ch = self.peek()
1244
- if ch == u'\0':
1245
- raise ScannerError("while scanning a quoted scalar", start_mark,
1246
- "found unexpected end of stream", self.get_mark())
1247
- elif ch in u'\r\n\x85\u2028\u2029':
1248
- line_break = self.scan_line_break()
1249
- breaks = self.scan_flow_scalar_breaks(double, start_mark)
1250
- if line_break != u'\n':
1251
- chunks.append(line_break)
1252
- elif not breaks:
1253
- chunks.append(u' ')
1254
- chunks.extend(breaks)
1255
- else:
1256
- chunks.append(whitespaces)
1257
- return chunks
1258
-
1259
- def scan_flow_scalar_breaks(self, double, start_mark):
1260
- # See the specification for details.
1261
- chunks = []
1262
- while True:
1263
- # Instead of checking indentation, we check for document
1264
- # separators.
1265
- prefix = self.prefix(3)
1266
- if (prefix == u'---' or prefix == u'...') \
1267
- and self.peek(3) in u'\0 \t\r\n\x85\u2028\u2029':
1268
- raise ScannerError("while scanning a quoted scalar", start_mark,
1269
- "found unexpected document separator", self.get_mark())
1270
- while self.peek() in u' \t':
1271
- self.forward()
1272
- if self.peek() in u'\r\n\x85\u2028\u2029':
1273
- chunks.append(self.scan_line_break())
1274
- else:
1275
- return chunks
1276
-
1277
- def scan_plain(self):
1278
- # See the specification for details.
1279
- # We add an additional restriction for the flow context:
1280
- # plain scalars in the flow context cannot contain ',', ':' and '?'.
1281
- # We also keep track of the `allow_simple_key` flag here.
1282
- # Indentation rules are loosed for the flow context.
1283
- chunks = []
1284
- start_mark = self.get_mark()
1285
- end_mark = start_mark
1286
- indent = self.indent+1
1287
- # We allow zero indentation for scalars, but then we need to check for
1288
- # document separators at the beginning of the line.
1289
- #if indent == 0:
1290
- # indent = 1
1291
- spaces = []
1292
- while True:
1293
- length = 0
1294
- if self.peek() == u'#':
1295
- break
1296
- while True:
1297
- ch = self.peek(length)
1298
- if ch in u'\0 \t\r\n\x85\u2028\u2029' \
1299
- or (not self.flow_level and ch == u':' and
1300
- self.peek(length+1) in u'\0 \t\r\n\x85\u2028\u2029') \
1301
- or (self.flow_level and ch in u',:?[]{}'):
1302
- break
1303
- length += 1
1304
- # It's not clear what we should do with ':' in the flow context.
1305
- if (self.flow_level and ch == u':'
1306
- and self.peek(length+1) not in u'\0 \t\r\n\x85\u2028\u2029,[]{}'):
1307
- self.forward(length)
1308
- raise ScannerError("while scanning a plain scalar", start_mark,
1309
- "found unexpected ':'", self.get_mark(),
1310
- "Please check http://pyyaml.org/wiki/YAMLColonInFlowContext for details.")
1311
- if length == 0:
1312
- break
1313
- self.allow_simple_key = False
1314
- chunks.extend(spaces)
1315
- chunks.append(self.prefix(length))
1316
- self.forward(length)
1317
- end_mark = self.get_mark()
1318
- spaces = self.scan_plain_spaces(indent, start_mark)
1319
- if not spaces or self.peek() == u'#' \
1320
- or (not self.flow_level and self.column < indent):
1321
- break
1322
- return ScalarToken(u''.join(chunks), True, start_mark, end_mark)
1323
-
1324
- def scan_plain_spaces(self, indent, start_mark):
1325
- # See the specification for details.
1326
- # The specification is really confusing about tabs in plain scalars.
1327
- # We just forbid them completely. Do not use tabs in YAML!
1328
- chunks = []
1329
- length = 0
1330
- while self.peek(length) in u' ':
1331
- length += 1
1332
- whitespaces = self.prefix(length)
1333
- self.forward(length)
1334
- ch = self.peek()
1335
- if ch in u'\r\n\x85\u2028\u2029':
1336
- line_break = self.scan_line_break()
1337
- self.allow_simple_key = True
1338
- prefix = self.prefix(3)
1339
- if (prefix == u'---' or prefix == u'...') \
1340
- and self.peek(3) in u'\0 \t\r\n\x85\u2028\u2029':
1341
- return
1342
- breaks = []
1343
- while self.peek() in u' \r\n\x85\u2028\u2029':
1344
- if self.peek() == ' ':
1345
- self.forward()
1346
- else:
1347
- breaks.append(self.scan_line_break())
1348
- prefix = self.prefix(3)
1349
- if (prefix == u'---' or prefix == u'...') \
1350
- and self.peek(3) in u'\0 \t\r\n\x85\u2028\u2029':
1351
- return
1352
- if line_break != u'\n':
1353
- chunks.append(line_break)
1354
- elif not breaks:
1355
- chunks.append(u' ')
1356
- chunks.extend(breaks)
1357
- elif whitespaces:
1358
- chunks.append(whitespaces)
1359
- return chunks
1360
-
1361
- def scan_tag_handle(self, name, start_mark):
1362
- # See the specification for details.
1363
- # For some strange reasons, the specification does not allow '_' in
1364
- # tag handles. I have allowed it anyway.
1365
- ch = self.peek()
1366
- if ch != u'!':
1367
- raise ScannerError("while scanning a %s" % name, start_mark,
1368
- "expected '!', but found %r" % ch.encode('utf-8'),
1369
- self.get_mark())
1370
- length = 1
1371
- ch = self.peek(length)
1372
- if ch != u' ':
1373
- while u'0' <= ch <= u'9' or u'A' <= ch <= u'Z' or u'a' <= ch <= u'z' \
1374
- or ch in u'-_':
1375
- length += 1
1376
- ch = self.peek(length)
1377
- if ch != u'!':
1378
- self.forward(length)
1379
- raise ScannerError("while scanning a %s" % name, start_mark,
1380
- "expected '!', but found %r" % ch.encode('utf-8'),
1381
- self.get_mark())
1382
- length += 1
1383
- value = self.prefix(length)
1384
- self.forward(length)
1385
- return value
1386
-
1387
- def scan_tag_uri(self, name, start_mark):
1388
- # See the specification for details.
1389
- # Note: we do not check if URI is well-formed.
1390
- chunks = []
1391
- length = 0
1392
- ch = self.peek(length)
1393
- while u'0' <= ch <= u'9' or u'A' <= ch <= u'Z' or u'a' <= ch <= u'z' \
1394
- or ch in u'-;/?:@&=+$,_.!~*\'()[]%':
1395
- if ch == u'%':
1396
- chunks.append(self.prefix(length))
1397
- self.forward(length)
1398
- length = 0
1399
- chunks.append(self.scan_uri_escapes(name, start_mark))
1400
- else:
1401
- length += 1
1402
- ch = self.peek(length)
1403
- if length:
1404
- chunks.append(self.prefix(length))
1405
- self.forward(length)
1406
- length = 0
1407
- if not chunks:
1408
- raise ScannerError("while parsing a %s" % name, start_mark,
1409
- "expected URI, but found %r" % ch.encode('utf-8'),
1410
- self.get_mark())
1411
- return u''.join(chunks)
1412
-
1413
- def scan_uri_escapes(self, name, start_mark):
1414
- # See the specification for details.
1415
- bytes = []
1416
- mark = self.get_mark()
1417
- while self.peek() == u'%':
1418
- self.forward()
1419
- for k in range(2):
1420
- if self.peek(k) not in u'0123456789ABCDEFabcdef':
1421
- raise ScannerError("while scanning a %s" % name, start_mark,
1422
- "expected URI escape sequence of 2 hexdecimal numbers, but found %r" %
1423
- (self.peek(k).encode('utf-8')), self.get_mark())
1424
- bytes.append(chr(int(self.prefix(2), 16)))
1425
- self.forward(2)
1426
- try:
1427
- value = unicode(''.join(bytes), 'utf-8')
1428
- except UnicodeDecodeError, exc:
1429
- raise ScannerError("while scanning a %s" % name, start_mark, str(exc), mark)
1430
- return value
1431
-
1432
- def scan_line_break(self):
1433
- # Transforms:
1434
- # '\r\n' : '\n'
1435
- # '\r' : '\n'
1436
- # '\n' : '\n'
1437
- # '\x85' : '\n'
1438
- # '\u2028' : '\u2028'
1439
- # '\u2029 : '\u2029'
1440
- # default : ''
1441
- ch = self.peek()
1442
- if ch in u'\r\n\x85':
1443
- if self.prefix(2) == u'\r\n':
1444
- self.forward(2)
1445
- else:
1446
- self.forward()
1447
- return u'\n'
1448
- elif ch in u'\u2028\u2029':
1449
- self.forward()
1450
- return ch
1451
- return u''
1452
-
1453
-#try:
1454
-# import psyco
1455
-# psyco.bind(Scanner)
1456
-#except ImportError:
1457
-# pass
1458
-
src/collectors/python.d.plugin/python_modules/pyyaml2/serializer.py
deleted
-112
@@ -1,112 +0,0 @@
1
-# SPDX-License-Identifier: MIT
2
-
3
-__all__ = ['Serializer', 'SerializerError']
4
-
5
-from error import YAMLError
6
-from events import *
7
-from nodes import *
8
-
9
-class SerializerError(YAMLError):
10
- pass
11
-
12
-class Serializer(object):
13
-
14
- ANCHOR_TEMPLATE = u'id%03d'
15
-
16
- def __init__(self, encoding=None,
17
- explicit_start=None, explicit_end=None, version=None, tags=None):
18
- self.use_encoding = encoding
19
- self.use_explicit_start = explicit_start
20
- self.use_explicit_end = explicit_end
21
- self.use_version = version
22
- self.use_tags = tags
23
- self.serialized_nodes = {}
24
- self.anchors = {}
25
- self.last_anchor_id = 0
26
- self.closed = None
27
-
28
- def open(self):
29
- if self.closed is None:
30
- self.emit(StreamStartEvent(encoding=self.use_encoding))
31
- self.closed = False
32
- elif self.closed:
33
- raise SerializerError("serializer is closed")
34
- else:
35
- raise SerializerError("serializer is already opened")
36
-
37
- def close(self):
38
- if self.closed is None:
39
- raise SerializerError("serializer is not opened")
40
- elif not self.closed:
41
- self.emit(StreamEndEvent())
42
- self.closed = True
43
-
44
- #def __del__(self):
45
- # self.close()
46
-
47
- def serialize(self, node):
48
- if self.closed is None:
49
- raise SerializerError("serializer is not opened")
50
- elif self.closed:
51
- raise SerializerError("serializer is closed")
52
- self.emit(DocumentStartEvent(explicit=self.use_explicit_start,
53
- version=self.use_version, tags=self.use_tags))
54
- self.anchor_node(node)
55
- self.serialize_node(node, None, None)
56
- self.emit(DocumentEndEvent(explicit=self.use_explicit_end))
57
- self.serialized_nodes = {}
58
- self.anchors = {}
59
- self.last_anchor_id = 0
60
-
61
- def anchor_node(self, node):
62
- if node in self.anchors:
63
- if self.anchors[node] is None:
64
- self.anchors[node] = self.generate_anchor(node)
65
- else:
66
- self.anchors[node] = None
67
- if isinstance(node, SequenceNode):
68
- for item in node.value:
69
- self.anchor_node(item)
70
- elif isinstance(node, MappingNode):
71
- for key, value in node.value:
72
- self.anchor_node(key)
73
- self.anchor_node(value)
74
-
75
- def generate_anchor(self, node):
76
- self.last_anchor_id += 1
77
- return self.ANCHOR_TEMPLATE % self.last_anchor_id
78
-
79
- def serialize_node(self, node, parent, index):
80
- alias = self.anchors[node]
81
- if node in self.serialized_nodes:
82
- self.emit(AliasEvent(alias))
83
- else:
84
- self.serialized_nodes[node] = True
85
- self.descend_resolver(parent, index)
86
- if isinstance(node, ScalarNode):
87
- detected_tag = self.resolve(ScalarNode, node.value, (True, False))
88
- default_tag = self.resolve(ScalarNode, node.value, (False, True))
89
- implicit = (node.tag == detected_tag), (node.tag == default_tag)
90
- self.emit(ScalarEvent(alias, node.tag, implicit, node.value,
91
- style=node.style))
92
- elif isinstance(node, SequenceNode):
93
- implicit = (node.tag
94
- == self.resolve(SequenceNode, node.value, True))
95
- self.emit(SequenceStartEvent(alias, node.tag, implicit,
96
- flow_style=node.flow_style))
97
- index = 0
98
- for item in node.value:
99
- self.serialize_node(item, node, index)
100
- index += 1
101
- self.emit(SequenceEndEvent())
102
- elif isinstance(node, MappingNode):
103
- implicit = (node.tag
104
- == self.resolve(MappingNode, node.value, True))
105
- self.emit(MappingStartEvent(alias, node.tag, implicit,
106
- flow_style=node.flow_style))
107
- for key, value in node.value:
108
- self.serialize_node(key, node, None)
109
- self.serialize_node(value, node, key)
110
- self.emit(MappingEndEvent())
111
- self.ascend_resolver()
112
-
src/collectors/python.d.plugin/python_modules/pyyaml2/tokens.py
deleted
-105
@@ -1,105 +0,0 @@
1
-# SPDX-License-Identifier: MIT
2
-
3
-class Token(object):
4
- def __init__(self, start_mark, end_mark):
5
- self.start_mark = start_mark
6
- self.end_mark = end_mark
7
- def __repr__(self):
8
- attributes = [key for key in self.__dict__
9
- if not key.endswith('_mark')]
10
- attributes.sort()
11
- arguments = ', '.join(['%s=%r' % (key, getattr(self, key))
12
- for key in attributes])
13
- return '%s(%s)' % (self.__class__.__name__, arguments)
14
-
15
-#class BOMToken(Token):
16
-# id = '<byte order mark>'
17
-
18
-class DirectiveToken(Token):
19
- id = '<directive>'
20
- def __init__(self, name, value, start_mark, end_mark):
21
- self.name = name
22
- self.value = value
23
- self.start_mark = start_mark
24
- self.end_mark = end_mark
25
-
26
-class DocumentStartToken(Token):
27
- id = '<document start>'
28
-
29
-class DocumentEndToken(Token):
30
- id = '<document end>'
31
-
32
-class StreamStartToken(Token):
33
- id = '<stream start>'
34
- def __init__(self, start_mark=None, end_mark=None,
35
- encoding=None):
36
- self.start_mark = start_mark
37
- self.end_mark = end_mark
38
- self.encoding = encoding
39
-
40
-class StreamEndToken(Token):
41
- id = '<stream end>'
42
-
43
-class BlockSequenceStartToken(Token):
44
- id = '<block sequence start>'
45
-
46
-class BlockMappingStartToken(Token):
47
- id = '<block mapping start>'
48
-
49
-class BlockEndToken(Token):
50
- id = '<block end>'
51
-
52
-class FlowSequenceStartToken(Token):
53
- id = '['
54
-
55
-class FlowMappingStartToken(Token):
56
- id = '{'
57
-
58
-class FlowSequenceEndToken(Token):
59
- id = ']'
60
-
61
-class FlowMappingEndToken(Token):
62
- id = '}'
63
-
64
-class KeyToken(Token):
65
- id = '?'
66
-
67
-class ValueToken(Token):
68
- id = ':'
69
-
70
-class BlockEntryToken(Token):
71
- id = '-'
72
-
73
-class FlowEntryToken(Token):
74
- id = ','
75
-
76
-class AliasToken(Token):
77
- id = '<alias>'
78
- def __init__(self, value, start_mark, end_mark):
79
- self.value = value
80
- self.start_mark = start_mark
81
- self.end_mark = end_mark
82
-
83
-class AnchorToken(Token):
84
- id = '<anchor>'
85
- def __init__(self, value, start_mark, end_mark):
86
- self.value = value
87
- self.start_mark = start_mark
88
- self.end_mark = end_mark
89
-
90
-class TagToken(Token):
91
- id = '<tag>'
92
- def __init__(self, value, start_mark, end_mark):
93
- self.value = value
94
- self.start_mark = start_mark
95
- self.end_mark = end_mark
96
-
97
-class ScalarToken(Token):
98
- id = '<scalar>'
99
- def __init__(self, value, plain, start_mark, end_mark, style=None):
100
- self.value = value
101
- self.plain = plain
102
- self.start_mark = start_mark
103
- self.end_mark = end_mark
104
- self.style = style
105
-