[lxml-dev] lxml 1.3 coming up

jholg at gmx.de jholg at gmx.de
Mon Jun 18 14:24:37 CEST 2007


Hi,

> You're not gonna let go, are you? :)
> 
> But I think you're right. I'll patch those two in. I'll need you to check
> that
> these things work, though. The test coverage in that area is not very
> great,
> since I had to leave out a couple of those big test cases as they wouldn't
> work without having lxml also generate the prefixes.

I propose changing DataElement() like this to come even closer to future
behaviour, without internal auto-prefixing; this is actually just taken
from trunk and left out the internal prefix addition:

Index: src/lxml/objectify.pyx
===================================================================
--- src/lxml/objectify.pyx      (revision 44327)
+++ src/lxml/objectify.pyx      (working copy)
@@ -1664,6 +1664,7 @@
     if the type can be identified.  If '_pytype' or '_xsi' are among the
     keyword arguments, they will be used instead.
     """
+    cdef python.PyObject* dict_result
     if nsmap is None:
         nsmap = _DEFAULT_NSMAP
     if attrib is not None:
@@ -1671,12 +1672,19 @@
             attrib.update(_attributes)
         _attributes = attrib
     if _xsi is not None:
+        if ':' in _xsi:
+            prefix, name = _xsi.split(':', 1)
+            ns = nsmap.get(prefix)
+            if ns != XML_SCHEMA_NS:
+                raise ValueError, "XSD types require the XSD namespace"
         python.PyDict_SetItem(_attributes, XML_SCHEMA_INSTANCE_TYPE_ATTR, _xsi)
         if _pytype is None:
-            # allow for s.o. using unregistered or even wrong xsi:type names
-            pytype_lookup = _SCHEMA_TYPE_DICT.get(_xsi)
-            if pytype_lookup is not None:
-                _pytype = pytype_lookup.name
+            # allow using unregistered or even wrong xsi:type names
+            dict_result = python.PyDict_GetItem(_SCHEMA_TYPE_DICT, _xsi)
+            if dict_result is NULL:
+                dict_result = python.PyDict_GetItem(_SCHEMA_TYPE_DICT, name)
+            if dict_result is not NULL:
+                _pytype = (<PyType>dict_result).name
 
     if python._isString(_value):
         strval = _value

This way, you can use type prefixes in DataElement if you wish, with the lookup being able to use the information:

>>> root = objectify.Element('root')
>>> root.no_prefix = DataElement(5, _xsi="long")
>>> root.prefix = DataElement(5, _xsi="xsd:long")
>>> print etree.tostring(root,  pretty_print="True")
<root xmlns:py="http://codespeak.net/lxml/objectify/pytype" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" py:pytype="TREE">
  <no_prefix py:pytype="long" xsi:type="long">5</no_prefix>
  <prefix py:pytype="long" xsi:type="xsd:long">5</prefix>
</root>
>>> 

Note how the <prefix> element gets identified as pytype "long" (as opposed to pytype "int").
It's easy to also remove the check for a given ns-prefix pointing to XML_SCHEMA_NS but I think it's compatible enough to 1.2.1 behaviour.

Patch file attached.

Holger
-- 
GMX FreeMail: 1 GB Postfach, 5 E-Mail-Adressen, 10 Free SMS.
Alle Infos und kostenlose Anmeldung: http://www.gmx.net/de/go/freemail
-------------- next part --------------
A non-text attachment was scrubbed...
Name: objectify.pyx.patch_DataElement
Type: application/octet-stream
Size: 1547 bytes
Desc: not available
Url : http://codespeak.net/pipermail/lxml-dev/attachments/20070618/8bf9b49c/attachment.obj 


More information about the lxml-dev mailing list