如何使用xquery查找节点和addChild?

时间:2014-12-15 14:35:22

标签: php xml xpath xquery

是否可以使用xpath / xquery查询特定的xml节点,然后导入/添加子节点?

示例(代码取自http://codepad.org/gJ1Y2LjM,在类似问题中提出,但不一样):

1。 我想添加一个数组

$book = array('isbn'=>123456789099, 'title' => 'Harry Potter 3', 'author' => 'J K. Rowling', 'edition' => '2007');

2。 到现有的XML。

$doc = new DOMDocument();
$doc->loadXML('<?xml version="1.0"?>
<books>
    <book>
        <isbn>123456789098</isbn>
        <title>Harry Potter</title>
        <author>J K. Rowling</author>
        <edition>2005</edition>
    </book>
    <book>
        <placeItHere></placeItHere>
        <isbn>1</isbn>
        <title>stuffs</title>
        <author>DA</author>
        <edition>2014</edition>
    </book>
</books>');

3。 为此,使用以下片段。

$fragment = $doc->createDocumentFragment();
$fragment->appendXML("    <book>
<isbn>{$book['isbn']}</isbn>
        <title>{$book['title']}</title>
        <author>{$book['author']}</author>
        <edition>{$book['edition']}</edition>
    </book>
");

4。 但是,不是将其附加到根节点,而是几乎我在互联网上找到的每个例子:

$doc->documentElement->appendChild($fragment);

5。 我想将它(p.ex)附加到/ books / book / placeItHere中找到的节点,而不是使用getElementbyId或tagName,而是使用xpath / xquery。我试过

$xp = new domxpath($doc);
$parent = $xp->query("books/book/placeItHere");

到达节点,但从未设法将其用作父节点。

问题:如何使用该位置appendChild $ fragment?有可能吗?

**YOUR BEAUTIFUL MAGIC**

最后我会保存它。

echo $doc->saveXML();

感谢您给予我任何帮助。

1 个答案:

答案 0 :(得分:1)

一些问题:

  1. 您的xpath表达式应为/books/book/placeItHere(带有前导/)。
  2. DOMXPath::query()会返回DOMNodeList而不是DOMNode,因此您需要从中抓取item()
  3. 我很少推荐使用文档片段,因为使用原始XML快速播放会导致出现问题。例如,如果您的图书标题包含&符号appendXML(),则会出现解析器错误。

    相反,我建议使用createElement()createTextNode(),它会自动将&之类的内容转换为&amp;


    实施例

    $xml = <<<'XML'
    <?xml version="1.0"?>
    <books>
        <book>
            <isbn>123456789098</isbn>
            <title>Harry Potter</title>
            <author>J K. Rowling</author>
            <edition>2005</edition>
        </book>
        <book>
            <placeItHere></placeItHere>
            <isbn>1</isbn>
            <title>stuffs</title>
            <author>DA</author>
            <edition>2014</edition>
        </book>
    </books>
    XML;
    
    $book = [
        'isbn'    => 123456789099,
        'title'   => 'Harry Potter 3',
        'author'  => 'J K. Rowling',
        'edition' => '2007'
    ];
    
    $dom = new DOMDocument();
    $dom->formatOutput = true;
    $dom->preserveWhiteSpace = false;
    $dom->loadXML($xml);
    $xpath = new DOMXPath($dom);
    
    $placeItHere = $xpath->query('/books/book/placeItHere')->item(0);
    $newBook = $placeItHere->appendChild($dom->createElement('book'));
    foreach ($book as $part => $value) {
        $element = $newBook->appendChild($dom->createElement($part));
        $element->appendChild($dom->createTextNode($value));
    }
    
    echo $dom->saveXML();
    

    输出:

    <?xml version="1.0"?>
    <books>
      <book>
        <isbn>123456789098</isbn>
        <title>Harry Potter</title>
        <author>J K. Rowling</author>
        <edition>2005</edition>
      </book>
      <book>
        <placeItHere>
          <book>
            <isbn>123456789099</isbn>
            <title>Harry Potter 3</title>
            <author>J K. Rowling</author>
            <edition>2007</edition>
          </book>
        </placeItHere>
        <isbn>1</isbn>
        <title>stuffs</title>
        <author>DA</author>
        <edition>2014</edition>
      </book>
    </books>