i am generating an XML file FROM Json FIle
$array = file_get_contents('Invoice.json');
$json = json_decode($array, true);
$token = $json['invoice'];
function array_to_xml( $data, &$xml_data ) {
foreach( $data as $key => $value ) {
if( is_array($value) ) {
if( is_numeric($key) ){
$key = 'item'.$key; //dealing with <0/>..<n/> issues
$key2 = 'contact_persons'.$key;
}
$subnode = $xml_data->addChild($key);
array_to_xml($value, $subnode);
} else {
$xml_data->addChild("$key",htmlspecialchars("$value"));
}
}
}
$xml_data = new SimpleXMLElement('<?xml version="1.0" encoding="UTF-8"?><data></data>');
// function call to convert array to xml
array_to_xml($token,$xml_data);
//saving generated xml file;
$result = $xml_data->asXML('Invoice.xml');
inside the XML I have this Error
<contact_persons><0>122396000000033035</0></contact_persons>
and All of my XML data is in one line
how can I Fix This Error and Create the XML to Show in multi-lines?
thank U!
---EDIT--
this is the Json :
{"invoice":{"can_send_in_mail":false,"zcrm_potential_id":"","is_client_review_settings_enabled":false,"discount":0,"taxes":[],"billing_address":{"zip":"","country":"","address":"","city":"","phone":"","attention":"","street2":"","state":"","fax":""},"line_items":[{"bcy_rate":50,"item_total_formatted":"\u20ac50,00","salesorder_item_id":"","line_item_id":"122396000000033067","rate_formatted":"\u20ac50,00","header_id":"","documents":[],"item_type":"","item_type_formatted":"","purchase_rate":"","description":"asdfasdfasdf","discount":0,"item_order":0,"project_id":"","rate":50,"markup_amount":0,"pricebook_id":"","bcy_rate_formatted":"\u20ac50,00","quantity":1,"image_document_id":"","item_id":"","expense_receipt_name":"","tax_name":"INPS","item_total":50,"header_name":"","item_custom_fields":[],"tax_id":"122396000000032221","purchase_rate_formatted":"","unit":"","tax_type":"tax","time_entry_ids":[],"name":"","tax_percentage":4,"markup_amount_formatted":"\u20ac0,00","expense_id":""},{"bcy_rate":200,"item_total_formatted":"\u20ac200,00","salesorder_item_id":"","line_item_id":"122396000000033441","rate_formatted":"\u20ac200,00","header_id":"","documents":[],"item_type":"","item_type_formatted":"","purchase_rate":"","description":"3334 asdf","discount":0,"item_order":1,"project_id":"","rate":200,"markup_amount":0,"pricebook_id":"","bcy_rate_formatted":"\u20ac200,00","quantity":1,"image_document_id":"","item_id":"","expense_receipt_name":"","tax_name":"INPS","item_total":200,"header_name":"","item_custom_fields":[],"tax_id":"122396000000032221","purchase_rate_formatted":"","unit":"","tax_type":"tax","time_entry_ids":[],"name":"","tax_percentage":4,"markup_amount_formatted":"\u20ac0,00","expense_id":""}],"payment_expected_date_formatted":"","balance":267,"terms":"asdf fgsdfg sdfg ","credits_applied":0,"credits_applied_formatted":"\u20ac0,00","invoice_number":"INV-000001","payment_options":{"payment_gateways":[]},"stop_reminder_until_payment_expected_date":false,"customer_default_billing_address":{"zip":"","country":"","address":"","city":"","phone":"","street2":"","state":"","fax":"","state_code":""},"sub_total_inclusive_of_tax":0,"inprocess_transaction_present":false,"exchange_rate":1,"approver_id":"","estimate_id":"","submitted_date_formatted":"","sales_channel":"direct_sales","merchant_name":"","shipping_charge_formatted":"\u20ac3,00","status_formatted":"Draft","reference_number":"ככגעכ","shipping_charge_tax_id":"","ecomm_operator_name":"","is_autobill_enabled":false,"discount_percent":0,"shipping_charge_tax_name":"","page_height":"11.69in","status":"draft","reader_offline_payment_initiated":false,"schedule_time_formatted":"","discount_total":0,"tax_total":0,"is_viewed_by_client":false,"adjustment_formatted":"\u20ac4,00","balance_formatted":"\u20ac267,00","write_off_amount":0,"salesorder_id":"","currency_code":"EUR","page_width":"8.27in","sub_statuses":[],"bcy_total":267,"last_reminder_sent_date_formatted":"","date_formatted":"14/06/2020","client_viewed_time_formatted":"","salesorders":[],"adjustment_description":"Adjustment","last_modified_time":"2020-06-14T21:15:18+0200","currency_symbol":"\u20ac","ach_supported":false,"shipping_bills":[],"discount_type":"entity_level","transaction_rounding_type":"no_rounding","contact_persons_details":[],"roundoff_value":0,"template_name":"","schedule_time":"","deliverychallans":[],"salesorder_number":"","template_id":"122396000000000103","customer_name":"Thest Compan","customer_id":"122396000000033033","roundoff_value_formatted":"\u20ac0,00","unused_retainer_payments_formatted":"\u20ac0,00","total_formatted":"\u20ac267,00","discount_total_formatted":"\u20ac0,00","payment_terms_label":"Due on Receipt","show_no_of_copies":true,"date":"2020-06-14","submitted_date":"","notes":"Thanks for your business.","template_type_formatted":"","late_fee":{"amount":0,"rate_formatted":"\u20ac0,00","rate":0,"name":"","amount_formatted":"\u20ac0,00","frequency_type":"month","type":"percentage"},"documents":[],"client_viewed_time":"","discount_amount":0,"ecomm_operator_id":"","shipping_charge_inclusive_of_tax":3,"last_modified_by_id":"122396000000032001","write_off_amount_formatted":"\u20ac0,00","payment_discount_formatted":"\u20ac0,00","invoice_id":"122396000000033059","contact_category":"","template_type":"","recurring_invoice_id":"","color_code":"","contact_persons":["122396000000033035"],"can_send_invoice_sms":true,"shipping_charge_tax":"","bcy_tax_total":10,"created_time":"2020-06-14T18:33:43+0200","created_date_formatted":"14/06/2020","last_payment_date_formatted":"","is_inclusive_tax":false,"custom_fields":[],"last_payment_date":"","discount_applied_on_amount_formatted":"\u20ac0,00","price_precision":2,"sub_total_inclusive_of_tax_formatted":"\u20ac0,00","current_sub_status_formatted":"Draft","payment_discount":0,"approvers_list":[],"shipping_charge_tax_percentage":"","zcrm_potential_name":"","adjustment":4,"created_by_id":"122396000000032001","is_backorder":"","current_sub_status":"draft","discount_amount_formatted":"\u20ac0,00","due_date_formatted":"14/06/2020","is_discount_before_tax":true,"shipping_charge_inclusive_of_tax_formatted":"\u20ac3,00","attachment_name":"","ach_payment_initiated":false,"last_reminder_sent_date":"","merchant_id":"","payment_terms":0,"shipping_charge_exclusive_of_tax":3,"total":267,"shipping_charge_exclusive_of_tax_formatted":"\u20ac3,00","tax_total_formatted":"\u20ac0,00","current_sub_status_id":"","sub_total_formatted":"\u20ac250,00","tax_amount_withheld":0,"tax_amount_withheld_formatted":"\u20ac0,00","custom_field_hash":{},"bcy_shipping_charge":3,"shipping_address":{"zip":"","country":"","address":"","city":"","phone":"","attention":"","street2":"","state":"","fax":""},"next_reminder_date_formatted":"","shipping_charge_tax_formatted":"","bcy_discount_total":0,"shipping_charge_tax_type":"","orientation":"portrait","discount_applied_on_amount":0,"due_date":"2020-06-14","no_of_copies":1,"submitter_id":"","submitted_by":"","subject_content":"This is The Subject","payment_made_formatted":"\u20ac0,00","payment_expected_date":"","unused_retainer_payments":0,"bcy_sub_total":250,"is_emailed":false,"reminders_sent":0,"salesperson_name":"","salesperson_id":"","shipping_charge":3,"payment_made":0,"bcy_adjustment":4,"sub_total":250,"allow_partial_payments":false,"created_date":"2020-06-14","currency_id":"122396000000000071","invoice_url":"https://zohosecurepay.eu/invoice/otwsrl/secure?CInvoiceID=2-6ca32e7b078791fcdcc5ead77dbc52a7b54cc4d3c1c1bb6d49d351c9232255b05582a0db903a6955a054be84c7c26eeb73482b971d9cd4781af23344c636f0a15ff36ce7c9675220 ","payment_reminder_enabled":true}}
The problem comes from when you have something which isn't an array which has a key of 0. So what I've done here is to move the check for a numeric key outside the if and so it gets applied to either time you add the key into the structure...
function array_to_xml( $data, &$xml_data ) {
foreach( $data as $key => $value ) {
if( is_numeric($key) ){
$key = 'item'.$key; //dealing with <0/>..<n/> issues
}
if( is_array($value) ) {
$subnode = $xml_data->addChild($key);
array_to_xml($value, $subnode);
} else {
$xml_data->addChild("$key",htmlspecialchars("$value"));
}
}
}
I have a json feed that is more or less a list of objects
each has it's own id and idParent. objects that have idParent of null are the base parent elements. What I'm trying to achieve is to make a proper multidimensional array like a tree view. Keep in mind that children can have children too.
{
"obj1":{
"idParent":null,
"id":"parent1"
},
"obj2":{
"idParent":null,
"id":"parent2"
},
"obj3":{
"idParent":null,
"id":"parent3"
},
"obj4":{
"idParent":null,
"id":"parent4"
},
"obj5":{
"idParent":null,
"id":"parent5"
},
"obj6":{
"idParent":"parent1",
"id":"layer1-1"
},
"obj7":{
"idParent":"parent1",
"id":"layer1-2"
},
"obj8":{
"idParent":"parent2",
"id":"layer1-3"
},
"obj9":{
"idParent":"parent4",
"id":"layer1-4"
},
"obj10":{
"idParent":"parent3",
"id":"layer1-5"
},
"obj11":{
"idParent":"layer1-1",
"id":"layer2-1"
},
"obj12":{
"idParent":"parent5",
"id":"layer2-2"
},
"obj13":{
"idParent":"layer1-4",
"id":"layer2-3"
},
"obj14":{
"idParent":"layer1-5",
"id":"layer2-4"
},
"obj15":{
"idParent":"layer1-5",
"id":"layer2-5"
}
}
I've managed to filter out the root parents but after that I fail very bad
The first function does filter out the root parent nodes with idParent of null.
function decodeData($data) {
global $out;
foreach ($data as $key => $obj) {
if (is_array($obj)) {
foreach ($obj as $prop => $value) {
if ($prop == 'idParent') {
if($value == null) {
array_push($out, $obj);
unset($data[$key]);
}
}
}
}
}
if (count($data) > 0) {
decodeData($data);
} else {
echo json_encode(array('length'=>count($data)));
}
}
And this is what I'm experimenting on with no result
function decodeData($arrays) {
global $out;
foreach ($arrays as $array_name => $arr) {
foreach ($arr as $arr_prop => $arr_val) {
if ($arr_prop == 'idParent' && $arr_val == null) { // we found root parents
array_push($out, $arr);
unset($arrays[$array_name]); //remove array from the list
} else { // check if idParent is inside out
foreach ($out as $out_arr_name => $out_arr) { // iterate through out arrays
foreach ($out_arr as $out_arr_prop => $out_prop_val) { //
if ($out_arr_prop == 'id' && $arr_prop == 'idParent' && $out_arr_val == $arr_val) {
array_push($out_arr['children'], $obj);
unset($arrays[$array_name]);
}
}
}
}
}
}
if (count($arrays) > 0) {
decodeData($arrays);
} else {
echo json_encode(array('length'=>count($arrays)));
}
}
If anyone could provide some help I would really appreciate it.
I couldn't figure out what output do you want, so I just made a simple tree structure:
$data = json_decode( $your_json_string );
// Store each element in a lookup table indexed by element id
// 0th pass: put a fake root element there
$by_id = array(
'*' => new stdclass
);
// First pass: put each element into there
foreach( $data as $o ) $by_id[ $o->id ] = $o;
// Second pass: add each element into its parent's children array
foreach( $data as $o ){
$pid = $o->idParent ? $o->idParent : '*';
$p = $by_id[ $pid ];
$p->children[] = $o;
}
// Trash everything else, we start from the (fake) root element:
$tree = $by_id['*']->children;
/**** REVERSE ****/
$todo = $tree;
$json = array();
while( $todo ){
$o = array_shift( $todo );
if( isset( $o->children )){
$todo = array_merge( $todo, $o->children );
unset( $o->children );
}
$json[] = $o;
};
echo json_encode( $json );
The result:
http://codepad.viper-7.com/V7PjDh