Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/php/231.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
在PHP中使用saveXML保存CDATA_Php_Xml - Fatal编程技术网

在PHP中使用saveXML保存CDATA

在PHP中使用saveXML保存CDATA,php,xml,Php,Xml,我编写了一个简短的PHP脚本来获取一个现有的XML文件,找到一个节点并将其更改为一个新值。新值必须包装到CDATA块中。这可以很好地工作,但是字符将替换为各自的HTML实体。这破坏了我在Java中的XML验证 <?php $fileName = "whatever"; $doc = new DOMDocument(); $doc->load('test.xml'); $doc->getElementsByTagName("SomeNode")->item(0)->

我编写了一个简短的PHP脚本来获取一个现有的XML文件,找到一个节点并将其更改为一个新值。新值必须包装到CDATA块中。这可以很好地工作,但是字符将替换为各自的HTML实体。这破坏了我在Java中的XML验证

<?php
$fileName = "whatever";

$doc = new DOMDocument();
$doc->load('test.xml');
$doc->getElementsByTagName("SomeNode")->item(0)->nodeValue = "<![CDATA[".$fileName."]]>";
header('Content-type: text/xml');
$doc->save("test.xml");
echo $doc->saveXML();

?>

假设您的
test.xml
文件是

<?xml version="1.0"?>
<Root>
    <FirstNode>
        <SomeNode>a</SomeNode>
    </FirstNode>
</Root>
或者您要在某个节点中替换

<SomeNode>
    a
    <![CDATA[whatever]]>
</SomeNode>
<SomeNode>
    <![CDATA[whatever]]>
</SomeNode>

不要使用
DOMNode::$nodeValue
写入值,空字符串除外。它的逃逸被打破了。创建XML节点有3个步骤:

1) 创建节点 2) 附加节点 3) 修改节点(可选)

创建节点 这取决于要创建的节点

元素节点:

$element = $document->createElement('nodename');
或文本节点:

$text = $document->createTextNode('<content>');
appendChild()的结果是追加的节点。因此,它可以与创建:

$element = $document->appendChild($document->createElement('nodename'));
修改节点 这主要是针对元素节点完成的。可以添加属性和子节点

$element->setAttribute('attr', 'value');
例子 输出:

<?xml version="1.0"?>
<nodename attr="value">&lt;content&gt;<![CDATA[<content>]]></nodename>
<?xml version="1.0"?>
<Root>
  <FirstNode>
    <SomeNode><![CDATA[<content>]]></SomeNode>
  </FirstNode>
</Root>

]]>
$someNode->nodeValue=''
。删除元素的所有子节点。这里没有实际的内容,因此逃逸的bug是不相关的。删除子项后,可以使用所需内容附加新的CDATA节


提示:尽可能使用文本节点,而不是CDATA节。CDATA部分禁用编码/转义功能。

这里有一个功能,谢谢。这似乎正是我所需要的……但它不起作用。我用结果更新了问题。@VeryAttractiveS没有将$cdata分配给nodeValue,而是使用appendChild,如@b.enoit.beSo close链接中的示例所示!这会将整个条目替换为。然后再次阅读答案并使用第一段代码。最后,我通过添加
$oldNode->nodeValue=“”,首先清除了节点的值
然后使用
appendChild($cdata)
。答案不太清楚,但我知道了。谢谢你的帮助!谢谢你的详细回答!最后一个例子正是我最后所做的(不包括xpath的使用)。我希望我能接受两个正确的答案。
$cdata = $document->createCDATASection('<content>');
$document->appendChild($element);
$element->appendChild($text);
$element->appendChild($cdata);
$element = $document->appendChild($document->createElement('nodename'));
$element->setAttribute('attr', 'value');
// create the document 
$document = new DOMDocument();

// create the document element node and append it
$element = $document->appendChild($document->createElement('nodename'));
// set an attribute on the element node
$element->setAttribute('attr', 'value');
// add a text node to the element node (escape <>)
$element->appendChild($document->createTextNode('<content>'));
// add a CDATA section to the element node (do not escape <>)
$element->appendChild($document->createCDATASection('<content>'));

echo $document->saveXml();
<?xml version="1.0"?>
<nodename attr="value">&lt;content&gt;<![CDATA[<content>]]></nodename>
$document = new DOMDocument();
$document->loadXml($xml);
$xpath = new DOMXPath($document);

foreach ($xpath->evaluate('/Root/FirstNode/SomeNode[1]') as $someNode) {
  $someNode->nodeValue = '';
  $someNode->appendChild($document->createCDATASection('<content>'));
}
echo $document->saveXml(); 
<?xml version="1.0"?>
<Root>
  <FirstNode>
    <SomeNode><![CDATA[<content>]]></SomeNode>
  </FirstNode>
</Root>