简体   繁体   中英

appendChild using DOMDocument/PHP/XML

I am trying to update my XML file based on an HTML form processed by PHP but the new XML snippet I am trying to append to specific areas of my current XML just keeps getting added to the end of my document.

$specific_node = "0"; //this is normally set by a select input from the form.
$doc = new DOMDocument();
$doc->load( 'rfp_files.xml' );
$doc->formatOutput = true;

//below is where my issue is having problems the variable '$specific_node' can be one of three options 0,1,2 and what I am trying to do is find the child of content_sets. So the first second or third child elemts and that is where I will add my new bit of XML
$r = $doc->getElementsByTagname('content_sets')->item($specific_node);

//This is where I build out my new XML to append
$fileName = $doc->createElement("file_name");
$fileName->appendChild(
    $doc->createTextNode( $Document_Array["url"] )
);
$b->appendChild( $fileName );

//this is were I add the new XML to the child node mention earlier in the script. 
$r->appendChild( $b );

XML Example:

<?xml version="1.0" encoding="UTF-8"?>
<content_sets>
  <doc_types>
    <article>
      <doc_name>Additional</doc_name>
      <file_name>Additional.docx</file_name>
      <doc_description>Test Word document. Please remove when live.</doc_description>
      <doc_tags>word document,test,rfp template,template,rfp</doc_tags>
      <last_update>01/26/2013 23:07</last_update>
    </article>
  </doc_types>
  <video_types>
    <article>
      <doc_name>Test Video</doc_name>
      <file_name>test_video.avi</file_name>
      <doc_description>Test video. Please remove when live.</doc_description>
      <doc_tags>test video,video, avi,xvid,svid avi</doc_tags>
      <last_update>01/26/2013 23:07</last_update>
    </article>
  </video_types>
  <image_types>
    <article>
     <doc_name>Test Image</doc_name>
     <file_name>logo.png</file_name>
     <doc_description>Logo transparent background. Please remove when live.</doc_description>
     <doc_tags>png,logo,logo png,no background,graphic,hi res</doc_tags>
     <last_update>01/26/2013 23:07</last_update>
    </article>
  </image_types>
</content_sets>

This is getting the root element:

$specific_node = "0";
$r = $doc->getElementsByTagname('content_sets')->item($specific_node);

So you are appending a child onto the root which is why you always see it added near the end of the document. You need to get the children of the root element like this:

$children = $doc->documentElement->childNodes;

This can return several types of node , but you are only interested in 'element' type nodes. It's not very elegant, but the only way I've found to get a child element by position is looping like this...

$j = 0;
foreach ($doc->documentElement->childNodes as $r) 
    if ($r->nodeType === XML_ELEMENT_NODE && $j++ == $specific_node) 
        break;

if ($j <= $specific_node)
    // handle situation where $specific_node is more than number of elements

You could use getElementsByTagName() if you can pass the name of the node required instead of the ordinal position, or change the XML so that the child elements all have the same name and use an attribute to differentiate them.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM