PHP – Дублирующий узел XML с использованием Simple XML

Мне нужно загрузить источник XML с помощью Simple XML, дублировать существующий узел со всеми его дочерними элементами, а затем настроить атрибут этого нового узла перед рендерингом XML. Любое предложение?

SimpleXML не может этого сделать, поэтому вам придется использовать DOM . Хорошей новостью является то, что DOM и SimpleXML являются двумя сторонами одной и той же монеты, libxml. Поэтому, независимо от того, используете ли вы SimpleXML или DOM, вы работаете над одним и тем же деревом. Вот пример:

$thing = simplexml_load_string( '<thing> <node n="1"><child/></node> </thing>' ); $dom_thing = dom_import_simplexml($thing); $dom_node = dom_import_simplexml($thing->node); $dom_new = $dom_thing->appendChild($dom_node->cloneNode(true)); $new_node = simplexml_import_dom($dom_new); $new_node['n'] = 2; echo $thing->asXML(); 

Если вы делаете такие вещи много, вы можете попробовать SimpleDOM , который является расширением для SimpleXML, который позволяет напрямую использовать методы DOM, не переходя из объектов DOM и DOM.

 include 'SimpleDOM.php'; $thing = simpledom_load_string( '<thing> <node n="1"><child/></node> </thing>' ); $new = $thing->appendChild($thing->node->cloneNode(true)); $new['n'] = 2; echo $thing->asXML(); 

С SimpleXML лучший способ, который я нашел, – обходной путь. Это довольно бобо, но он работает:

 // Strip it out so it's not passed by reference $newNode = new SimpleXMLElement($xml->someNode->asXML()); // Modify your value $newnode['attribute'] = $attValue; // Create a dummy placeholder for it wherever you need it $xml->addChild('replaceMe'); // Do a string replace on the empty fake node $xml = str_replace('<replaceMe/>',$newNode->asXML(),$xml->asXML()); // Convert back to the object $xml = new SimpleXMLElement($xml); # leave this out if you want the xml 

Поскольку это обходной путь для функции, которая, кажется, не существует в SimpleXML, вам нужно знать, что я ожидаю, что это нарушит любые ссылки на объекты, которые вы определили до этого момента, если они есть.

Попробуйте следующее

 // Get the node you need $node = $xml->root->someNode->nodetoDuplicate[0]; // Edit the node $node["someAttribute"] = "newValue"; // Add node as a child $xml->root->someNode[0].addChild($node);