PHP对象作为XML文档
获取给定PHP对象并将其序列化为XML的最佳方法是什么?我正在研究simple_xml,并使用它将xml解析为对象,但我不清楚它是如何反过来工作的。使用dom函数来完成这项工作: 导入SimpleXML对象,然后保存。上面的链接包含一个示例:) 简言之:PHP对象作为XML文档,php,xml,xml-serialization,Php,Xml,Xml Serialization,获取给定PHP对象并将其序列化为XML的最佳方法是什么?我正在研究simple_xml,并使用它将xml解析为对象,但我不清楚它是如何反过来工作的。使用dom函数来完成这项工作: 导入SimpleXML对象,然后保存。上面的链接包含一个示例:) 简言之: <?php $array = array('hello' => 'world', 'good' => 'morning'); $xml = simplexml_load_string("<?xml version='
<?php
$array = array('hello' => 'world', 'good' => 'morning');
$xml = simplexml_load_string("<?xml version='1.0' encoding='utf-8'?><foo />");
foreach ($array as $k=>$v) {
$xml->addChild($k, $v);
}
?>
$v){
$xml->addChild($k,$v);
}
?>
好吧,虽然有点脏,但您始终可以在对象的属性上运行循环
$_xml = '';
foreach($obj as $key => $val){
$_xml .= '<' . $key . '>' . $val . '</' . $key . ">\n";
}
$\u xml='';
foreach($obj as$key=>$val){
$\u xml.=''.$val.看一看PEAR的包。我用过它,效果很好。你可以给它提供数组、对象等,它会将它们转换成xml。它还有一系列选项,比如选择根节点的名称等
应使用WDDX执行此操作:
(如果安装了此扩展)
它致力于:
这不是对原始问题的完全回答,但我解决问题的方法是将我的对象声明为:
$root = '<?xml version="1.0" encoding="UTF-8"?><Activities/>';
$object = new simpleXMLElement($root);
在我开始添加任何值之前!我同意使用PEAR的XML_序列化程序,但是如果您想要一些简单的支持嵌套属性的对象/数组的东西,可以使用它
class XMLSerializer {
// functions adopted from http://www.sean-barton.co.uk/2009/03/turning-an-array-or-object-into-xml-using-php/
public static function generateValidXmlFromObj(stdClass $obj, $node_block='nodes', $node_name='node') {
$arr = get_object_vars($obj);
return self::generateValidXmlFromArray($arr, $node_block, $node_name);
}
public static function generateValidXmlFromArray($array, $node_block='nodes', $node_name='node') {
$xml = '<?xml version="1.0" encoding="UTF-8" ?>';
$xml .= '<' . $node_block . '>';
$xml .= self::generateXmlFromArray($array, $node_name);
$xml .= '</' . $node_block . '>';
return $xml;
}
private static function generateXmlFromArray($array, $node_name) {
$xml = '';
if (is_array($array) || is_object($array)) {
foreach ($array as $key=>$value) {
if (is_numeric($key)) {
$key = $node_name;
}
$xml .= '<' . $key . '>' . self::generateXmlFromArray($value, $node_name) . '</' . $key . '>';
}
} else {
$xml = htmlspecialchars($array, ENT_QUOTES);
}
return $xml;
}
}
类XMLSerializer{
//通过的职能http://www.sean-barton.co.uk/2009/03/turning-an-array-or-object-into-xml-using-php/
公共静态函数generateValidXmlFromObj(stdClass$obj、$node_block='nodes',$node_name='node'){
$arr=获取对象变量($obj);
返回self::generateValidXmlFromArray($arr、$node_block、$node_name);
}
公共静态函数generateValidXmlFromArray($array、$node\u block='nodes',$node\u name='node')){
$xml='';
$xml.='';
$xml.=self::generateXmlFromArray($array,$node_name);
$xml.='';
返回$xml;
}
私有静态函数generateXmlFromArray($array,$node_name){
$xml='';
if(is_数组($array)| is_对象($array)){
foreach($key=>$value的数组){
如果(是数字($key)){
$key=$node\u name;
}
$xml.=''.self::generateXmlFromArray($value,$node_name)。'';
}
}否则{
$xml=htmlspecialchars($array,entu引号);
}
返回$xml;
}
}
虽然我同意@philfreo和他的推理,即您不应该依赖PEAR,但他的解决方案仍然不太完善。当密钥可能是包含以下任意字符的字符串时,存在潜在问题:
- \s(空间)
- "
- "
function xml_encode( $var, $indent = false, $i = 0 ) {
$version = "1.0";
if ( !$i ) {
$data = '<?xml version="1.0"?>' . ( $indent ? "\r\n" : '' )
. '<root vartype="' . gettype( $var ) . '" xml_encode_version="'. $version . '">' . ( $indent ? "\r\n" : '' );
}
else {
$data = '';
}
foreach ( $var as $k => $v ) {
$data .= ( $indent ? str_repeat( "\t", $i ) : '' ) . '<var vartype="' .gettype( $v ) . '" varname="' . htmlentities( $k ) . '"';
if($v == "") {
$data .= ' />';
}
else {
$data .= '>';
if ( is_array( $v ) ) {
$data .= ( $indent ? "\r\n" : '' ) . xml_encode( $v, $indent, $verbose, ($i + 1) ) . ( $indent ? str_repeat("\t", $i) : '' );
}
else if( is_object( $v ) ) {
$data .= ( $indent ? "\r\n" : '' ) . xml_encode( json_decode( json_encode( $v ), true ), $indent, $verbose, ($i + 1)) . ($indent ? str_repeat("\t", $i) : '');
}
else {
$data .= htmlentities( $v );
}
$data .= '</var>';
}
$data .= ($indent ? "\r\n" : '');
}
if ( !$i ) {
$data .= '</root>';
}
return $data;
}
函数xml_encode($var,$indent=false,$i=0){
$version=“1.0”;
如果(!$i){
$data=''($indent?\r\n:'')
“.”($indent?\r\n:”);
}
否则{
$data='';
}
foreach($var为$k=>$v){
$data.=($indent?str_repeat(“\t”,$i):”);
}
否则{
$data.='>';
if(is_数组($v)){
$data.=($indent?”\r\n:“).xml\u encode($v,$indent,$verbose,($i+1))。($indent?str\u repeat($t“,$i):”);
}
else if(is_object($v)){
$data.=($indent?\r\n:“).xml_编码(json_解码(json_编码($v),true),$indent,$verbose,($i+1))。($indent?str_repeat(“\t”,$i):”);
}
否则{
$data.=htmlentities($v);
}
$data.='';
}
$data.=($indent?\r\n):“”);
}
如果(!$i){
$data.='';
}
返回$data;
}
下面是一个示例用法:
// sample object
$tests = Array(
"stringitem" => "stringvalue",
"integeritem" => 1,
"floatitem" => 1.00,
"arrayitems" => Array("arrayvalue1", "arrayvalue2"),
"hashitems" => Array( "hashkey1" => "hashkey1value", "hashkey2" => "hashkey2value" ),
"literalnull" => null,
"literalbool" => json_decode( json_encode( 1 ) )
);
// add an objectified version of itself as a child
$tests['objectitem'] = json_decode( json_encode( $tests ), false);
// convert and output
echo xml_encode( $tests );
/*
// output:
<?xml version="1.0"?>
<root vartype="array" xml_encode_version="1.0">
<var vartype="integer" varname="integeritem">1</var>
<var vartype="string" varname="stringitem">stringvalue</var>
<var vartype="double" varname="floatitem">1</var>
<var vartype="array" varname="arrayitems">
<var vartype="string" varname="0">arrayvalue1</var>
<var vartype="string" varname="1">arrayvalue2</var>
</var>
<var vartype="array" varname="hashitems">
<var vartype="string" varname="hashkey1">hashkey1value</var>
<var vartype="string" varname="hashkey2">hashkey2value</var>
</var>
<var vartype="NULL" varname="literalnull" />
<var vartype="integer" varname="literalbool">1</var>
<var vartype="object" varname="objectitem">
<var vartype="string" varname="stringitem">stringvalue</var>
<var vartype="integer" varname="integeritem">1</var>
<var vartype="integer" varname="floatitem">1</var>
<var vartype="array" varname="arrayitems">
<var vartype="string" varname="0">arrayvalue1</var>
<var vartype="string" varname="1">arrayvalue2</var>
</var>
<var vartype="array" varname="hashitems">
<var vartype="string" varname="hashkey1">hashkey1value</var>
<var vartype="string" varname="hashkey2">hashkey2value</var>
</var>
<var vartype="NULL" varname="literalnull" />
<var vartype="integer" varname="literalbool">1</var>
</var>
</root>
*/
//示例对象
$tests=数组(
“stringitem”=>“stringvalue”,
“整数项”=>1,
“浮动项目”=>1.00,
“arrayitems”=>数组(“arrayvalue1”、“arrayvalue2”),
“hashitems”=>数组(“hashkey1”=>“hashkey1value”、“hashkey2”=>“hashkey2value”),
“literalnull”=>null,
“literalbool”=>json_解码(json_编码(1))
);
//将自身的对象化版本添加为子对象
$tests['objectitem']=json_解码(json_编码($tests),false);
//转换输出
echo xml_编码($tests);
/*
//输出:
1.
stringvalue
1.
数组值1
数组值2
hashkey1value
hashkey2value
1.
stringvalue
1.
1.
数组值1
数组值2
hashkey1value
hashkey2value
1.
*/
请注意,键名存储在varname属性(html编码)中,甚至类型也存储在其中,因此可以进行对称反序列化。这只存在一个问题:它不会序列化类,只序列化实例化的对象,而实例化的对象不包括类方法。这只用于传递“数据”“来来回回
我希望这对某些人有所帮助,尽管这在很久以前就得到了回答。看看我的版本
class XMLSerializer {
/**
*
* The most advanced method of serialization.
*
* @param mixed $obj => can be an objectm, an array or string. may contain unlimited number of subobjects and subarrays
* @param string $wrapper => main wrapper for the xml
* @param array (key=>value) $replacements => an array with variable and object name replacements
* @param boolean $add_header => whether to add header to the xml string
* @param array (key=>value) $header_params => array with additional xml tag params
* @param string $node_name => tag name in case of numeric array key
*/
public static function generateValidXmlFromMixiedObj($obj, $wrapper = null, $replacements=array(), $add_header = true, $header_params=array(), $node_name = 'node')
{
$xml = '';
if($add_header)
$xml .= self::generateHeader($header_params);
if($wrapper!=null) $xml .= '<' . $wrapper . '>';
if(is_object($obj))
{
$node_block = strtolower(get_class($obj));
if(isset($replacements[$node_block])) $node_block = $replacements[$node_block];
$xml .= '<' . $node_block . '>';
$vars = get_object_vars($obj);
if(!empty($vars))
{
foreach($vars as $var_id => $var)
{
if(isset($replacements[$var_id])) $var_id = $replacements[$var_id];
$xml .= '<' . $var_id . '>';
$xml .= self::generateValidXmlFromMixiedObj($var, null, $replacements, false, null, $node_name);
$xml .= '</' . $var_id . '>';
}
}
$xml .= '</' . $node_block . '>';
}
else if(is_array($obj))
{
foreach($obj as $var_id => $var)
{
if(!is_object($var))
{
if (is_numeric($var_id))
$var_id = $node_name;
if(isset($replacements[$var_id])) $var_id = $replacements[$var_id];
$xml .= '<' . $var_id . '>';
}
$xml .= self::generateValidXmlFromMixiedObj($var, null, $replacements, false, null, $node_name);
if(!is_object($var))
$xml .= '</' . $var_id . '>';
}
}
else
{
$xml .= htmlspecialchars($obj, ENT_QUOTES);
}
if($wrapper!=null) $xml .= '</' . $wrapper . '>';
return $xml;
}
/**
*
* xml header generator
* @param array $params
*/
public static function generateHeader($params = array())
{
$basic_params = array('version' => '1.0', 'encoding' => 'UTF-8');
if(!empty($params))
$basic_params = array_merge($basic_params,$params);
$header = '<?xml';
foreach($basic_params as $k=>$v)
{
$header .= ' '.$k.'='.$v;
}
$header .= ' ?>';
return $header;
}
}
类XMLSerializer{
/**
*
*最先进的序列化方法。
*
*@param mixed$obj=>可以是objectm、数组或字符串。可以包含无限数量的子对象和子数组
*@param string$wrapper=>xml的主包装器
*@param数组(key=>value)$replacements=>替换变量和对象名的数组
*@param boolean$add_header=>是否将头添加到xml字符串
*@param数组(key=>value)$header\u params=>array和其他xml标记参数
*@param string$node_name=>数字数组键情况下的标记名
*/
公共静态函数generateValidXmlFromMixiedObj($obj,$wrapper=null,$replacements=array(),$add\u header=true,$header\u params=array(),$node\n
class XMLSerializer {
/**
*
* The most advanced method of serialization.
*
* @param mixed $obj => can be an objectm, an array or string. may contain unlimited number of subobjects and subarrays
* @param string $wrapper => main wrapper for the xml
* @param array (key=>value) $replacements => an array with variable and object name replacements
* @param boolean $add_header => whether to add header to the xml string
* @param array (key=>value) $header_params => array with additional xml tag params
* @param string $node_name => tag name in case of numeric array key
*/
public static function generateValidXmlFromMixiedObj($obj, $wrapper = null, $replacements=array(), $add_header = true, $header_params=array(), $node_name = 'node')
{
$xml = '';
if($add_header)
$xml .= self::generateHeader($header_params);
if($wrapper!=null) $xml .= '<' . $wrapper . '>';
if(is_object($obj))
{
$node_block = strtolower(get_class($obj));
if(isset($replacements[$node_block])) $node_block = $replacements[$node_block];
$xml .= '<' . $node_block . '>';
$vars = get_object_vars($obj);
if(!empty($vars))
{
foreach($vars as $var_id => $var)
{
if(isset($replacements[$var_id])) $var_id = $replacements[$var_id];
$xml .= '<' . $var_id . '>';
$xml .= self::generateValidXmlFromMixiedObj($var, null, $replacements, false, null, $node_name);
$xml .= '</' . $var_id . '>';
}
}
$xml .= '</' . $node_block . '>';
}
else if(is_array($obj))
{
foreach($obj as $var_id => $var)
{
if(!is_object($var))
{
if (is_numeric($var_id))
$var_id = $node_name;
if(isset($replacements[$var_id])) $var_id = $replacements[$var_id];
$xml .= '<' . $var_id . '>';
}
$xml .= self::generateValidXmlFromMixiedObj($var, null, $replacements, false, null, $node_name);
if(!is_object($var))
$xml .= '</' . $var_id . '>';
}
}
else
{
$xml .= htmlspecialchars($obj, ENT_QUOTES);
}
if($wrapper!=null) $xml .= '</' . $wrapper . '>';
return $xml;
}
/**
*
* xml header generator
* @param array $params
*/
public static function generateHeader($params = array())
{
$basic_params = array('version' => '1.0', 'encoding' => 'UTF-8');
if(!empty($params))
$basic_params = array_merge($basic_params,$params);
$header = '<?xml';
foreach($basic_params as $k=>$v)
{
$header .= ' '.$k.'='.$v;
}
$header .= ' ?>';
return $header;
}
}
interface SerializeXml {
public function hasAttributes();
public function getAttributes();
public function setAttributes($attribs = array());
public function getNameOwerriden();
public function isNameOwerriden();
}
abstract class SerializeXmlAbstract implements SerializeXml {
protected $attributes;
protected $nameOwerriden;
function __construct($name = NULL) {
$this->nameOwerriden = $name;
}
public function getAttributes() {
return $this->attributes;
}
public function getNameOwerriden() {
return $this->nameOwerriden;
}
public function setAttributes($attribs = array()) {
$this->attributes = $attribs;
}
public function hasAttributes() {
return (is_array($this->attributes) && count($this->attributes) > 0) ? TRUE : FALSE;
}
public function isNameOwerriden() {
return $this->nameOwerriden != NULL ? TRUE : FALSE;
}
}
abstract class Entity_list extends SplObjectStorage {
protected $_listItemType;
public function __construct($type) {
$this->setListItemType($type);
}
private function setListItemType($param) {
$this->_listItemType = $param;
}
public function detach($object) {
if ($object instanceOf $this->_listItemType) {
parent::detach($object);
}
}
public function attach($object, $data = null) {
if ($object instanceOf $this->_listItemType) {
parent::attach($object, $data);
}
}
}
abstract class Array_list extends SerializeXmlAbstract {
protected $_listItemType;
protected $_items;
public function __construct() {
//$this->setListItemType($type);
$this->_items = new SplObjectStorage();
}
protected function setListItemType($param) {
$this->_listItemType = $param;
}
public function getArray() {
$return = array();
$this->_items->rewind();
while ($this->_items->valid()) {
$return[] = $this->_items->current();
$this->_items->next();
}
// print_r($return);
return $return;
}
public function detach($object) {
if ($object instanceOf $this->_listItemType) {
if (in_array($this->_items->contains($object))) {
$this->_items->detach($object);
}
}
}
public function attachItem($ob) {
$this->_items->attach($ob);
}
}
class Object2xml {
public $rootPrefix = "ernm";
private $addPrefix;
public $xml;
public function serialize($object, $name = NULL, $prefix = FALSE) {
if ($object instanceof SerializeXml) {
$this->xml = new DOMDocument('1.0', 'utf-8');
$this->xml->appendChild($this->object2xml($object, $name, TRUE));
$this->xml->formatOutput = true;
echo $this->xml->saveXML();
} else {
die("Not implement SerializeXml interface");
}
}
protected function object2xml(SerializeXmlAbstract $object, $nodeName = NULL, $prefix = null) {
$single = property_exists(get_class($object), "value");
$nName = $nodeName != NULL ? $nodeName : get_class($object);
if ($prefix) {
$nName = $this->rootPrefix . ":" . $nName;
}
if ($single) {
$ref = $this->xml->createElement($nName);
} elseif (is_object($object)) {
if ($object->isNameOwerriden()) {
$nodeName = $object->getNameOwerriden();
}
$ref = $this->xml->createElement($nName);
if ($object->hasAttributes()) {
foreach ($object->getAttributes() as $key => $value) {
$ref->setAttribute($key, $value);
}
}
foreach (get_object_vars($object) as $n => $prop) {
switch (gettype($prop)) {
case "object":
if ($prop instanceof SplObjectStorage) {
$ref->appendChild($this->handleList($n, $prop));
} elseif ($prop instanceof Array_list) {
$node = $this->object2xml($prop);
foreach ($object->ResourceGroup->getArray() as $key => $value) {
$node->appendChild($this->object2xml($value));
}
$ref->appendChild($node);
} else {
$ref->appendChild($this->object2xml($prop));
}
break;
default :
if ($prop != null) {
$ref->appendChild($this->xml->createElement($n, $prop));
}
break;
}
}
} elseif (is_array($object)) {
foreach ($object as $value) {
$ref->appendChild($this->object2xml($value));
}
}
return $ref;
}
private function handleList($name, SplObjectStorage $param, $nodeName = NULL) {
$lst = $this->xml->createElement($nodeName == NULL ? $name : $nodeName);
$param->rewind();
while ($param->valid()) {
if ($param->current() != null) {
$lst->appendChild($this->object2xml($param->current()));
}
$param->next();
}
return $lst;
}
}
<InsertMessage priority="high">
<NodeSimpleValue firstAttrib="first" secondAttrib="second">simple value</NodeSimpleValue>
<Arrarita>
<Title>PHP OOP is great</Title>
<SequenceNumber>1</SequenceNumber>
<Child>
<FirstChild>Jimmy</FirstChild>
</Child>
<Child2>
<FirstChild>bird</FirstChild>
</Child2>
</Arrarita>
<ThirdChild>
<NodeWithChilds>
<FirstChild>John</FirstChild>
<ThirdChild>James</ThirdChild>
</NodeWithChilds>
<NodeWithChilds>
<FirstChild>DomDocument</FirstChild>
<SecondChild>SplObjectStorage</SecondChild>
</NodeWithChilds>
</ThirdChild>
</InsertMessage>
class NodeWithArrayList extends Array_list {
public $Title;
public $SequenceNumber;
public function __construct($name = NULL) {
echo $name;
parent::__construct($name);
}
}
class EntityListNode extends Entity_list {
public function __construct($name = NULL) {
parent::__construct($name);
}
}
class NodeWithChilds extends SerializeXmlAbstract {
public $FirstChild;
public $SecondChild;
public $ThirdChild;
public function __construct($name = NULL) {
parent::__construct($name);
}
}
class NodeSimpleValue extends SerializeXmlAbstract {
protected $value;
public function getValue() {
return $this->value;
}
public function setValue($value) {
$this->value = $value;
}
public function __construct($name = NULL) {
parent::__construct($name);
}
}
$firstChild = new NodeSimpleValue("firstChild");
$firstChild->setValue( "simple value" );
$firstChild->setAttributes(array("firstAttrib" => "first", "secondAttrib" => "second"));
$secondChild = new NodeWithArrayList("Arrarita");
$secondChild->Title = "PHP OOP is great";
$secondChild->SequenceNumber = 1;
$firstListItem = new NodeWithChilds();
$firstListItem->FirstChild = "John";
$firstListItem->ThirdChild = "James";
$firstArrayItem = new NodeWithChilds("Child");
$firstArrayItem->FirstChild = "Jimmy";
$SecondArrayItem = new NodeWithChilds("Child2");
$SecondArrayItem->FirstChild = "bird";
$secondListItem = new NodeWithChilds();
$secondListItem->FirstChild = "DomDocument";
$secondListItem->SecondChild = "SplObjectStorage";
$secondChild->attachItem($firstArrayItem);
$secondChild->attachItem($SecondArrayItem);
$list = new EntityListNode("NodeWithChilds");
$list->attach($firstListItem);
$list->attach($secondListItem);
$message = New NodeWithChilds("InsertMessage");
$message->setAttributes(array("priority" => "high"));
$message->FirstChild = $firstChild;
$message->SecondChild = $secondChild;
$message->ThirdChild = $list;
$object2xml = new Object2xml();
$object2xml->serialize($message, "xml", TRUE);
class XMLSerializer {
/**
* Get object class name without namespace
* @param object $object Object to get class name from
* @return string Class name without namespace
*/
private static function GetClassNameWithoutNamespace($object) {
$class_name = get_class($object);
return end(explode('\\', $class_name));
}
/**
* Converts object to XML compatible with .NET XmlSerializer.Deserialize
* @param type $object Object to serialize
* @param type $root_node Root node name (if null, objects class name is used)
* @return string XML string
*/
public static function Serialize($object, $root_node = null) {
$xml = '<?xml version="1.0" encoding="UTF-8" ?>';
if (!$root_node) {
$root_node = self::GetClassNameWithoutNamespace($object);
}
$xml .= '<' . $root_node . ' xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema">';
$xml .= self::SerializeNode($object);
$xml .= '</' . $root_node . '>';
return $xml;
}
/**
* Create XML node from object property
* @param mixed $node Object property
* @param string $parent_node_name Parent node name
* @param bool $is_array_item Is this node an item of an array?
* @return string XML node as string
* @throws Exception
*/
private static function SerializeNode($node, $parent_node_name = false, $is_array_item = false) {
$xml = '';
if (is_object($node)) {
$vars = get_object_vars($node);
} else if (is_array($node)) {
$vars = $node;
} else {
throw new Exception('Coś poszło nie tak');
}
foreach ($vars as $k => $v) {
if (is_object($v)) {
$node_name = ($parent_node_name ? $parent_node_name : self::GetClassNameWithoutNamespace($v));
if (!$is_array_item) {
$node_name = $k;
}
$xml .= '<' . $node_name . '>';
$xml .= self::SerializeNode($v);
$xml .= '</' . $node_name . '>';
} else if (is_array($v)) {
$xml .= '<' . $k . '>';
if (count($v) > 0) {
if (is_object(reset($v))) {
$xml .= self::SerializeNode($v, self::GetClassNameWithoutNamespace(reset($v)), true);
} else {
$xml .= self::SerializeNode($v, gettype(reset($v)), true);
}
} else {
$xml .= self::SerializeNode($v, false, true);
}
$xml .= '</' . $k . '>';
} else {
$node_name = ($parent_node_name ? $parent_node_name : $k);
if ($v === null) {
continue;
} else {
$xml .= '<' . $node_name . '>';
if (is_bool($v)) {
$xml .= $v ? 'true' : 'false';
} else {
$xml .= htmlspecialchars($v, ENT_QUOTES);
}
$xml .= '</' . $node_name . '>';
}
}
}
return $xml;
}
}
class GetProductsCommandResult {
public $description;
public $Errors;
}
class Error {
public $id;
public $error;
}
$obj = new GetProductsCommandResult();
$obj->description = "Teścik";
$obj->Errors = array();
$obj->Errors[0] = new Error();
$obj->Errors[0]->id = 666;
$obj->Errors[0]->error = "Sth";
$obj->Errors[1] = new Error();
$obj->Errors[1]->id = 666;
$obj->Errors[1]->error = null;
$xml = XMLSerializer::Serialize($obj);
<?xml version="1.0" encoding="UTF-8"?>
<GetProductsCommandResult xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
<description>Teścik</description>
<Errors>
<Error>
<id>666</id>
<error>Sth</error>
</Error>
<Error>
<id>666</id>
</Error>
</Errors>
</GetProductsCommandResult>
private function ReadProperty($xmlElement, $object) {
foreach ($object as $key => $value) {
if ($value != null) {
if (is_object($value)) {
$element = $this->xml->createElement($key);
$this->ReadProperty($element, $value);
$xmlElement->AppendChild($element);
} elseif (is_array($value)) {
$this->ReadProperty($xmlElement, $value);
} else {
$this->AddAttribute($xmlElement, $key, $value);
}
}
}
}
class XMLSerializer {
private $OpenTag = "<";
private $CloseTag = ">";
private $BackSlash = "/";
public $Root = "root";
public function __construct() {
}
private function Array_To_XML($array, $arrayElementName = "element_", $xmlString = "")
{
if($xmlString === "")
{
$xmlString = "{$this->OpenTag}{$this->Root}{$this->CloseTag}";
}
$startTag = "{$this->OpenTag}{$arrayElementName}{$this->CloseTag}";
$xmlString .= $startTag;
foreach($array as $key => $value){
if(gettype($value) === "string" || gettype($value) === "boolean" || gettype($value) === "integer" || gettype($value) === "double" || gettype($value) === "float")
{
$elementStartTag = "{$this->OpenTag}{$arrayElementName}_{$key}{$this->CloseTag}";
$elementEndTag = "{$this->OpenTag}{$this->BackSlash}{$arrayElementName}_{$key}{$this->CloseTag}";
$xmlString .= "{$elementStartTag}{$value}{$elementEndTag}";
continue;
}
else if(gettype($value) === "array")
{
$xmlString = $this->Array_To_XML($value, $arrayElementName, $xmlString);
continue;
}
else if(gettype($value) === "object")
{
$xmlString = $this->Object_To_XML($value, $xmlString);
continue;
}
else
{
continue;
}
}
$endTag = "{$this->OpenTag}{$this->BackSlash}{$arrayElementName}{$this->CloseTag}";
$xmlString .= $endTag;
return $xmlString;
}
private function Object_To_XML($objElement, $xmlString = "")
{
if($xmlString === "")
{
$xmlString = "{$this->OpenTag}{$this->Root}{$this->CloseTag}";
}
foreach($objElement as $key => $value){
if(gettype($value) !== "array" && gettype($value) !== "object")
{
$startTag = "{$this->OpenTag}{$key}{$this->CloseTag}";
$endTag = "{$this->OpenTag}{$this->BackSlash}{$key}{$this->CloseTag}";
$xmlString .= "{$startTag}{$value}{$endTag}";
continue;
}
else if(gettype($value) === "array")
{
$xmlString = $this->Array_To_XML($value, $key, $xmlString);
continue;
}
else if(gettype($value) === "object")
{
$xmlString = $this->Object_To_XML($value, $xmlString);
continue;
}
else
{
continue;
}
}
return $xmlString;
}
public function Serialize_Object($element, $xmlString = "")
{
$endTag = "{$this->OpenTag}{$this->BackSlash}{$this->Root}{$this->CloseTag}";
return "{$this->Object_To_XML($element, $xmlString)}{$endTag}";
}
public function Serialize_Array($element, $xmlString = "")
{
$endTag = "{$this->OpenTag}{$this->BackSlash}{$this->Root}{$this->CloseTag}";
return "{$this->Array_To_XML($element, $xmlString)}{$endTag}";
}
}