That patch is not a good idea.

Assume you have this situation:

<foo xmlns="urn:lol">
 <x:bar xmlns:x="urn:hai">
 </x:bar>
</foo>

Adding a child "baz" to bar and have it default to no namespace prefix would 
result in this:

<foo xmlns="urn:lol">
 <x:bar xmlns:x="urn:hai">
   <baz />
 </x:bar>
</foo>

Now <baz /> would be in the namespace "urn:lol".

Keep in mind that xmlns="" is, as per the XML spec, a perfectly valid way to 
reset the namespace of an element.

Also keep in mind that namespace prefixes are not what you should be looking 
at. They are just a way to make things easier to read. What matters is the 
namespace URI of an element.

SimpleXML is supposed to be simple (I find it more stupid than simple, but 
that's my personal opinion). I guess that's why it, by default, inherits the 
parent namespace.

David


On 27.04.2011, at 01:23, Tom Samplonius wrote:

> 
>  It is not possible to use SimpleXML to add a child element without a 
> namespace prefix to a parent element that has a namespace element. Instead, 
> the child element inherits the namespace prefix of the parent. So this XML 
> fragment: 
> 
> <ns1:parent> 
> <child>abc</child> 
> </ns1:parent> 
> 
> is impossible to construct with SimpleXML. The SimpleXML extension would add 
> the <child> element with the ns1 namespace prefix. This is a problem for me, 
> as I have an XML schema that specifies that the child elements must not 
> namespace qualified. 
> 
>  I looked into the SimpleXML code, and I believe this is actually a bug, as 
> the code goes through some effort to distinguish between a set but blank 
> namespace, and a set but not blank namespace. I believe the design intent was 
> that specifying a blank namespace, would mean that no namespace would be 
> used, rather than inheriting the namespace of the parent. 
> 
> <?php 
> header('Content-Type: text/plain'); 
> 
> $r = new SimpleXMLElement('<r />'); 
> $c1 = $r->addChild('ns1:child1', NULL, 'urn:myspace1'); 
> $c1->addChild('child2'); 
> echo $r->asXML(), "\n"; 
> 
> $r = new SimpleXMLElement('<r />'); 
> $r->addChild('Thing1', 100, ''); 
> echo $r->asXML(), "\n"; 
> 
> 
> Expected result: 
> ---------------- 
> <?xml version="1.0"?> 
> <r><ns1:child1 xmlns:ns1="urn:myspace1"><ns1:child2/></ns1:child1></r> 
> 
> <?xml version="1.0"?> 
> <r><Thing1>100</Thing1></r> 
> 
> Actual result: 
> -------------- 
> <?xml version="1.0"?> 
> <r><ns1:child1 xmlns:ns1="urn:myspace1"><ns1:child2/></ns1:child1></r> 
> 
> <?xml version="1.0"?> 
> <r><Thing1 xmlns="">100</Thing1></r> 
> 
> 
>  The current behavior of specifying a blank namespace, is to add a literal 
> blank namespace (xmlns=""), which isn't a useful result. No one would be 
> depending on using a blank namepspace to get xmlns="". 
> 
> The patch is pretty simple: 
> 
> --- simplexml.c.orig 2011-04-26 16:00:31.000000000 -0700 
> +++ simplexml.c 2011-04-26 16:00:41.000000000 -0700 
> @@ -1619,12 +1619,14 @@ 
> localname = xmlStrdup((xmlChar *)qname); 
> } 
> 
> + /* Add new child with no namespace */ 
> newnode = xmlNewChild(node, NULL, localname, (xmlChar *)value); 
> 
> if (nsuri != NULL) { 
> + /* If namespace is not NULL but blank, use no namespace 
> + Use this to prevent inheriting the name space of the parent */ 
> if (nsuri_len == 0) { 
> newnode->ns = NULL; 
> - nsptr = xmlNewNs(newnode, (xmlChar *)nsuri, prefix); 
> } else { 
> nsptr = xmlSearchNsByHref(node->doc, node, (xmlChar *)nsuri); 
> if (nsptr == NULL) { 
> 
> 
> (see also http://bugs.php.net/bug.php?id=54354) 
> 
> 
> If this patch is accepted, I'll also submit patches to clarify the 
> documentation and add some tests. SimpleXML with the above patch, passes the 
> existing tests. It is hard to know for sure what the design intent was, as 
> the code has few comments, few tests, and the documentation is pretty thin. 
> But I believe the above is correct. 
> 
> 
> Tom 
> 
> -- 
> PHP Internals - PHP Runtime Development Mailing List
> To unsubscribe, visit: http://www.php.net/unsub.php
> 
> 

Attachment: smime.p7s
Description: S/MIME cryptographic signature

Reply via email to