jfk888 Posted July 26, 2011 Share Posted July 26, 2011 I'm trying to parse an xml-file which is full of namespaces, here is an example: <parent> <name>Bill Clinton jr.</name> <pr:element> <pr:code>123</pr:code> <pr:text>Hello!</pr:text> </pr:element> <cmn:address> <cmn:street>My Street 10</cmn:street> <cmn:zip>22334</cmn:zip> </cmn:address> </parent> I get the values like this: $xml = simplexml_load_string($str); $name = $xml->parent->name; $code = $xml->parent->children('pr', true)->element->code; $street = $xml->parent->children('cmn', true)->address->street; But the fun part is that sometimes some of the elements may not exist, in this case it's the <cmn:address> element: <parent> <name>Bill Clinton jr.</name> <pr:element> <pr:code>123</pr:code> <pr:text>Hello!</pr:text> </pr:element> </parent> $street = $xml->parent->children('cmn', true)->address->street; The above code gives "Fatal error: Call to a member function children() on a non-object in...". To avoid the fatal error I could check that the <cmn:address> exists, but the actual file can be nested very deep and there are many optional elements. Checking every single element would cause me a hairloss. In my dreams the above code example would just ignore the missing <cmn:address> element and the $street variable would stay empty. I can't even suppress the fatal error (I do understand why) with the '@'-practice, well I can but the execution of the script stops as expected. Is there any other ways to handle this situation? Quote Link to comment https://forums.phpfreaks.com/topic/242844-simplexml-and-child-elements/ Share on other sites More sharing options...
salathe Posted July 26, 2011 Share Posted July 26, 2011 <parent> <name>Bill Clinton jr.</name> <pr:element> <pr:code>123</pr:code> <pr:text>Hello!</pr:text> </pr:element> </parent> $street = $xml->parent->children('cmn', true)->address->street; Your line of code is incorrect given the XML shown. $xml will be the <parent> element so to try and access the <street> you would want: $street = $xml->children('cmn', true)->address->street; If the <cmn:address> is not present, the above will assign NULL to $street with no warnings or errors. Quote Link to comment https://forums.phpfreaks.com/topic/242844-simplexml-and-child-elements/#findComment-1247289 Share on other sites More sharing options...
jfk888 Posted July 26, 2011 Author Share Posted July 26, 2011 I try to be more specific. $str = " <xml xmlns:pr=\"http://www.example.com\"> <element1> <element1>1</element1> <element2>2</element2> </element1> <element2> <element1> <pr:element1>1</pr:element1> <pr:element2>2</pr:element2> </element1> <element2> <pr:element1>1</pr:element1> <pr:element2>2</pr:element2> </element2> <!-- <element3> <element1> <pr:element1>1</pr:element1> <pr:element2>2</pr:element2> </element1> </element3> --> </element2> </xml>"; $xml = simplexml_load_string($str); echo $xml->element1->element1 . '<br>'; echo $xml->element2->element1->children('pr', true)->element1 . '<br>'; echo $xml->element2->element2->children('pr', true)->element2 . '<br>'; echo $xml->element2->element3->children('pr', true)->element1 . '<br>'; echo $xml->element2->element3->element1->children('pr', true)->element1; Result: 1 1 2 Warning: main(): Node no longer exists in /var/www/test.php on line 40 Call Stack: 0.0002 654960 1. {main}() /var/www/test.php:0 Fatal error: Call to a member function children() on a non-object in /var/www/test.php on line 41 Call Stack: 0.0002 654960 1. {main}() /var/www/test.php:0 When examining the xml, it seems that on the first non-existent level PHP gives a warning and one level further it gives a fatal error. My actual point was that if I can't be sure that a particular element exists in the xml-data, it seems that I can't use the above approach. If someone knows better, please tell me. Quote Link to comment https://forums.phpfreaks.com/topic/242844-simplexml-and-child-elements/#findComment-1247384 Share on other sites More sharing options...
Recommended Posts
Join the conversation
You can post now and register later. If you have an account, sign in now to post with your account.