Получение содержимого cdata при анализе xml-файла

У меня есть xml-файл

<?xml version="1.0" encoding="utf-8"?> <xml> <events date="01-10-2009" color="0x99CC00" selected="true"> <event> <title>You can use HTML and CSS</title> <description><![CDATA[This is the description ]]></description> </event> </events> </xml> 

Я использовал xpath и и xquery для синтаксического анализа xml.

 $xml_str = file_get_contents('xmlfile'); $xml = simplexml_load_string($xml_str); if(!empty($xml)) { $nodes = $xml->xpath('//xml/events'); } 

Я получаю заголовок правильно, но я не получаю описание. Как я могу получить данные внутри cdata

    У SimpleXML есть немного проблемы с CDATA, поэтому используйте:

     $xml = simplexml_load_file('xmlfile', 'SimpleXMLElement', LIBXML_NOCDATA); if(!empty($xml)) { $nodes = $xml->xpath('//xml/events'); } print_r( $nodes ); 

    Это даст вам:

     Array ( [0] => SimpleXMLElement Object ( [@attributes] => Array ( [date] => 01-10-2009 [color] => 0x99CC00 [selected] => true ) [event] => SimpleXMLElement Object ( [title] => You can use HTML and CSS [description] => This is the description ) ) ) 

    Вероятно, вы ошибаетесь, думая, что CDATA отсутствует, используя print_r или одну из других «нормальных» функций отладки PHP. Они не могут видеть полный контент объекта SimpleXML, поскольку он не является «реальным» объектом PHP.

    Если вы запустите echo $nodes[0]->Description , вы обнаружите, что ваш CDATA вышел отлично. Что происходит, так это то, что PHP знает, что echo ожидает строку, поэтому просит SimpleXML для одного; SimpleXML отвечает всем содержимым строки, включая CDATA.

    Чтобы надежно получить полное строковое содержимое, просто скажите PHP, что вы хотите использовать строку с помощью оператора (string) cast, например $description = (string)$nodes[0]->Description .

    Чтобы отлаживать объекты SimpleXML и не обманываться такими причудами, используйте выделенную функцию отладки, такую ​​как один из них: https://github.com/IMSoP/simplexml_debug

    Это также может быть еще одним жизнеспособным вариантом, который удалит этот код и облегчит жизнь.

     $xml = str_replace("-", "_", $xml); $xml = str_replace("<![CDATA[", "", $xml); $xml = str_replace("]]>", "", $xml);