开发者

How do you merge two XML documents in PHP using SimpleXML?

I have a database row that looks like this.

ID (int):       123
Name (string):  SomeName
Data (string):  <data><foo>one</foo></bar>two</bar></data>

I need to format this data as XML in the following way.

<row>
  <id>123</id>
  <name>SomeName</name>
  <data>
    <foo>one</foo>
    <bar>two</bar>
  </data>
<row>

I'm currently using SimpleXML to try to build this, but I'm not sure how to go about inserting the existing XML into the new XML document I'm trying to build.

If there are other standard XML builders that come with PHP, I'm open to using those, too. String concatenation is not an acceptable answer.

Edit: It looks as though SimpleXML won't do what I need. I guess at this point, I need suggestions for other XML pars开发者_如何转开发ers.


$xml = new SimpleXMLElement('<row></row>');
$xml->addChild('id', /*database ID column*/);
$xml->addChild('name', /*database Name column*/);

$data = new SimpleXMLElement(/*database Data column*/);

$xml->addChild('data');
$xml->data->addChild('foo', $data->foo);
$xml->data->addChild('bar', $data->bar);

Tested and it works. It should be trivial to convert this to your actual application. There may be a more flexible way of doing it, but I'm not aware of it. They don't call it SimpleXML for nothing :)


$xml = '<data><foo>one</foo><bar>two</bar></data>'; // your data field

$row = new SimpleXMLElement('<row></row>'); // new row to inject your database fields into
$data = new SimpleXMLElement($xml); // new object from your xml data field

$row->id = '123'; // your id field
$row->name = 'Somename'; // your name field
$row->data->foo = $data->foo; // your foo record from your xml data field
$row->data->bar = $data->bar; // your bar record from your xml data field

$final_xml = $row->saveXML(); // restructure your xml file/string
echo $final_xml; // <?xml version="1.0"?><row><id>123</id><name>Somename</name><data><foo>one</foo><bar>two</bar></data></row>

Tested this code and it also works. You will have to create two SimpleXml Objects like the answer above. Other than that you can just add additional elements like adding class vars. A <?xml version="1.0"?> will be added to the final xml string/file.

Not sure if you need the <?xml version="1.0"?>. If not you can take it out with:

$final_xml = str_replace("<?xml version=\"1.0\"?>\n",'',$final_xml);

You can check out http://www.php.net/manual/en/simplexmlelement.asxml.php for more info on re-saving SimpleXml objects back to xml strings/files.


/**
* Converts your record to XML.
* 
* @param array/object $record
* @return SimpleXMLElement
*/
function ConvertToXml($record){
    // Objects need to be arrays
    if(is_object($record)){
        $record = get_object_vars($record);
    }

    // We need an array argument
    if(!is_array($record)){
        trigger_error('$record must be an object or an array.', E_USER_WARNING);
        return null;
    }

    // Now we build XML
    ob_start();
    echo '<xml>', PHP_EOL;
    foreach($record as $name => $value){
        if(is_object($value) or is_array($value) or is_resource($value)){
            trigger_error('$record must have only scalar values.', E_USER_WARNING);
            return null;
        }
        if(!is_string($name) or !preg_match('~[a-z_][a-z0-9]*~i', $name)){
            trigger_error('$record must have only XML-tag friendly string keys.', E_USER_WARNING);
            return null;
        }

        // NULL produces an empty node
        if(is_null($value)){
            echo "<{$name} />", PHP_EOL;
            continue;
        }

        // Numerics don't need to be XML encoded
        if(is_integer($value) or is_float($value) or is_bool($value)){
            echo "<{$name}>{$value}</{$name}>", PHP_EOL;
            continue;
        }

        // We must have a string now
        if(!is_string($name)){
            trigger_error('$record must have only scalar values.', E_USER_WARNING);
            return null;
        }

        // Do we have an XML field?
        if(preg_match('~^\s*<.+>\s*$~s', $value)){
            // Test it for real!
            if($xml = @simplexml_load_string("<xml>{$value}</xml>")){
                echo $value, PHP_EOL;
                continue;
            }
        }

        // Now output random strings
        echo "<{$name}>", htmlentities($value, ENT_QUOTES, 'utf-8'), "</{$name}>", PHP_EOL;
    }
    echo '</xml>', PHP_EOL;

    // Store built XML
    $xml = ob_get_clean();

    // Load the built XML
    return @simplexml_load_string($xml);;
}

// Prepare an array
$record = array();
$record['ID'] = 1;
$record['Name'] = 'SomeName';
$record['Data'] = '<data><foo>one</foo><bar>two</bar></data>';
if($xml = ConvertToXml($record)){
    echo $xml->asXML();
}

^ An answer for posterity.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