PHP 使用 DOMdocument 更新 xml CDATA 字段



我有以下XML数据:

<?xml version="1.0" encoding="utf-8"?>
<source>
    <publisher>some-data</publisher>
    <publisherurl>some-data</publisherurl>
    <lastBuildDate>a-date</lastBuildDate>
    <element>
        <sub-element><![CDATA[some-data]]></sub-element>
    </element>
</source>

我正在尝试使用 PHP 内置的 DOMdocument 解析器来更新 sub-element 中的文本。

我试过:

$dom=new DOMDocument();
$dom->load("document.xml");
$ele=$root->getElementsByTagName('element');
foreach ($ele as $e) {
    $e->getElementsByTagName('sub-element')->item(0)->nodeValue = "new val";
}

这种工作,但它删除了CDATA,只是用new-val替换它。 我想保留 CDATA 字段,因此尝试了以下操作:

$dom=new DOMDocument();
$dom->load("document.xml");
$ele=$root->getElementsByTagName('element');
foreach ($ele as $e) {  
    $sub=$e->getElementsByTagName('sub-element');   
    foreach($sub->childNodes as $child) {
        if ($child->nodeType == XML_CDATA_SECTION_NODE) {
            $child->nodeValue = 'new-val';
        }
    }
}

这似乎应该有效,但 PHP 返回以下通知

未定义的属性:DOMNodeList::$childNodes

感觉我走在

正确的道路上,但我就是无法弄清楚我在这里做错了什么。 有谁知道如何解决?

我的最终目标输出是:

<?xml version="1.0" encoding="utf-8"?>
<source>
    <publisher>some-data</publisher>
    <publisherurl>some-data</publisherurl>
    <lastBuildDate>a-date</lastBuildDate>
    <element>
        <sub-element><![CDATA[new-val]]></sub-element>
    </element>
</source>
您需要

firstChild进行比较

$xml = '<?xml version="1.0" encoding="utf-8"?>
<source>
    <publisher>some-data</publisher>
    <publisherurl>some-data</publisherurl>
    <lastBuildDate>a-date</lastBuildDate>
    <element>
        <sub-element><![CDATA[some-data]]></sub-element>
    </element>
    <element>
        <sub-element>some-other-data</sub-element>
    </element>
</source>';
$dom = new DOMDocument();
$dom->loadXML($xml);
$ele=$dom->getElementsByTagName('element');
foreach ($ele as $e) {
    $item = $e->getElementsByTagName('sub-element')->item(0);
    if($item->firstChild->nodeType == XML_CDATA_SECTION_NODE) { //<------
        //it's CDATA do whatever
         $item->firstChild->nodeValue = "new val";
    } else {
        //it's not , do something else
        $item->nodeValue = "new val";
    }
}
echo "<pre>";
print_r(htmlentities($dom->saveXML()));
echo "</pre>";

输出:

<?xml version="1.0" encoding="utf-8"?>
<source>
    <publisher>some-data</publisher>
    <publisherurl>some-data</publisherurl>
    <lastBuildDate>a-date</lastBuildDate>
    <element>
        <sub-element><![CDATA[new val]]></sub-element>
    </element>
    <element>
        <sub-element>new val</sub-element>
    </element>
</source>

PS:如果您不必区分CDATA,只需使用firstChild

foreach ($ele as $e) {
    $item = $e->getElementsByTagName('sub-element')->item(0);
    $item->firstChild->nodeValue = "new val";
}

最新更新