I have sent a JSON object to PHP to query my database and return a resultset, however I am getting some unusual behaviour - my JSON object arrives in my script as:
{ "username": "Bobby", "dob": "2015-02-12T00:00:00.000Z" }
Which looks fine too me, in order to perform operations on that data I know I need to use json_decode so that PHP receives it as an array, however when I perform json_decode($request) the output array is:
{ undefined: 24, Bobby: ["dob"]}
I have never had this happen before, and can't quite get my head around exactly why this is happening
EDIT: My complete operation looks like:
if(isset($request)) {
var_dump($request);
$json = json_decode($request, true);
var_dump($json);
}
The first dump is correct, once decoded I get the skewed output
EDIT: I am sending the JSON object from Angular, but I don't think this should cause any problems, however its the only thing I have done differently to what I have in previous apps:
if (!(userName === undefined) && !(userDob === undefined))
{
var json = { "name" : userName, "dob" : userDob };
// Create POST request to the file in the url, send it to PHP in JSON format
var callback = $http.post($scope.url, json );
callback.success(function(data, status) {
...
});
}
EDIT I don't quite understand why, but using print_f or var_dump was delivering skewed results, however if I simply did:
$json = json_decode($request);
$name = $json->name;
$dob = $json->dob;
echo $name;
echo $dob;
It returns the results I would expect.
I believe you may need quotes around the keys:
{ "username": "Bobby", "dob": "2015-02-12T00:00:00.000Z" }
Give that a try.
That's a JavaScript object. Try:
var json = { "name" : userName, "dob" : userDob };
JSON.stringify(json);
Related
I'm loading a large amount of data into a Node array. Then, I'm passing that data to a PHP page like this:
const rows = res.data.values;
axios.post('./template.php', qs.stringify({rows}))
.then((res) => {
console.log(res.data);
fs.writeFileSync('test.php', res.data, 'utf-8');
})
Then, when I get to test.php, the $_POST variable is only the first 100 entries of my array I just passed.
I noticed when debugging and using console.log() to print the same array, I was getting something that said "... 19 more items". I was able to resolve that by calling this:
util.inspect.defaultOptions.maxArrayLength = null;
At the top of my function. This worked great to stop the "... 19 more items" and now the full array displays with console.log(), however, it seems to have had no effect on my POST.
I'm stumped as to what I'm missing here -- does anyone know why my array is getting truncated when doing the POST? Thanks!
Something like this
let objectData = [{a: 1, b: 2}, {a: 5, b:6}];
axios.post(url, objectData, {
headers: {
"Content-Type": "application/json"
}
})
and at the PHP side, read the raw INPUT
$json = file_get_contents('php://input');
$data = json_decode($json);
Not sure what issue was with first pastebin code, here is another attempt.
I am connecting to Vimeo Live API, in doing so the response is huge > 500kb in total - I have an example with only one object here -> there are over 20 it returns. I have a better idea of what Im doing in JS than PHP, but returning the huge array or json to the browser doesn't seem like a good idea and its use of repeated ajax calls isn't good either. So this question is two fold, both in theory and practice. Is this a good design and how do I filter the result in PHP and only send what I need back to browser.
Here is the design, or at least what I think is best:
page loads, sends ajax request to PHP script
PHP script connects to API and gets response in an array (example of one object)
Search through the array for 'metadata->connections->live_video' for one that has an associated array containing [status] => streaming'
If one (there will only be one at a time) is found, return that whole object and that object only, not the entire array.
At this time I do not have a complete understanding of how this data should be returned or formatted for ease of sifting through. Ive tried using json_encode on the array, which gets nicely formatted JSON but I can't iterate through it and can only get single objects like data[0]->metadata->connections->live_video. Ive tried json_encode, then json_decode and Im back to a similar array structure of what is originally sent.
However, in the browser I am able to return the whole array and in the success function of the ajax call sift through it via JS like so:
let live_stream = json.data.filter(function(value, key) {
let connection = value.metadata.connections['live_video'];
return connection && connection.status === 'streaming';
});
I know this isn't the right way, I know I need to sift through the array, find the object / key Im looking for and only return that. Any advice is appreciated, once I get this figured out, I can apply it in a range of ways for this project.
The closest I can get in PHP is:
function live_event() {
global xxx;
$lib = xxx;
$response = xxx;
$body = $response['body'];
header('Content-Type: application/json');
$jsonstr = json_encode($body);
$json = json_decode($jsonstr);
foreach ($json->data as $item) {
if ($item->uri == "/live_events/2354796") {
echo"one";
}
}
}
and this:
function live_event() {
$global xxx;
$lib = xxx;
$response = xxx;
$body = $response['body'];
header('Content-Type: application/json');
$jsonstr = json_encode($body);
$json = json_decode($jsonstr,true);
$results = array_filter($json['data'], function($item) {
return $item['metadata']['connections']['live_video']['status'] == "streaming";
});
var_dump($results);
}
last one gets me this error "Warning: Trying to access array offset on value of type null in /var/www/vhosts/mysite.com/httpdocs/SSI/Vimeo.php on line 31" is there something similar to optional chaining in PHP? if its null I don't want it to log an error.
This at least output "one" as there is only one object with [uri]=>"/live_events/2354796". I can't get it to return that entire object or search one more nested array deeper.
There are a few things that come to mind.
OBJECTS:
If you're using PHP 8 you could use the safe access operator
function live_event() {
//...
$results = []
foreach ($json->data as $item) {
if($item?->metadata?->connections?->live_video?->status == 'streaming'){
$results[] = $item;
}
}
return $results;
}
ARRAYS:
For lower versions of PHP it's better to work with arrays when dealing with keys that may or may not exists.
Generally speaking whatever fetch library you're working with will allow you set the output to either array or object. If Object is your only option then yes doing the old json_decode(json_encode($data), true) is the way to go.
checking first isset(). Assuming that's it's desired to filter out results without that key.
function live_event() {
//...
$results = array_filter($json['data'], function($item) {
if(!isset($item['metadata']['connections']['live_video']['status']))
return false;
return $item['metadata']['connections']['live_video']['status'] == "streaming";
});
header('Content-Type: application/json');
echo json_encode([
"status" => true,
"data" => $results
]);
}
or you can always just use the age old trick of suppressing the error with the # symbol. TBH i'm not sure where the # symbol would go to suppress the error, perhaps in front of the filter function definition.
function live_event() {
//...
$results = array_filter($json['data'], function($item) {
return #$item['metadata']['connections']['live_video']['status'] == "streaming";
});
return $results;
}
I am making an CMS, Where you have to put in your own JSON data string.
Like this
Then its going to a php file. But in that file I want to split the data string
from something like this:
{"main_object": {"audio":"nl", "title":"Opdracht 1", "vraag":"[0, 1, "a"]", "antwoord"["yes", "no", 0]" }}
to this
["audio", "title", "vraag", "antwoord"]
Using json_decode, care, your JSON string is not correct :
$json_string = '{"main_object": {"audio":"nl", "title":"Opdracht 1", "vraag":[0, 1, "a"], "antwoord":["yes", "no", 0]}}';
// Add TRUE to force an array, not an object
$array = json_decode($json_string, TRUE);
print_r(array_keys($array['main_object']));
It works with this code. I tried.
Assuming the following PHP code:
<?php
$JSONData = '{"main_object": {"audio":"nl", "title":"Opdracht 1", "vraag":"[0, 1, "a"]", "antwoord"["yes", "no", 0]" }}'; //In reality you'll be getting the JSON data from the form rather than assigning it here.
$arrayData = json_decode($JSONData, true);
if ($arrayData !== null
&& is_array($arrayData)
&& isset($arrayData["main_object"])
&& is_array($arrayData["main_object"])) { //JSON was valid and in the correct format
$usableData = array_keys($arrayData["main_object"]);
//Do whatever you need to do with your $usableData
} else {
//Handle badly formatted data here.
}
I am requesting my output look like this:
Response
{
error_num: 0
error_details:
[
{
"zipcode": 98119
},
{
"zipcode": 98101
}
]
}
The values are irrelevant for this example.
My code looks like this:
$returndata = array('error_num' => $error_code);
$returndata['error_details'] = $error_msg;
$temp_data = array();
$temp_value = '';
foreach ($zipcodes_array as $value) {
//$temp_data['zipcode'] = $value;
//$temp_value .= json_encode($temp_data);
$temp_value .= '{"zipcode":$value},';
}
//$returndata['test'] = $temp_value;
$returndata['zipcodes'] = $temp_value;
echo json_encode($returndata);
My output varies depending on my different attempts (which you can see with the commented out things) but basically, I don't understand how the 3rd part (the part with the zipcodes) doesn't have a key or a definition before the first open bracket "["
Here is the output for the code above:
{"error_num":0,"error_details":"","zipcodes":"{\"zipcode\":11111},{\"zipcode\":11112},{\"zipcode\":11113},{\"zipcode\":22222},{\"zipcode\":33333},{\"zipcode\":77325},{\"zipcode\":77338},{\"zipcode\":77339},{\"zipcode\":77345},{\"zipcode\":77346},{\"zipcode\":77347},{\"zipcode\":77396},{\"zipcode\":81501},{\"zipcode\":81502},{\"zipcode\":81503},{\"zipcode\":81504},{\"zipcode\":81505},{\"zipcode\":81506},{\"zipcode\":81507},{\"zipcode\":81508},{\"zipcode\":81509},"}
Obviously i did not show the variables being filled/created because its through MySQL. The values are irrelevant. Its the format of the output i'm trying to get down. I don't understand how they have the "zipcode": part in between {} brackets inside another section which appears to be using JSON_ENCODE
It is close but see how it still has the "zipcodes": part in there defining what key those values are on? My question is, is the "response" above being requested by a partner actually in JSON_ENCODE format?? or is it in some custom format which I'll just have to make w/out using any json features of PHP? I can easily write that but based on the way it looks in the example above (the response) I was thinking it was JSON_ENCODE being used.
Also, it keeps putting the \'s in front of the " which isn't right either. I know it's probably doing that because i'm json_encode'ing a string. Hopefully you see what i'm trying to do.
If this is just custom stuff made to resemble JSON, I apologize. I've tried to ask the partner but I guess i'm not asking the right questions (or the right person). They can never seem to give me answers.
EDIT: notice my output also doesn't have any [ or ] in it. but some of my test JSON_ENCODE stuff has had those in it. I'm sure its just me failing here i just cant figure it out.
If you want your output to look like the JSON output at the very top of your question, write the code like this:
$returndata = array('error_num' => $error_code);
$returndata['error_details'] = array();
foreach ($zipcodes_array as $value) {
$returndata['error_details'][] = array('zipcode' => (int)$value);
}
echo 'Response ' . json_encode($returndata);
This will return JSON formatted like you requested above.
Response
{
error_num: 0
error_details:
[
{
"zipcode": 98119
},
{
"zipcode": 98101
}
]
}
Can you just use single ZipCode object as associative array, push all your small ZipCode objects to the ZipCodes array and encode whole data structure. Here is the code example:
$returndata = array(
'error_num' => $error_code,
'error_details' => array()
);
foreach ($zipcodes_array as $value) {
$returndata['error_details'][] = array('zipcode' => $value);
}
echo json_encode($returndata);
I've been experiencing a lot of trouble with my issue all afternoon. Endless searches on Google and SO haven't helped me unfortunately.
The issue
I need to send an array to a PHP script using jQuery AJAX every 30 seconds. After constructing the array and sending it to the PHP file I seemingly get stuck. I can't seem to properly decode the array, it gives me null when I look at my console.
The scripts
This is what I have so far. I am running jQuery 1.11.1 and PHP version 5.3.28 by the way.
The jQuery/Ajax part
$(document).ready(function(){
$.ajaxSetup({cache: false});
var interval = 30000;
// var ids = ['1','2','3'];
var ids = []; // This creates an array like this: ['1','2','3']
$(".player").each(function() {
ids.push(this.id);
});
setInterval(function() {
$.ajax({
type: "POST",
url: "includes/fetchstatus.php",
data: {"players" : ids},
dataType: "json",
success: function(data) {
console.log(data);
}
});
}, interval);
});
The PHP part (fetchstatus.php)
if (isset($_POST["players"])) {
$data = json_decode($_POST["players"], true);
header('Content-Type: application/json');
echo json_encode($data);
}
What I'd like
After decoding the JSON array I'd like to foreach loop it in order to get specific information from the rows in the database belonging to a certain id. In my case the rows 1, 2 and 3.
But I don't know if the decoded array is actually ready for looping. My experience with the console is minimal and I have no idea how to check if it's okay.
All the information belonging to the rows with those id's are then bundled into a new array, json encoded and then sent back in a success callback. Elements in the DOM are then altered using the information sent in this array.
Could someone tell me what exactly I am doing wrong/missing?
Perhaps the answer is easier than I think but I can't seem to find out myself.
Best regards,
Peter
The jQuery.ajax option dataType is just for the servers answer. What type of anser are you expexting from 'fetchstatus.php'. And it's right, it's json. But what you send to this file via post method is not json.
You don't have to json_decode the $_POST data. Try outputting the POST data with var_dump($_POST).
And what happens if 'players' is not given as parameter? Then no JSON is returning. Change your 'fetchstatus.php' like this:
$returningData = array(); // or 'false'
$data = #$_POST['players']; // # supresses PHP notices if key 'players' is not defined
if (!empty($data) && is_array($data))
{
var_dump($data); // dump the whole 'players' array
foreach($data as $key => $value)
{
var_dump($value); // dump only one player id per iteration
// do something with your database
}
$returningData = $data;
}
header('Content-Type: application/json');
echo json_encode($returningData);
Using JSON:
You can simply use your returning JSON data in jQuery, e.g. like this:
// replace ["1", "2", "3"] with the 'data' variable
jQuery.each(["1", "2", "3"], function( index, value ) {
console.log( index + ": " + value );
});
And if you fill your $data variable on PHP side, use your player id as array key and an array with additional data as value e.g. this following structure:
$data = array(
1 => array(
// data from DB for player with ID 1
),
2 => array(
// data from DB for player with ID 2
),
...
);
// [...]
echo json_decode($data);
What I suspect is that the data posted is not in the proper JSON format. You need to use JSON.stringify() to encode an array in javascript. Here is an example of building JSON.
In JS you can use console.log('something'); to see the output in browser console window. To see posted data in php you can do echo '<pre>'; print_r($someArrayOrObjectOrAnything); die();.
print_r prints human-readable information about a variable
So in your case use echo '<pre>'; print_r($_POST); to see if something is actually posted or not.