Parsing and echoing JSON with PHP - php

Ok I have banged my head for the last 24hrs and cannot figure this out after testing and reading SO. I have a JSON file that I need to parse and for some reason I cannot get the right combination of code to echo anything out other than "Array" or "Trying to get property of non-object" or "Invalid argument supplied for foreach()". Here is the full JSON that I am trying to iterate over. I need to print out the name of each 'project', the 'dataset' in each project, and the 'permissions' for each 'dataset'. I am building this JSON myself, so I can change the format if necessary.
$data = json_decode($json, true);
Outputs JSON below:
[
[
{
"projects":[
{
"project":"test-project-1",
"datasets":[
{
"dataset":"testing1",
"permissions":[
{
"role":"READER",
"google_group":"testing1#test.com"
}
]
},
{
"dataset":"testing2",
"permissions":[
{
"role":"OWNER",
"google_group":"testing2#test.com"
}
]
},
{
"dataset":"testing3",
"permissions":[
{
"role":"READER",
"google_group":"testing3#test.com"
}
]
},
{
"dataset":"testing4",
"permissions":[
{
"role":"WRITER",
"google_group":"testing4#test.com"
}
]
}
]
},
{
"project":"test-project-2",
"datasets":[
{
"dataset":"testing1",
"permissions":[
{
"role":"READER",
"google_group":"testing1#test.com"
}
]
},
{
"dataset":"testing2",
"permissions":[
{
"role":"READER",
"google_group":"testing2#test.com"
}
]
},
{
"dataset":"testing3",
"permissions":[
{
"role":"READER",
"google_group":"testing3#test.com"
}
]
},
{
"dataset":"testing4",
"permissions":[
{
"role":"READER",
"google_group":"testing4#test.com"
}
]
}
]
}
]
}
]
]
I have tried things like:
foreach($data->projects as $output)
{
echo $output->project . "\n";
foreach($output->datasets as $datasets)
{
echo $output->dataset . "\n";
}
}
Thank you for the help!
EDIT: Working code that parses the JSON above:
$projects = $json['projects'];
foreach ($projects as $project) {
echo $project['project'] . "<br>";
foreach ($json['projects'][0]['datasets'] as $datasets){
echo $datasets['dataset'] . "<br>";
foreach ($json['projects'][0]['datasets'][0]['permissions'] as $permissions){
echo $permissions['role'] . "<br>";
echo $permissions['google_group'] . "<br>";
}
}
}

Your json contains two nested arrays, which contain the object, you want. So first you could use something like [0][0] to get the associative array, which contains the project.
// ...
$projects = $json['projects'];
foreach ($projects as $project) {
echo "Project: " . $project['project'] . "\n";
foreach ($project['datasets'] as $dataset) {
echo "Dataset: " . $dataset['dataset'];
foreach ($dataset['permissions'][0] as $key => $value) {
// ...
}
}
}

Related

How to recursively iterate for dynamic data

I've Json data in PHP which is:
{
"module": [
{
"jhooq-webserver-1": [
{
"source": ".//module-1"
}
]
},
{
"jhooq-webserver-2": [
{
"source": ".//module-2"
}
]
}
],
"provider": [
{
"aws": [
{
"access_key": "var.access_key",
"region": "var.web_region",
"secret_key": "var.secret_key"
}
]
}
]
}
All i wanted is to use recursive function to convert it to the below format (output):
provider "aws" {
region = "var.web_region"
access_key = "var.access_key"
secret_key = "var.secret_key"
}
module "jhooq-webserver-1" {
source = ".//module-1"
}
module "jhooq-webserver-2" {
source = ".//module-2"
}
Any help will be greatly appreciated.
I've tried using recursive function in php which i failed unfortunately failed. I'm unclear to use recursive function for my scenario.
You don't really need a recursive function to do this:
foreach($array as $blockName => $level2) {
foreach($level2 as $level3) {
foreach($level3 as $title => $level4) {
echo "$blockName \"$title\" {\n";
foreach($level4 as $level5) {
foreach($level5 as $key => $value) {
echo " $key = \"$value\"\n";
}
}
echo "}\n";
}
}
}

How to get data from JSON after decoding

