Skip to content

Commit 14d1351

Browse files
committed
added new sdk API handling for cluster communication
1 parent e544e4f commit 14d1351

1 file changed

Lines changed: 303 additions & 0 deletions

File tree

lib/array2xml.php

Lines changed: 303 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,303 @@
1+
<?php
2+
/**
3+
* Array2XML: A class to convert array in PHP to XML
4+
* It also takes into account attributes names unlike SimpleXML in PHP
5+
* It returns the XML in form of DOMDocument class for further manipulation.
6+
* It throws exception if the tag name or attribute name has illegal chars.
7+
*
8+
* Author : Lalit Patel
9+
* Website: http://www.lalit.org/lab/convert-php-array-to-xml-with-attributes
10+
* License: Apache License 2.0
11+
* http://www.apache.org/licenses/LICENSE-2.0
12+
* Version: 0.1 (10 July 2011)
13+
* Version: 0.2 (16 August 2011)
14+
* - replaced htmlentities() with htmlspecialchars() (Thanks to Liel Dulev)
15+
* - fixed a edge case where root node has a false/null/0 value. (Thanks to Liel Dulev)
16+
* Version: 0.3 (22 August 2011)
17+
* - fixed tag sanitize regex which didn't allow tagnames with single character.
18+
* Version: 0.4 (18 September 2011)
19+
* - Added support for CDATA section using @cdata instead of @value.
20+
* Version: 0.5 (07 December 2011)
21+
* - Changed logic to check numeric array indices not starting from 0.
22+
* Version: 0.6 (04 March 2012)
23+
* - Code now doesn't @cdata to be placed in an empty array
24+
* Version: 0.7 (24 March 2012)
25+
* - Reverted to version 0.5
26+
* Version: 0.8 (02 May 2012)
27+
* - Removed htmlspecialchars() before adding to text node or attributes.
28+
*
29+
* Usage:
30+
* $xml = Array2XML::createXML('root_node_name', $php_array);
31+
* echo $xml->saveXML();
32+
*/
33+
34+
class Array2XML {
35+
36+
private static $xml = null;
37+
private static $encoding = 'UTF-8';
38+
39+
/**
40+
* Initialize the root XML node [optional]
41+
* @param $version
42+
* @param $encoding
43+
* @param $format_output
44+
*/
45+
public static function init($version = '1.0', $encoding = 'UTF-8', $format_output = true) {
46+
self::$xml = new DomDocument($version, $encoding);
47+
self::$xml->formatOutput = $format_output;
48+
self::$encoding = $encoding;
49+
}
50+
51+
/**
52+
* Convert an Array to XML
53+
* @param string $node_name - name of the root node to be converted
54+
* @param array $arr - aray to be converterd
55+
* @return DomDocument
56+
*/
57+
public static function &createXML($node_name, $arr=array()) {
58+
$xml = self::getXMLRoot();
59+
$xml->appendChild(self::convert($node_name, $arr));
60+
61+
self::$xml = null; // clear the xml node in the class for 2nd time use.
62+
return $xml;
63+
}
64+
65+
/**
66+
* Convert an Array to XML
67+
* @param string $node_name - name of the root node to be converted
68+
* @param array $arr - aray to be converterd
69+
* @return DOMNode
70+
*/
71+
private static function &convert($node_name, $arr=array()) {
72+
73+
//print_arr($node_name);
74+
$xml = self::getXMLRoot();
75+
$node = $xml->createElement($node_name);
76+
77+
if(is_array($arr)){
78+
// get the attributes first.;
79+
if(isset($arr['@attributes'])) {
80+
foreach($arr['@attributes'] as $key => $value) {
81+
if(!self::isValidTagName($key)) {
82+
throw new Exception('[Array2XML] Illegal character in attribute name. attribute: '.$key.' in node: '.$node_name);
83+
}
84+
$node->setAttribute($key, self::bool2str($value));
85+
}
86+
unset($arr['@attributes']); //remove the key from the array once done.
87+
}
88+
89+
// check if it has a value stored in @value, if yes store the value and return
90+
// else check if its directly stored as string
91+
if(isset($arr['@value'])) {
92+
$node->appendChild($xml->createTextNode(self::bool2str($arr['@value'])));
93+
unset($arr['@value']); //remove the key from the array once done.
94+
//return from recursion, as a note with value cannot have child nodes.
95+
return $node;
96+
} else if(isset($arr['@cdata'])) {
97+
$node->appendChild($xml->createCDATASection(self::bool2str($arr['@cdata'])));
98+
unset($arr['@cdata']); //remove the key from the array once done.
99+
//return from recursion, as a note with cdata cannot have child nodes.
100+
return $node;
101+
}
102+
}
103+
104+
//create subnodes using recursion
105+
if(is_array($arr)){
106+
// recurse to get the node for that key
107+
foreach($arr as $key=>$value){
108+
if(!self::isValidTagName($key)) {
109+
throw new Exception('[Array2XML] Illegal character in tag name. tag: '.$key.' in node: '.$node_name);
110+
}
111+
if(is_array($value) && is_numeric(key($value))) {
112+
// MORE THAN ONE NODE OF ITS KIND;
113+
// if the new array is numeric index, means it is array of nodes of the same kind
114+
// it should follow the parent key name
115+
foreach($value as $k=>$v){
116+
$node->appendChild(self::convert($key, $v));
117+
}
118+
} else {
119+
// ONLY ONE NODE OF ITS KIND
120+
$node->appendChild(self::convert($key, $value));
121+
}
122+
unset($arr[$key]); //remove the key from the array once done.
123+
}
124+
}
125+
126+
// after we are done with all the keys in the array (if it is one)
127+
// we check if it has any text value, if yes, append it.
128+
if(!is_array($arr)) {
129+
$node->appendChild($xml->createTextNode(self::bool2str($arr)));
130+
}
131+
132+
return $node;
133+
}
134+
135+
/*
136+
* Get the root XML node, if there isn't one, create it.
137+
*/
138+
private static function getXMLRoot(){
139+
if(empty(self::$xml)) {
140+
self::init();
141+
}
142+
return self::$xml;
143+
}
144+
145+
/*
146+
* Get string representation of boolean value
147+
*/
148+
private static function bool2str($v){
149+
//convert boolean to text value.
150+
$v = $v === true ? 'true' : $v;
151+
$v = $v === false ? 'false' : $v;
152+
return $v;
153+
}
154+
155+
/*
156+
* Check if the tag name or attribute name contains illegal characters
157+
* Ref: http://www.w3.org/TR/xml/#sec-common-syn
158+
*/
159+
private static function isValidTagName($tag){
160+
$pattern = '/^[a-z_]+[a-z0-9\:\-\.\_]*[^:]*$/i';
161+
return preg_match($pattern, $tag, $matches) && $matches[0] == $tag;
162+
}
163+
}
164+
165+
/**
166+
* XML2Array: A class to convert XML to array in PHP
167+
* It returns the array which can be converted back to XML using the Array2XML script
168+
* It takes an XML string or a DOMDocument object as an input.
169+
*
170+
* See Array2XML: http://www.lalit.org/lab/convert-php-array-to-xml-with-attributes
171+
*
172+
* Author : Lalit Patel
173+
* Website: http://www.lalit.org/lab/convert-xml-to-array-in-php-xml2array
174+
* License: Apache License 2.0
175+
* http://www.apache.org/licenses/LICENSE-2.0
176+
* Version: 0.1 (07 Dec 2011)
177+
* Version: 0.2 (04 Mar 2012)
178+
* Fixed typo 'DomDocument' to 'DOMDocument'
179+
*
180+
* Usage:
181+
* $array = XML2Array::createArray($xml);
182+
*/
183+
184+
class XML2Array {
185+
186+
private static $xml = null;
187+
private static $encoding = 'UTF-8';
188+
189+
/**
190+
* Initialize the root XML node [optional]
191+
* @param $version
192+
* @param $encoding
193+
* @param $format_output
194+
*/
195+
public static function init($version = '1.0', $encoding = 'UTF-8', $format_output = true) {
196+
self::$xml = new DOMDocument($version, $encoding);
197+
self::$xml->formatOutput = $format_output;
198+
self::$encoding = $encoding;
199+
}
200+
201+
/**
202+
* Convert an XML to Array
203+
* @param string $node_name - name of the root node to be converted
204+
* @param array $arr - aray to be converterd
205+
* @return DOMDocument
206+
*/
207+
public static function &createArray($input_xml) {
208+
$xml = self::getXMLRoot();
209+
if(is_string($input_xml)) {
210+
$parsed = $xml->loadXML($input_xml);
211+
if(!$parsed) {
212+
throw new Exception('[XML2Array] Error parsing the XML string.');
213+
}
214+
} else {
215+
if(get_class($input_xml) != 'DOMDocument') {
216+
throw new Exception('[XML2Array] The input XML object should be of type: DOMDocument.');
217+
}
218+
$xml = self::$xml = $input_xml;
219+
}
220+
$array[$xml->documentElement->tagName] = self::convert($xml->documentElement);
221+
self::$xml = null; // clear the xml node in the class for 2nd time use.
222+
return $array;
223+
}
224+
225+
/**
226+
* Convert an Array to XML
227+
* @param mixed $node - XML as a string or as an object of DOMDocument
228+
* @return mixed
229+
*/
230+
private static function &convert($node) {
231+
$output = array();
232+
233+
switch ($node->nodeType) {
234+
case XML_CDATA_SECTION_NODE:
235+
$output['@cdata'] = trim($node->textContent);
236+
break;
237+
238+
case XML_TEXT_NODE:
239+
$output = trim($node->textContent);
240+
break;
241+
242+
case XML_ELEMENT_NODE:
243+
244+
// for each child node, call the covert function recursively
245+
for ($i=0, $m=$node->childNodes->length; $i<$m; $i++) {
246+
$child = $node->childNodes->item($i);
247+
$v = self::convert($child);
248+
if(isset($child->tagName)) {
249+
$t = $child->tagName;
250+
251+
// assume more nodes of same kind are coming
252+
if(!isset($output[$t])) {
253+
$output[$t] = array();
254+
}
255+
$output[$t][] = $v;
256+
} else {
257+
//check if it is not an empty text node
258+
if($v !== '') {
259+
$output = $v;
260+
}
261+
}
262+
}
263+
264+
if(is_array($output)) {
265+
// if only one node of its kind, assign it directly instead if array($value);
266+
foreach ($output as $t => $v) {
267+
if(is_array($v) && count($v)==1) {
268+
$output[$t] = $v[0];
269+
}
270+
}
271+
if(empty($output)) {
272+
//for empty nodes
273+
$output = '';
274+
}
275+
}
276+
277+
// loop through the attributes and collect them
278+
if($node->attributes->length) {
279+
$a = array();
280+
foreach($node->attributes as $attrName => $attrNode) {
281+
$a[$attrName] = (string) $attrNode->value;
282+
}
283+
// if its an leaf node, store the value in @value instead of directly storing it.
284+
if(!is_array($output)) {
285+
$output = array('@value' => $output);
286+
}
287+
$output['@attributes'] = $a;
288+
}
289+
break;
290+
}
291+
return $output;
292+
}
293+
294+
/*
295+
* Get the root XML node, if there isn't one, create it.
296+
*/
297+
private static function getXMLRoot(){
298+
if(empty(self::$xml)) {
299+
self::init();
300+
}
301+
return self::$xml;
302+
}
303+
}

0 commit comments

Comments
 (0)