Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How can I set text value of SimpleXmlElement without using its parent?

Tags:

I want to set text of some node found by xpath()

<?php  $args = new SimpleXmlElement( <<<XML <a>   <b>     <c>text</c>     <c>stuff</c>   </b>   <d>     <c>code</c>   </d> </a> XML );  // I want to set text of some node found by xpath  // Let's take (//c) for example  // convoluted and I can't be sure I'm setting right node $firstC = reset($args->xpath("//c[1]/parent::*"));  $firstC->c[0] = "test 1";  // like here: Found node is not actually third in its parent. $firstC = reset($args->xpath("(//c)[3]/parent::*"));  $firstC->c[2] = "test 2";  // following won't work for obvious reasons,  // some setText() method would be perfect but I can't find nothing similar,  $firstC = reset($args->xpath("//c[1]")); $firstC = "test";   // maybe there's some hack for it? $firstC = reset($args->xpath("//c[1]")); $firstC->{"."} = "test"; // nope, just adds child named . $firstC->{""} = "test"; // still not right, 'Cannot write or create unnamed element' $firstC["."] = "test"; // still no luck, adds attribute named . $firstC[""] = "test"; // still no luck, 'Cannot write or create unnamed attribute' $firstC->addChild('','test'); // grr, 'SimpleXMLElement::addChild(): Element name is required' $firstC->addChild('.','test'); // just adds another child with name .  echo $args->asXML();  // it outputs: //  // PHP Warning:  main(): Cannot add element c number 2 when only 1 such elements exist  // PHP Warning:  main(): Cannot write or create unnamed element  // PHP Warning:  main(): Cannot write or create unnamed attribute  // PHP Warning:  SimpleXMLElement::addChild(): Element name is required  // <?xml version="1.0"? > // <a> //  <b> //   <c .="test">test 1<.>test</.><.>test</.></c> //   <c>stuff</c> //  </b> //  <d> //   <c>code</c> //  <c>test 2</c></d> // </a> 
like image 226
Kamil Szot Avatar asked Jun 30 '10 21:06

Kamil Szot


2 Answers

You can do with a SimpleXMLElement self-reference:

$firstC->{0} = "Victory!!"; // hackity, hack, hack! //  -or- $firstC[0]   = "Victory!!"; 

found after looking at

var_dump((array) reset($xml->xpath("(//c)[3]"))) 

This also works with unset operations as outlined in an answer to:

  • Remove a child with a specific attribute, in SimpleXML for PHP
like image 139
Kamil Szot Avatar answered Jan 03 '23 12:01

Kamil Szot


The real answer is: you kind of can't.

On the other hand you can use DOM for it, e.g.

dom_import_simplexml($node)->nodeValue = 'foo'; 
like image 43
Josh Davis Avatar answered Jan 03 '23 10:01

Josh Davis