diff options
author | Tobias Deiminger <haxtibal@posteo.de> | 2022-02-13 19:40:39 +0100 |
---|---|---|
committer | GitHub <noreply@github.com> | 2022-02-13 19:40:39 +0100 |
commit | f7bb07b5f68fede97754685dad076cd7b7442bac (patch) | |
tree | 09c582d6fb2d2b8d90e378ae164e5189d41b7d13 /src/lxml | |
parent | 1e3666018329cadf8e147607824614aebf7e2099 (diff) | |
download | python-lxml-f7bb07b5f68fede97754685dad076cd7b7442bac.tar.gz |
Use expected XSD spellings for xsi:double infinity and NaN (GH-338)
W3C specification for xsd:double says
> The special values positive and negative infinity and
> not-a-number have lexical representations INF, -INF and NaN,
> respectively.
Thus case matters. The previously used float.__repr__ would generate
"inf", "-inf", "nan". Now we prepend special handling to get
"INF", "-INF", "NaN" instead (which is still pytype compatible).
Includes minor non-functional alignments of related bool to text code,
and tests to assert its XML schema conformance as well.
Diffstat (limited to 'src/lxml')
-rw-r--r-- | src/lxml/objectify.pyx | 20 | ||||
-rw-r--r-- | src/lxml/tests/test_objectify.py | 9 |
2 files changed, 25 insertions, 4 deletions
diff --git a/src/lxml/objectify.pyx b/src/lxml/objectify.pyx index cacbe806..376695a8 100644 --- a/src/lxml/objectify.pyx +++ b/src/lxml/objectify.pyx @@ -38,6 +38,9 @@ import_lxml__etree() __version__ = etree.__version__ +cdef object _float_is_inf, _float_is_nan +from math import isinf as _float_is_inf, isnan as _float_is_nan + cdef object re import re @@ -1205,8 +1208,17 @@ cdef dict _PYTYPE_DICT = {} cdef dict _SCHEMA_TYPE_DICT = {} cdef list _TYPE_CHECKS = [] -cdef unicode _lower_bool(b): - return u"true" if b else u"false" +cdef unicode _xml_bool(value): + return u"true" if value else u"false" + +cdef unicode _xml_float(value): + if _float_is_inf(value): + if value > 0: + return u"INF" + return u"-INF" + if _float_is_nan(value): + return u"NaN" + return unicode(repr(value)) cdef _pytypename(obj): return u"str" if python._isString(obj) else _typename(obj) @@ -1230,11 +1242,11 @@ cdef _registerPyTypes(): pytype = PyType(u'long', None, IntElement) pytype.register() - pytype = PyType(u'float', _checkFloat, FloatElement, repr) # wraps _parseFloat for Python + pytype = PyType(u'float', _checkFloat, FloatElement, _xml_float) # wraps functions for Python pytype.xmlSchemaTypes = (u"double", u"float") pytype.register() - pytype = PyType(u'bool', _checkBool, BoolElement, _lower_bool) # wraps functions for Python + pytype = PyType(u'bool', _checkBool, BoolElement, _xml_bool) # wraps functions for Python pytype.xmlSchemaTypes = (u"boolean",) pytype.register() diff --git a/src/lxml/tests/test_objectify.py b/src/lxml/tests/test_objectify.py index 178ba256..f50a3447 100644 --- a/src/lxml/tests/test_objectify.py +++ b/src/lxml/tests/test_objectify.py @@ -873,6 +873,10 @@ class ObjectifyTestCase(HelperTestCase): self.assertTrue(isinstance(value, objectify.BoolElement)) self.assertEqual(value, False) + def test_data_element_bool_text(self): + self.assertEqual(objectify.DataElement(False).text, "false") + self.assertEqual(objectify.DataElement(True).text, "true") + def test_type_str(self): Element = self.Element SubElement = self.etree.SubElement @@ -1115,6 +1119,11 @@ class ObjectifyTestCase(HelperTestCase): value = objectify.DataElement(f) self.assertEqual(hash(value), hash(f)) + def test_data_element_float_special_value_text(self): + self.assertEqual(objectify.DataElement(float("inf")).text, "INF") + self.assertEqual(objectify.DataElement(float("-inf")).text, "-INF") + self.assertEqual(objectify.DataElement(float("nan")).text, "NaN") + def test_data_element_xsitypes(self): for xsi, objclass in xsitype2objclass.items(): # 1 is a valid value for all ObjectifiedDataElement classes |