Xpoint
   [напомнить пароль]

Соединение XML файлов в php

Метки: [без меток]
2010-03-18 02:52:25 [обр] met[досье]

Долго мучаюсь с проблемой. Как выбрать нескольк xml файлов и соединить их в один.
Суть такая. Есть несколько xml файлов. Хочу выбрать их средствами php и создать новый xml такой структуры
<src>
    первый xml файл (только без "шапки" <?xml version="1.0" encoding="Windows-1251"?><?xml-stylesheet type="text/xsl" ?>)
    ....
    последний xml файл
</src>
Приведу отрывок кода:

$dir = "../orders/"; // директорий с xml файлами
$orders = scandir($dir); //загружаем файлы
array_shift($orders); //удаляем лишнее
array_shift($orders);

$domxml = new DOMDocument(); //будем использовать для загрузки файлов
$dom = new DOMDocument(); // для создания нового xml файла
$src = $dom->createElement('src'); //создаю тэг, в который хочу подключать xml файлы
$dom->appendChild($src); //тэг создан
foreach ($orders as $ors) // перебираю xml файлы
{
        $domxml->load($dir.$ors);
   $xp = new DOMXPath($domxml);
   $yy = $xp->query("/root"); //вытаскиваю содержимое
   foreach ($yy as $y) // пытаюсь подключить вытащенное содержимое в созданный ранее тег <src></src> дочерными узлами
   {
       $src->appendChild($y);
   }
}
И вот во втором цыкле проблема - Fatal Error типа: 'Wrong Document Error' а все из-за того, что DOMNode->appendChild(Object(DOMElement)). Компилятор справедливо ругается, требуя вместо DOMElement объект типа DOMNode, но откуда, бога ради, там взялся DOMElement, если DOMNodelist::item должен возвращать объект типа DOMNode! И хотя DOMElement является наследует DOMNode, от этого ничуть не легче, компилятору как-то все равно, ему надо DOMNode и все тут.
Какой ФАК мне надо прочитать, чтобы разобраться наконец с этой чертовой проблемой!?
P.S. Прошу прощения за неоформленный код, но я так и не нашел на сайте, каким способом отделять код от текста 0_о

спустя 9 часов [обр] Амир(0/4)[досье]
незнаю правильно ли, при помощи simplexml_load_file объединял файлы xml я.
Вроде работает.
как правильно обьединить несколько xml файлов, средствами PHP ?
спустя 3 часа 8 минут [обр] Marat Tanalin(0/78)[досье]

DOMDocument::importNode?

P. S. Описание псевдоразметки доступно по щелчку на кнопке слева от поля ввода.

спустя 1 день 2 часа [обр] met[досье]

Спасибо, всем откликнувшимся.
Амир,
признателен Вам за помощь, вобщем я разбирал ваш вариант, но остановился когда дошел до preg_replace :-). Вариант имеет право на жизнь, на крайний случай его можно использовать, но все же использование DOMDocument::importNode облегчит вам жизнь, и не надо будет лишних preg_replace использовать.

MT,
просто Большое спасибо! :)

спустя 16 минут [обр] met[досье]
Кстати, Амир, я дописал в вашу тему наброски как можно усовершенствовать ваш скрипт.
И еще, все таки непонятным остается вопрос, почему метод DOMNodelist::item возвращает объект DOMElement, при этом DOMDocument::importNode прекрасно его видит, хотя должен бы ругаться как и DOMNode::appendChild, потому что оба метода воспринимают только объекты типа DOMNode.
спустя 46 минут [обр] Marat Tanalin(0/78)[досье]
DOMElement наследуется от DOMNode.
спустя 22 часа [обр] met[досье]

Это так, но все же, посмотрите что получается:

$dom = new DOMDocument();
$src = $dom->createElement('src');
$dom->appendChild($src);
$domxml = new DOMDocument();
$domxml->load("example.xml");
$xp = new DOMXPath($domxml);
$yy = $xp->query("/root");
foreach ($yy as $y){
   print_r($y);
   $node = $dom->importNode($y, true); 
   print_r($node);
   print_r($src);
   $x = $src->appendChild($node);
   print_r($x);
   $src->appendChild($y);
}

Простой пример с выводом типов переменных на печать. Все объекты $y, $node, $x, $src - объекты типа DOMElement, что показывает функция print_r(). Но $src->appendChild($node); ошибки не выдает, а $src->appendChild($y); - выдает. То есть, имеем объекты одинакового типа, вызывает их одна и та же переменная, но в одном случае есть ошибка, а в другом нет. Это немного озадачивает.

спустя 4 часа 2 минуты [обр] Marat Tanalin(0/78)[досье]
Методу appendChild() не нравится не тип объекта, а документ, к которому он принадлежит. importNode() не делает ничего магического, а просто создаёт копию узла, которая, в отличие от исходного объекта, принадлежит к документу, для которого этот метод вызван.
спустя 1 день 4 часа [обр] met[досье]
Ага, теперь понятно, да, действительно $dom и $xp разные документы. Хотя и сообщение наводящще же было exception with message 'Wrong Document Error', все равно сам бы не додумался. Просто в голову бы не пришло, что для интерпретатора это важно.
Спасибо еще раз.
спустя 9 минут [обр] Marat Tanalin(0/78)[досье]
Интерпретатор следует стандарту.
спустя 1 день 16 часов [обр] met[досье]
Ясно, думал это особенность реализации в php такая, а нет, стандарт. Но вот эта фраза совсем не понравилась. Different DOMs may implement Nodes in completely different ways, and the implementation details may not be compatable even though both support the same public APIs. Это же, наверное, немного отход в сторону от принципов ООП, но видимо у разработчиков стандарта не было другого выхода.
Powered by POEM™ Engine Copyright © 2002-2005