I am trying to get data from a JSON that's a bit complex for me.
How can I get the value in Amount or Transaction date
I can get the MerchantRequestID using this code
$mpesaResponse = file_get_contents('php://input');
$jsonMpesaResponse = json_decode($mpesaResponse, true);
$MerchantRequestID = $jsonMpesaResponse["Body"]["stkCallback"]["MerchantRequestID"];
// An accepted request
{
"Body":{
"stkCallback":{
"MerchantRequestID":"19465-780693-1",
"CheckoutRequestID":"ws_CO_27072017154747416",
"ResultCode":0,
"ResultDesc":"The service request is processed successfully.",
"CallbackMetadata":{
"Item":[
{
"Name":"Amount",
"Value":1
},
{
"Name":"MpesaReceiptNumber",
"Value":"LGR7OWQX0R"
},
{
"Name":"Balance"
},
{
"Name":"TransactionDate",
"Value":20170727154800
},
{
"Name":"PhoneNumber",
"Value":254721566839
}
]
}
}
}
}
At the moment it comes out blank what ever i try
You need to loop through your Item array.
<?php
$str = '
{
"Body":{
"stkCallback":{
"MerchantRequestID":"19465-780693-1",
"CheckoutRequestID":"ws_CO_27072017154747416",
"ResultCode":0,
"ResultDesc":"The service request is processed successfully.",
"CallbackMetadata":{
"Item":[
{
"Name":"Amount",
"Value":1
},
{
"Name":"MpesaReceiptNumber",
"Value":"LGR7OWQX0R"
},
{
"Name":"Balance"
},
{
"Name":"TransactionDate",
"Value":20170727154800
},
{
"Name":"PhoneNumber",
"Value":254721566839
}
]
}
}
}
}
';
$json = json_decode($str, true);
foreach($json['Body']['stkCallback']['CallbackMetadata']['Item'] as $index => $item_array_element){
if( $item_array_element['Name'] == 'Amount' ){
echo "Found Amount " . $item_array_element['Value'] . "\n";
}
else if( $item_array_element['Name'] == 'TransactionDate' ){
echo "Found TransactionDate " . $item_array_element['Value'] . "\n";
}
}
Output
Found Amount 1
Found TransactionDate 20170727154800

JSON Array convert to CSV

