mirror of
https://github.com/yaml/pyyaml.git
synced 2025-10-19 19:13:19 +00:00
Also add reuse_anchors to libyaml backend
This commit is contained in:
parent
bd96e4000c
commit
737ad62df0
10 changed files with 58 additions and 26 deletions
|
@ -48,7 +48,7 @@ def parse(stream, Loader=Loader, reuse_anchors=False):
|
||||||
finally:
|
finally:
|
||||||
loader.dispose()
|
loader.dispose()
|
||||||
|
|
||||||
def compose(stream, Loader=Loader):
|
def compose(stream, Loader=Loader, reuse_anchors=False):
|
||||||
"""
|
"""
|
||||||
Parse the first YAML document in a stream
|
Parse the first YAML document in a stream
|
||||||
and produce the corresponding representation tree.
|
and produce the corresponding representation tree.
|
||||||
|
|
|
@ -15,36 +15,36 @@ from .resolver import *
|
||||||
|
|
||||||
class CBaseLoader(CParser, BaseConstructor, BaseResolver):
|
class CBaseLoader(CParser, BaseConstructor, BaseResolver):
|
||||||
|
|
||||||
def __init__(self, stream):
|
def __init__(self, stream, reuse_anchors=False):
|
||||||
CParser.__init__(self, stream)
|
CParser.__init__(self, stream, reuse_anchors=reuse_anchors)
|
||||||
BaseConstructor.__init__(self)
|
BaseConstructor.__init__(self)
|
||||||
BaseResolver.__init__(self)
|
BaseResolver.__init__(self)
|
||||||
|
|
||||||
class CSafeLoader(CParser, SafeConstructor, Resolver):
|
class CSafeLoader(CParser, SafeConstructor, Resolver):
|
||||||
|
|
||||||
def __init__(self, stream):
|
def __init__(self, stream, reuse_anchors=False):
|
||||||
CParser.__init__(self, stream)
|
CParser.__init__(self, stream, reuse_anchors=reuse_anchors)
|
||||||
SafeConstructor.__init__(self)
|
SafeConstructor.__init__(self)
|
||||||
Resolver.__init__(self)
|
Resolver.__init__(self)
|
||||||
|
|
||||||
class CFullLoader(CParser, FullConstructor, Resolver):
|
class CFullLoader(CParser, FullConstructor, Resolver):
|
||||||
|
|
||||||
def __init__(self, stream):
|
def __init__(self, stream, reuse_anchors=False):
|
||||||
CParser.__init__(self, stream)
|
CParser.__init__(self, stream, reuse_anchors=reuse_anchors)
|
||||||
FullConstructor.__init__(self)
|
FullConstructor.__init__(self)
|
||||||
Resolver.__init__(self)
|
Resolver.__init__(self)
|
||||||
|
|
||||||
class CUnsafeLoader(CParser, UnsafeConstructor, Resolver):
|
class CUnsafeLoader(CParser, UnsafeConstructor, Resolver):
|
||||||
|
|
||||||
def __init__(self, stream):
|
def __init__(self, stream, reuse_anchors=False):
|
||||||
CParser.__init__(self, stream)
|
CParser.__init__(self, stream, reuse_anchors=reuse_anchors)
|
||||||
UnsafeConstructor.__init__(self)
|
UnsafeConstructor.__init__(self)
|
||||||
Resolver.__init__(self)
|
Resolver.__init__(self)
|
||||||
|
|
||||||
class CLoader(CParser, Constructor, Resolver):
|
class CLoader(CParser, Constructor, Resolver):
|
||||||
|
|
||||||
def __init__(self, stream):
|
def __init__(self, stream, reuse_anchors=False):
|
||||||
CParser.__init__(self, stream)
|
CParser.__init__(self, stream, reuse_anchors=reuse_anchors)
|
||||||
Constructor.__init__(self)
|
Constructor.__init__(self)
|
||||||
Resolver.__init__(self)
|
Resolver.__init__(self)
|
||||||
|
|
||||||
|
|
3
tests/data/duplicate-anchor-1.loader-error
Normal file
3
tests/data/duplicate-anchor-1.loader-error
Normal file
|
@ -0,0 +1,3 @@
|
||||||
|
- &foo bar
|
||||||
|
- &bar bar
|
||||||
|
- &foo bar
|
|
@ -258,7 +258,7 @@ def test_constructor_types(data_filename, code_filename, verbose=False):
|
||||||
native2 = None
|
native2 = None
|
||||||
try:
|
try:
|
||||||
with open(data_filename, 'rb') as file:
|
with open(data_filename, 'rb') as file:
|
||||||
native1 = list(yaml.load_all(file, Loader=MyLoader, reuse_anchors=True))
|
native1 = list(yaml.load_all(file, Loader=MyLoader))
|
||||||
if len(native1) == 1:
|
if len(native1) == 1:
|
||||||
native1 = native1[0]
|
native1 = native1[0]
|
||||||
with open(code_filename, 'rb') as file:
|
with open(code_filename, 'rb') as file:
|
||||||
|
@ -296,6 +296,34 @@ def test_subclass_blacklist_types(data_filename, verbose=False):
|
||||||
|
|
||||||
test_subclass_blacklist_types.unittest = ['.subclass_blacklist']
|
test_subclass_blacklist_types.unittest = ['.subclass_blacklist']
|
||||||
|
|
||||||
|
def test_reuse_anchors(data_filename, code_filename, verbose=False):
|
||||||
|
try:
|
||||||
|
with open(data_filename, 'rb') as file:
|
||||||
|
native1 = list(yaml.load_all(file, Loader=yaml.SafeLoader, reuse_anchors=True))
|
||||||
|
if len(native1) == 1:
|
||||||
|
native1 = native1[0]
|
||||||
|
with open(code_filename, 'rb') as file:
|
||||||
|
native2 = _load_code(file.read())
|
||||||
|
try:
|
||||||
|
if native1 == native2:
|
||||||
|
return
|
||||||
|
except TypeError:
|
||||||
|
pass
|
||||||
|
if verbose:
|
||||||
|
print("SERIALIZED NATIVE1:")
|
||||||
|
print(_serialize_value(native1))
|
||||||
|
print("SERIALIZED NATIVE2:")
|
||||||
|
print(_serialize_value(native2))
|
||||||
|
assert _serialize_value(native1) == _serialize_value(native2), (native1, native2)
|
||||||
|
finally:
|
||||||
|
if verbose:
|
||||||
|
print("NATIVE1:")
|
||||||
|
pprint.pprint(native1)
|
||||||
|
print("NATIVE2:")
|
||||||
|
pprint.pprint(native2)
|
||||||
|
|
||||||
|
test_reuse_anchors.unittest = ['.reuse-anchors-data', '.reuse-anchors-code']
|
||||||
|
|
||||||
if __name__ == '__main__':
|
if __name__ == '__main__':
|
||||||
import sys, test_constructor
|
import sys, test_constructor
|
||||||
sys.modules['test_constructor'] = sys.modules['__main__']
|
sys.modules['test_constructor'] = sys.modules['__main__']
|
||||||
|
|
|
@ -18,28 +18,28 @@ def new_parse(stream, Loader=yaml.CLoader):
|
||||||
return old_parse(stream, Loader)
|
return old_parse(stream, Loader)
|
||||||
|
|
||||||
old_compose = yaml.compose
|
old_compose = yaml.compose
|
||||||
def new_compose(stream, Loader=yaml.CLoader):
|
def new_compose(stream, Loader=yaml.CLoader, reuse_anchors=False):
|
||||||
return old_compose(stream, Loader)
|
return old_compose(stream, Loader, reuse_anchors=reuse_anchors)
|
||||||
|
|
||||||
old_compose_all = yaml.compose_all
|
old_compose_all = yaml.compose_all
|
||||||
def new_compose_all(stream, Loader=yaml.CLoader):
|
def new_compose_all(stream, Loader=yaml.CLoader, reuse_anchors=False):
|
||||||
return old_compose_all(stream, Loader)
|
return old_compose_all(stream, Loader, reuse_anchors=reuse_anchors)
|
||||||
|
|
||||||
old_load = yaml.load
|
old_load = yaml.load
|
||||||
def new_load(stream, Loader=yaml.CLoader):
|
def new_load(stream, Loader=yaml.CLoader, reuse_anchors=False):
|
||||||
return old_load(stream, Loader)
|
return old_load(stream, Loader, reuse_anchors=reuse_anchors)
|
||||||
|
|
||||||
old_load_all = yaml.load_all
|
old_load_all = yaml.load_all
|
||||||
def new_load_all(stream, Loader=yaml.CLoader):
|
def new_load_all(stream, Loader=yaml.CLoader, reuse_anchors=False):
|
||||||
return old_load_all(stream, Loader)
|
return old_load_all(stream, Loader, reuse_anchors=reuse_anchors)
|
||||||
|
|
||||||
old_safe_load = yaml.safe_load
|
old_safe_load = yaml.safe_load
|
||||||
def new_safe_load(stream):
|
def new_safe_load(stream, reuse_anchors=False):
|
||||||
return old_load(stream, yaml.CSafeLoader)
|
return old_load(stream, yaml.CSafeLoader, reuse_anchors=reuse_anchors)
|
||||||
|
|
||||||
old_safe_load_all = yaml.safe_load_all
|
old_safe_load_all = yaml.safe_load_all
|
||||||
def new_safe_load_all(stream):
|
def new_safe_load_all(stream, reuse_anchors=False):
|
||||||
return old_load_all(stream, yaml.CSafeLoader)
|
return old_load_all(stream, yaml.CSafeLoader, reuse_anchors=reuse_anchors)
|
||||||
|
|
||||||
old_emit = yaml.emit
|
old_emit = yaml.emit
|
||||||
def new_emit(events, stream=None, Dumper=yaml.CDumper, **kwds):
|
def new_emit(events, stream=None, Dumper=yaml.CDumper, **kwds):
|
||||||
|
|
|
@ -256,7 +256,8 @@ cdef class CParser:
|
||||||
cdef int stream_cache_pos
|
cdef int stream_cache_pos
|
||||||
cdef int unicode_source
|
cdef int unicode_source
|
||||||
|
|
||||||
def __init__(self, stream):
|
def __init__(self, stream, reuse_anchors=False):
|
||||||
|
self.reuse_anchors=reuse_anchors
|
||||||
cdef is_readable
|
cdef is_readable
|
||||||
if yaml_parser_initialize(&self.parser) == 0:
|
if yaml_parser_initialize(&self.parser) == 0:
|
||||||
raise MemoryError
|
raise MemoryError
|
||||||
|
@ -714,7 +715,7 @@ cdef class CParser:
|
||||||
and self.parsed_event.data.mapping_start.anchor != NULL:
|
and self.parsed_event.data.mapping_start.anchor != NULL:
|
||||||
anchor = PyUnicode_FromYamlString(self.parsed_event.data.mapping_start.anchor)
|
anchor = PyUnicode_FromYamlString(self.parsed_event.data.mapping_start.anchor)
|
||||||
if anchor is not None:
|
if anchor is not None:
|
||||||
if anchor in self.anchors:
|
if anchor in self.anchors and not self.reuse_anchors:
|
||||||
mark = Mark(self.stream_name,
|
mark = Mark(self.stream_name,
|
||||||
self.parsed_event.start_mark.index,
|
self.parsed_event.start_mark.index,
|
||||||
self.parsed_event.start_mark.line,
|
self.parsed_event.start_mark.line,
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue