Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
98 changes: 58 additions & 40 deletions LSS/Array2XML.php
Original file line number Diff line number Diff line change
Expand Up @@ -2,23 +2,24 @@
/**
* OpenLSS - Lighter Smarter Simpler
*
* This file is part of OpenLSS.
* This file is part of OpenLSS.
*
* OpenLSS is free software: you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License as
* published by the Free Software Foundation, either version 3 of
* the License, or (at your option) any later version.
* OpenLSS is free software: you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License as
* published by the Free Software Foundation, either version 3 of
* the License, or (at your option) any later version.
*
* OpenLSS is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Lesser General Public License for more details.
* OpenLSS is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Lesser General Public License for more details.
*
* You should have received a copy of the
* GNU Lesser General Public License along with OpenLSS.
* If not, see <http://www.gnu.org/licenses/>.
*/
* You should have received a copy of the
* GNU Lesser General Public License along with OpenLSS.
* If not, see <http://www.gnu.org/licenses/>.
*/
namespace LSS;

use \DomDocument;
use \Exception;

Expand Down Expand Up @@ -48,16 +49,20 @@
* - Reverted to version 0.5
* Version: 0.8 (02 May 2012)
* - Removed htmlspecialchars() before adding to text node or attributes.
* Version: 0.11 (28 October 2015)
* - Fixed typos; Added support for plain insertion of XML trough @xml.
*
* Usage:
* $xml = Array2XML::createXML('root_node_name', $php_array);
* echo $xml->saveXML();
*/

class Array2XML {

/**
* @var DOMDocument
*/
private static $xml = null;
private static $encoding = 'UTF-8';
private static $encoding = 'UTF-8';

/**
* Initialize the root XML node [optional]
Expand All @@ -68,7 +73,7 @@ class Array2XML {
public static function init($version = '1.0', $encoding = 'UTF-8', $format_output = true) {
self::$xml = new DomDocument($version, $encoding);
self::$xml->formatOutput = $format_output;
self::$encoding = $encoding;
self::$encoding = $encoding;
}

/**
Expand All @@ -77,7 +82,7 @@ public static function init($version = '1.0', $encoding = 'UTF-8', $format_outpu
* @param array $arr - aray to be converterd
* @return DomDocument
*/
public static function &createXML($node_name, $arr=array()) {
public static function &createXML($node_name, $arr = array()) {
$xml = self::getXMLRoot();
$xml->appendChild(self::convert($node_name, $arr));

Expand All @@ -86,23 +91,29 @@ public static function &createXML($node_name, $arr=array()) {
}

/**
* Convert an Array to XML
* @param string $node_name - name of the root node to be converted
* @param array $arr - aray to be converterd
* @return DOMNode
* Convert an Array to XML.
*
* @param string $node_name
* Name of the root node to be converted.
* @param array $arr
* Array to be converted.
*
* @throws \Exception
*
* @return \DOMNode
*/
private static function &convert($node_name, $arr=array()) {
private static function &convert($node_name, $arr = array()) {

//print_arr($node_name);
$xml = self::getXMLRoot();
$node = $xml->createElement($node_name);

if(is_array($arr)){
if (is_array($arr)) {
// get the attributes first.;
if(isset($arr['@attributes'])) {
foreach($arr['@attributes'] as $key => $value) {
if(!self::isValidTagName($key)) {
throw new Exception('[Array2XML] Illegal character in attribute name. attribute: '.$key.' in node: '.$node_name);
if (isset($arr['@attributes'])) {
foreach ($arr['@attributes'] as $key => $value) {
if (!self::isValidTagName($key)) {
throw new Exception('[Array2XML] Illegal character in attribute name. attribute: ' . $key . ' in node: ' . $node_name);
}
$node->setAttribute($key, self::bool2str($value));
}
Expand All @@ -111,31 +122,38 @@ private static function &convert($node_name, $arr=array()) {

// check if it has a value stored in @value, if yes store the value and return
// else check if its directly stored as string
if(isset($arr['@value'])) {
if (isset($arr['@value'])) {
$node->appendChild($xml->createTextNode(self::bool2str($arr['@value'])));
unset($arr['@value']); //remove the key from the array once done.
//return from recursion, as a note with value cannot have child nodes.
return $node;
} else if(isset($arr['@cdata'])) {
} else if (isset($arr['@cdata'])) {
$node->appendChild($xml->createCDATASection(self::bool2str($arr['@cdata'])));
unset($arr['@cdata']); //remove the key from the array once done.
//return from recursion, as a note with cdata cannot have child nodes.
return $node;
}
else if (isset($arr['@xml'])) {
$fragment = $xml->createDocumentFragment();
$fragment->appendXML($arr['@xml']);
$node->appendChild($fragment);
unset($arr['@xml']);
return $node;
}
}

//create subnodes using recursion
if(is_array($arr)){
if (is_array($arr)) {
// recurse to get the node for that key
foreach($arr as $key=>$value){
if(!self::isValidTagName($key)) {
throw new Exception('[Array2XML] Illegal character in tag name. tag: '.$key.' in node: '.$node_name);
foreach ($arr as $key => $value) {
if (!self::isValidTagName($key)) {
throw new Exception('[Array2XML] Illegal character in tag name. tag: ' . $key . ' in node: ' . $node_name);
}
if(is_array($value) && is_numeric(key($value))) {
if (is_array($value) && is_numeric(key($value))) {
// MORE THAN ONE NODE OF ITS KIND;
// if the new array is numeric index, means it is array of nodes of the same kind
// it should follow the parent key name
foreach($value as $k=>$v){
foreach ($value as $k => $v) {
$node->appendChild(self::convert($key, $v));
}
} else {
Expand All @@ -148,7 +166,7 @@ private static function &convert($node_name, $arr=array()) {

// after we are done with all the keys in the array (if it is one)
// we check if it has any text value, if yes, append it.
if(!is_array($arr)) {
if (!is_array($arr)) {
$node->appendChild($xml->createTextNode(self::bool2str($arr)));
}

Expand All @@ -158,8 +176,8 @@ private static function &convert($node_name, $arr=array()) {
/*
* Get the root XML node, if there isn't one, create it.
*/
private static function getXMLRoot(){
if(empty(self::$xml)) {
private static function getXMLRoot() {
if (empty(self::$xml)) {
self::init();
}
return self::$xml;
Expand All @@ -168,7 +186,7 @@ private static function getXMLRoot(){
/*
* Get string representation of boolean value
*/
private static function bool2str($v){
private static function bool2str($v) {
//convert boolean to text value.
$v = $v === true ? 'true' : $v;
$v = $v === false ? 'false' : $v;
Expand All @@ -179,7 +197,7 @@ private static function bool2str($v){
* Check if the tag name or attribute name contains illegal characters
* Ref: http://www.w3.org/TR/xml/#sec-common-syn
*/
private static function isValidTagName($tag){
private static function isValidTagName($tag) {
$pattern = '/^[a-z_]+[a-z0-9\:\-\.\_]*[^:]*$/i';
return preg_match($pattern, $tag, $matches) && $matches[0] == $tag;
}
Expand Down
32 changes: 32 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,38 @@ $array = XML2Array::createArray($xml);
print_r($array);
```

Array2XML
----

@xml example:
```php
// Build the array that should be transformed into a XML object.
$array = [
'title' => 'A title',
'body' => [
'@xml' => '<html><body><p>The content for the news item</p></body></html>',
],
];

// Use the Array2XML object to transform it.
$xml = Array2XML::createXML('news', $array);
echo $xml->saveXML();
```
This will result in the following.
```xml
<?xml version="1.0" encoding="UTF-8"?>
<news>
<title>A title</title>
<body>
<html>
<body>
<p>The content for the news item</p>
</body>
</html>
</body>
</news>
```

Reference
----
More complete references can be found here
Expand Down