I'm trying to convert a JSON response to CSV file but I have a problem about arrays
Here is the conversion code to CSV
$jsonString = file_get_contents("feed.json");
$jsonDecoded = json_decode($jsonString, true);
$json = $jsonDecoded['results'];
jsonToCsv($json, "feed.csv");
function jsonToCsv ($json, $csvFilePath = false, $boolOutputFile = false) {
// See if the string contains something
if (empty($json)) {
die("The JSON string is empty!");
}
// If passed a string, turn it into an array
if (is_array($json) === false) {
$json = json_decode($json, true);
}
// If a path is included, open that file for handling. Otherwise, use a temp file (for echoing CSV string)
if ($csvFilePath !== false) {
$f = fopen($csvFilePath,'w+');
if ($f === false) {
die("Couldn't create the file to store the CSV, or the path is invalid. Make sure you're including the full path, INCLUDING the name of the output file (e.g. '../save/path/csvOutput.csv')");
}
}
else {
$boolEchoCsv = true;
if ($boolOutputFile === true) {
$boolEchoCsv = false;
}
$strTempFile = 'feed' . date("U") . ".csv";
$f = fopen($strTempFile,"w+");
}
$firstLineKeys = false;
foreach ($json as $line) {
if (empty($firstLineKeys)) {
$firstLineKeys = array_keys($line);
fputcsv($f, $firstLineKeys);
$firstLineKeys = array_flip($firstLineKeys);
}
// Using array_merge is important to maintain the order of keys acording to the first element
fputcsv($f, array_merge($firstLineKeys, $line));
}
fclose($f);
// Take the file and put it to a string/file for output (if no save path was included in function arguments)
if ($boolOutputFile === true) {
if ($csvFilePath !== false) {
$file = $csvFilePath;
}
else {
$file = $strTempFile;
}
// Output the file to the browser (for open/save)
if (file_exists($file)) {
header('Content-Type: text/csv');
header('Content-Disposition: attachment; filename='.basename($file));
header('Content-Length: ' . filesize($file));
readfile($file);
}
}
elseif ($boolEchoCsv === true) {
if (($handle = fopen($strTempFile, "r")) !== FALSE) {
while (($data = fgetcsv($handle)) !== FALSE) {
echo implode(",",$data);
echo "<br />";
}
fclose($handle);
}
}
// Delete the temp file
unlink($strTempFile);
}
?>
And here is a example of feed.json content
{
"isError":false,
"messages":[
],
"results":[
{
"part_number_key":"DASDSA",
"buy_button_rank":1,
"category_id":11,
"id":123,
"brand":"brand",
"vendor_category_id":null,
"name":"Name",
"part_number":"part number",
"sale_price":12.31,
"currency":"RON",
"description":"description",
"url":"https://www.url.com",
"warranty":12,
"general_stock":10,
"weight":"0",
"status":1,
"recommended_price":12.19,
"images":[
{
"url":"https://url.com/images.jpg1",
"display_type":1
},
{
"url":"https://url.com/images.jpg2",
"display_type":0
},
{
"url":"https://url.com/images.jpg3",
"display_type":0
}
],
"characteristics":[
{
"id":8937,
"value":"value"
},
{
"id":8930,
"value":"value"
},
{
"id":8927,
"value":"value"
},
{
"id":8928,
"value":"value"
},
{
"id":5537,
"value":"value"
},
{
"id":8932,
"value":"value"
},
{
"id":8934,
"value":"value"
},
{
"id":8929,
"value":"value"
},
{
"id":7235,
"value":"value"
},
{
"id":6556,
"value":"value"
},
{
"id":5401,
"value":"value"
}
],
"attachments":[
],
"vat_id":1,
"family":{
"id":1104,
"name":"NAME",
"family_type_id":244
},
"start_date":[
],
"estimated_stock":10,
"reversible_vat_charging":false,
"min_sale_price":11,
"max_sale_price":200,
"offer_details":{
"id":2484194,
"warranty_type":null,
"supply_lead_time":14
},
"offer_properties":[
],
"product_measurements":[
],
"availability":[
{
"warehouse_id":1,
"id":3
}
],
"stock":[
{
"warehouse_id":1,
"value":10
}
],
"handling_time":[
{
"warehouse_id":1,
"value":0
}
],
"barcode":[
],
"ean":[
],
"commission":{
"value":"20.0000",
"type":"percentage",
"id":"123",
"priority":"4",
"created":"2010-01-16 11:25:02"
},
"validation_status":[
{
"value":9,
"description":"Approved documentation",
"errors":null
}
],
"offer_validation_status":{
"value":1,
"description":"Saleable",
"errors":null
},
"ownership":1,
"best_offer_sale_price":11,
"best_offer_recommended_price":11,
"number_of_offers":1
},
{
"part_number_key":"D3129DKQW",
"buy_button_rank":1,
"category_id":456,
"id":123,
"brand":"Bluedio",
"vendor_category_id":null,
"name":"name",
"part_number":"part number",
"sale_price":123,
"currency":"EUR",
"description":"description",
"url":"https://url.com",
"warranty":24,
"general_stock":1,
"weight":"0",
"status":1,
"recommended_price":12,
"images":[
{
"url":"https://url.com/images.jpg1",
"display_type":1
},
{
"url":"https://url.com/images.jpg2",
"display_type":0
},
{
"url":"https://url.com/images.jpg3",
"display_type":0
}
],
"characteristics":[
{
"id":7774,
"value":"val"
},
{
"id":7947,
"value":"val"
},
{
"id":8001,
"value":"val"
},
{
"id":8937,
"value":"val"
},
{
"id":8930,
"value":"val"
},
{
"id":8927,
"value":"val"
},
{
"id":8928,
"value":"val"
},
{
"id":5537,
"value":"val"
},
{
"id":8932,
"value":"val"
},
{
"id":8934,
"value":"val"
},
{
"id":8929,
"value":"val"
},
{
"id":7235,
"value":"val"
},
{
"id":6556,
"value":"val"
},
{
"id":5401,
"value":"val"
}
],
"attachments":[
],
"vat_id":1,
"family":{
"id":123456,
"name":"Name",
"family_type_id":244
},
"start_date":[
],
"estimated_stock":144,
"reversible_vat_charging":false,
"min_sale_price":11,
"max_sale_price":200,
"offer_details":{
"id":242414,
"warranty_type":null,
"supply_lead_time":14
},
"offer_properties":[
],
"product_measurements":[
],
"availability":[
{
"warehouse_id":1,
"id":3
}
],
"stock":[
{
"warehouse_id":1,
"value":9
}
],
"handling_time":[
{
"warehouse_id":1,
"value":0
}
],
"barcode":[
],
"ean":[
],
"commission":{
"value":"20.0000",
"type":"percentage",
"id":"12492",
"priority":"4",
"created":"2010-01-16 11:25:02"
},
"validation_status":[
{
"value":9,
"description":"Approved documentation",
"errors":null
}
],
"offer_validation_status":{
"value":1,
"description":"Saleable",
"errors":null
},
"ownership":1,
"best_offer_sale_price":77.31,
"best_offer_recommended_price":83.19,
"number_of_offers":1
}
]
}
Here is the output of the conversion
part_number_key,buy_button_rank,category_id,id,brand,vendor_category_id,name,part_number,sale_price,currency,description,url,warranty,general_stock,weight,status,recommended_price,images,characteristics,attachments,vat_id,family,start_date,estimated_stock,reversible_vat_charging,min_sale_price,max_sale_price,offer_details,offer_properties,product_measurements,availability,stock,handling_time,barcode,ean,commission,validation_status,offer_validation_status,ownership,best_offer_sale_price,best_offer_recommended_price,number_of_offers
DASDSA,1,11,123,brand,,Name,"part number",12.31,RON,description,https://www.url.com,12,10,0,1,12.19,Array,Array,Array,1,Array,Array,10,,11,200,Array,Array,Array,Array,Array,Array,Array,Array,Array,Array,Array,1,11,11,1
D3129DKQW,1,456,123,Bluedio,,name,"part number",123,EUR,description,https://url.com,24,1,0,1,12,Array,Array,Array,1,Array,Array,144,,11,200,Array,Array,Array,Array,Array,Array,Array,Array,Array,Array,Array,1,77.31,83.19,1
As you can see, there is array instead of values, can someone tell me why?
I tried reset() function but I get only the value from the first column ( part_number_key )
foreach ($json as $line){
if (empty($firstLineKeys)) {
$firstLineKeys = array_keys($line); print_r("aici3"); fputcsv($f,
$firstLineKeys); print_r("aici3"); $firstLineKeys = array_flip($firstLineKeys);
} fputcsv($f,
array_merge($firstLineKeys,
$line)); $first = reset($line); print_r($first);
}
I want to extract all columns but to show only the first row value from every from every column, for example at "images" column I would like to extract just the first url and same for the rest of columns
And one more thing, what is the best method to ignore few columns?
Thanks in advance!

