小编典典

CakePHP Xml实用程序库触发DOMDocument警告

php

我正在使用CakePHP的Xml核心库在视图中生成XML :

$xml = Xml::build($data, array('return' => 'domdocument'));
echo $xml->saveXML();

视图由控制器通过数组提供:

$this->set(
    array(
        'data' => array(
            'root' => array(
                array(
                    '@id' => 'A & B: OK',
                    'name' => 'C & D: OK',
                    'sub1' => array(
                        '@id' => 'E & F: OK',
                        'name' => 'G & H: OK',
                        'sub2' => array(
                            array(
                                '@id' => 'I & J: OK',
                                'name' => 'K & L: OK',
                                'sub3' => array(
                                    '@id' => 'M & N: OK',
                                    'name' => 'O & P: OK',
                                    'sub4' => array(
                                        '@id' => 'Q & R: OK',
                                        '@'   => 'S & T: ERROR',
                                    ),
                                ),
                            ),
                        ),
                    ),
                ),
            ),
        ),
    )
);

无论出于何种原因,CakePHP都会发出这样的内部调用:

$dom = new DOMDocument;
$key = 'sub4';
$childValue = 'S & T: ERROR';
$dom->createElement($key, $childValue);

…会触发PHP警告:

Warning (2): DOMDocument::createElement(): unterminated entity reference               T [CORE\Cake\Utility\Xml.php, line 292

…因为(如记录所示DOMDocument::createElement不会转义值。但是,如测试用例所示,它仅在某些节点中执行此操作。

我是在做错什么,还是刚遇到CakePHP中的错误?


阅读 219

收藏
2020-05-29

共1个答案

小编典典

问题似乎出在具有属性和值的节点中,因此需要使用以下@语法:

'@id' => 'A & B: OK',  // <-- Handled as plain text
'name' => 'C & D: OK', // <-- Handled as plain text
'@' => 'S & T: ERROR', // <-- Handled as raw XML

我写了一些辅助函数:

protected function escapeXmlValue($value){
    return is_null($value) ? null : htmlspecialchars($value, ENT_XML1, 'UTF-8');
}

…并在创建数组时注意手动调用它:

'@id' => 'A & B: OK',
'name' => 'C & D: OK',
'@' => $this->escapeXmlValue('S & T: NOW WORKS FINE'),

由于文档中没有提及它,因此很难说它是错误还是功能。

2020-05-29