0

I am using this class for porting array to XML:

class ArrayToXML
{
    /**
     * The main function for converting to an XML document.
     * Pass in a multi dimensional array and this recrusively loops through and builds up an XML document.
     *
     * @param array $data
     * @param string $rootNodeName - what you want the root node to be - defaultsto data.
     * @param SimpleXMLElement $xml - should only be used recursively
     * @return string XML
     */
    public static function toXml($data, $rootNodeName = 'data', &$xml=null)
    {
        // turn off compatibility mode as simple xml throws a wobbly if you don't.
        if (ini_get('zend.ze1_compatibility_mode') == 1)
        {
            ini_set ('zend.ze1_compatibility_mode', 0);
        }

        if (is_null($xml))
        {
            $xml = simplexml_load_string("");
        }

        // loop through the data passed in.
        foreach($data as $key => $value)
        {
            // if numeric key, assume array of rootNodeName elements
            if (is_numeric($key))
            {
                $key = $rootNodeName;
            }

            // delete any char not allowed in XML element names
            $key = preg_replace('/[^a-z0-9\-\_\.\:]/i', '', $key);

            // if there is another array found recrusively call this function
            if (is_array($value))
            {
                // create a new node unless this is an array of elements
                $node = ArrayToXML::isAssoc($value) ? $xml->addChild($key) : $xml;

                // recrusive call - pass $key as the new rootNodeName
                ArrayToXML::toXml($value, $key, $node);
            }
            else
            {
                // add single node.
                $value = htmlentities($value);
                $xml->addChild($key,$value);
            }

        }
        // pass back as string. or simple xml object if you want!
        return $xml->asXML();
    }

    // determine if a variable is an associative array
    public static function isAssoc( $array ) {
        return (is_array($array) && 0 !== count(array_diff_key($array, array_keys(array_keys($array)))));
    }
}

and I am calling this function with this code sample just to test a bit:

require_once('test_xml.php');
$library = array(
    'book' => array(
        array(
            'authorFirst' => 'Mark',
            'authorLast' => 'Twain',
            'title' => 'The Innocents Abroad'
        ),
        array(
            'authorFirst' => 'Charles',
            'authorLast' => 'Dickens',
            'title' => 'Oliver Twist'
        )
    )
);
$ArrayToXml=new ArrayToXml();
$ArrayToXml->toXml($library)

And I am getting this error: Fatal error: Call to a member function addChild() on a non-object in on line 42.

Any idea what has went wrong? Thank you.

EDIT: Line 42: $node = ArrayToXML::isAssoc($value) ? $xml->addChild($key) : $xml;

EDIT2: With all do respect guys, this code is ain't working yet. Answer was correct, but I only get MarkTwainCharlesDickens as an output. And I shoud get properly formed XML. Should I enable some extensions? But I have already seen that simplexml is enabled.

Any help is appreciated.

0

1 Answer 1

2

You cannot create an XML document out of an empty string.

var_dump(simplexml_load_string(""));
bool(false)

vs

var_dump(simplexml_load_string("<root/>"));
object(SimpleXMLElement)#1 (0) {}

To get the book value out of your $data:

$root = key($data);
$rootNode = "<{$root}/>";
Sign up to request clarification or add additional context in comments.

7 Comments

thank you for the answer but I need to add something like this in when sending array to function if I understood correctly: $var="<root/>"; $ArrayToXml->toXml($library,'data',$var);
You need to know what you XML file will look like and fix that call to simplexml_load_string accordingly. $rootNodeName seems to be a good candidate for it, doesn't it?
For example I want to look like my above test code. book would be root node and then name..as in example..but how to send data to make this code work
something like that: simplexml_load_string("<".key($data)."/>");
I get it working using the two files above and the fix I gave you: pastie.org/private/rmumpjgfyppqolzurfna
|

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.