Problems storing nested JSON objects

Could anyone assist me with how I can pass one JSON object as a field to another without having quotes added? Basically I have a function that needs to be able to append a 'header' to a set of data pre parsed into JSON in some cases or just parse the data in others.
Problem is everything works fine until I try to pass a JSON object to be stored as a "payload" for a header, at which point the JSON becomes invalid because of the extra set of quotations attached.
The object that I am trying to use is:
{
"header": {
"table": "user",
"action": "insert",
"opType": "string",
"message": "Insert sucessful for user: 6",
"start of records": false,
"end of records": true
},
"data": "[
{
"id": "6",
"Surname": "Peter",
"Forename": "Kane",
"Email": "pkane#a.co.uk",
"Personal_Email": "p.kane#gmail.com",
"Home_Phone_No": "01216045429",
"Work_Phone_No": "087852489",
"Mobile_Phone_No": "77245455598",
"Address_Line_1": "1aplace",
"Address_Line_2": "thistown",
"Address_Line_3": "Someplace",
"Address_Line_4": "whereever",
"Post_Code": "W549AJ",
"Mode_ID": "44",
"Route_ID": "g12",
"image": ""
}
]"
}
The problem is the quotes after the "data" key and before the last curley brace without these everything validates fine.
As I've said Im using PHP Ive tried regex expressions substring etc but nothing seems to work.
my PHP is as follows:
public function dataToJSON($operationType, $table, $action, $data, $message, $header = true, $firstRecord = null) {
if ((!($operationType) === 'recordSet') and (!($operationType === 'error')) and (!($operationType === 'string') )) {
throw new Exception("Operation type:" . ' ' . $operationType . ' ' . 'passed to the dataToJSON function not recogonised');
}
if (!(is_null($firstRecord))) {
$isFirstRecord = $firstRecord;
$isLastRecord = !$firstRecord;
} else {
$isFirstRecord = false;
$isLastRecord = false;
}
if ($header) {
$jsonData = array('header' => array(
'table' => "$table",
'action' => "$action",
'opType' => "$operationType",
'message' => "$message",
'start of records' => $isFirstRecord,
'end of records' => $isLastRecord),
);
} else {
$jsonData = array();
}
$recordSet = array();
if ($operationType === 'recordSet') {
while ($row = mysql_fetch_assoc($data)) {
array_push($recordSet, $row);
}
if ($header) {
$jsonData ['data'] = $recordSet;
return json_encode($jsonData);
} else {
return json_encode($recordSet);
}
} else if (($operationType === 'error') || ($operationType === 'string')) {
if ($header) {
$jsonData ['data'] = $data;
return stripslashes(json_encode($jsonData));
} else {
return $data;
}
}
}
in order to use / parse json, it needs to be valid json... and those **"** chars make it invalid.
paste and process here to see what i mean: http://jsonformat.com/
A JSON object is nothing more than a mere string. To achieve what you are trying to achieve, you would probably need to decode and then re-encode your JSON string:
$jsonData['data'] = json_decode($data, TRUE);

JSON Encode Help

Currently, I have a JSON encoded array that looks like this:
[
{
"username1": {
"post": {
"some_key" : "some_value"
}
}
},
{
"username1": {
"post": {
"some_key" : "some_value"
}
}
}
]
But how can I make it so that the json follows this pattern:
username -> array_of_posts -> post -> values
instead of the current pattern?
Thanks
Here is my current code:
while ($row = mysql_fetch_assoc($query)) {
$row['username'] = $username;
$returns[][$username]["post"] = $row;
}
}
echo json_encode(array_values($returns));
$returns[$username][] = $row;
echo json_encode($returns);

Categories