Javascript how to parse JSON with json array - javascript

I want to parse this using jQuery or javascript
My JSON generated from the PHP code is as follows:
JSON
{
"user": {
"name": "John Carter",
"position": 0,
"tickets": {
"months": [
"October",
"November"
],
"start_Time": "2014-10-02",
"end_Time": "2014-11-21",
"Open": [
"1",
"3"
]
}
}
}
My Javascript
$.ajax({
url: 'ajax.report.php',
type: 'POST',
data: 'start='+startDate+'&&end='+endDate,
success: function(response){
var json_obj = $.parseJSON(response);
for(var i =0; i < json_obj.user.length; i++){
//What is the next?
}
}
});
Kindly help.
Thank you !

The json returned by jQuery is already a JavaScript object, not a string. You do not have to parse it any further to use it. I'm on a mobile device right now so I can't confirm, but I'm pretty sure you can just do this:
success: function(response){
//try
var name = response.user.name
//try this as well
var name = response.name
}
You should be able to print out the name string using console.log() after this.

I'm assuming that you're trying to convert some JSON in string form to an object usable by JS. You can parse a valid JSON string into a JS object by using JSON.parse(jsonString). (Where jsonString is a variable containing the string of JSON)

I suggest that you look over the jquery docs for more info, the best thing you can use is jquery.ajax Make sure that in your php script you encode the text as JSON, otherwise jquery will interpret it as plain/text.
Little snippet, which you can also find on the jquery docs..
$.ajax( "example.php" )
.done(function(data) {
console.log(data);
});

Related

Properly returning a JSON object with an embedded JS function

Updated Post
I have a solution for that problem which works with me so far (only tested on Firefox).
My main goal was to dynamically update a Flot graph with Ajax. I also need to dynamically update the axis styles and you can do this by the tickFormatter option. To avoid the problems I previously had, I simply insert the desired return string in the PHP array and JSON encode that array. After returned to the Ajax function I create a new function using the javascript Function() constructor (Link). I hope this helps someone.
Ajax
$.ajax({
url: 'someControllerWhichCreatesJSONdata',
data: 'some Value',
type: 'post',
cache: false,
datatype: 'json'
})
.success(function(data) {
var datas = data[0]; // fetch data array
var options = data[1]; // fetch options array
var xReturn = options.xaxes[0].tickFormatter; // fetch return string
var yReturn = options.yaxes[0].tickFormatter;
var xFunc = new Function("val", "axis", xReturn); // create function
var yFunc = new Function("val", "axis", yReturn);
options.xaxes[0].tickFormatter = xFunc; // update tickFormatter with function
options.yaxes[0].tickFormatter = yFunc;
$.plot($("#yw0"), datas, options);
})
.error(function(data) {
$("#error").html(data.responseText); // show error in separate div
});
PHP array
$options = array(
'legend' => array(
'position' => 'nw',
'show' => true,
'margin' => 10,
'backgroundOpacity' => 0.5
),
'grid' => array(
'clickable' => true,
'hoverable' => true
),
'pan' => array('interactive' => true),
'zoom' => array('interactive' => true),
'axisLabels' => array('show' => true),
'xaxes' => array(
array(
'axisLabel' => 'someUnit',
'tickFormatter' => 'return "foo bar"' // enter whatever return value you need
)
),
'yaxes' => array(
array(
'axisLabel' => 'someUnit',
'tickFormatter' => 'return "foo bar"'
)
)
);
I skip the data array as it looks similar. Both arrays get combined and JSON encoded.
public function actionSomeControllerWhichCreatesJSONdata() {
$returnArray = array($data, $options);
echo json_encode($returnArray);
return true;
}
The resulting array looks like the one I've posted in the bottom of this post.
Original Post
I'm trying for hours now, but I can't get this to work.
I have an Ajax request which gets a JSON object as return value on success. This works fine as long as I don't use a JS function in my JSON array. So my JSON array looks as follows (after json_encode):
[{
"data": [{
{1,2},
{3,4},
}],
"function": "function(){return \"foo bar\";}"
}]
In order to get rid of the "'s in the function string. I use str_replace and replace the quoted string with an unquoted one. This then looks like so:
[{
"data": [{
{1,2},
{3,4},
}],
"function": function(){return "foo bar";}
}]
The plain json_encode works fine and my Ajax function reads it as a JSON object. After I replace the string it turns out that the return value is no longer a JSON object but a plain text string. I've tried to parse the string again with jquery.parseJSON() but this results in the syntax error:
SyntaxError: JSON.parse: unexpected keyword at line 1 column 396 of the JSON data
Ajax function:
$.ajax({
url: 'someControllerWhichCreatesJSONdata',
data: 'some Value',
type: 'post',
cache: false,
datatype: 'json' // or text when trying to parse
})
.success(function(data) {
console.log(data);
var dat = jQuery.parseJSON(data); // trying to parse (only when dataType: "text")
var datas = dat[0]; // or data[0] when datType = json
var options = dat[1]; // ---
$.plot($("#yw0"), datas, options); // trying to update a FLOT window
})
.error(function(data) {
console.log("error");
$("#error").html(data.responseText); // show error in separate div
});
So when using this function and setting the return type to "json", it produces an error. If the return type is "text" and I try to parse the string I get the error above. Is there any solution for this problem or am I doing something completely wrong?
Thank's for your help!
UPDATE
Sorry of course my JSON data is not valid! As I said, my JSON object gets created by json_encode which I guess should get the syntax right. The plain array after son_encode looks like:
[[{
"data":[[0.0042612,0.0042612]],
"label":"WISE.W3: Cutri et. al 2012",
"lines":{"show":false},
"points":{"show":true,"radius":3}}],
{
"legend": {
"position":"nw",
"show":true,
"margin":10,
"backgroundOpacity":0.5},
"grid": {
"clickable":true,
"hoverable":true},
"pan":{"interactive":true},
"zoom":{"interactive":true},
"axisLabels":{"show":true},
"axisLabel": {
"unit":"Jy",
"id":null,
"name":null},
"tickFormatter":"$tickFormatter$",
"position":"right"
}]
and after str_replace I get
[[{
"data":[[0.0042612,0.0042612]],
"label":"WISE.W3: Cutri et. al 2012",
"lines":{"show":false},
"points":{"show":true,"radius":3}}],
{
"legend": {
"position":"nw",
"show":true,
"margin":10,
"backgroundOpacity":0.5},
"grid":{"clickable":true,"hoverable":true},
"pan":{"interactive":true},
"zoom":{"interactive":true},
"axisLabels":{"show":true},
"axisLabel":{"unit":"Jy","id":null,"name":null},
"tickFormatter":function(val, axis){return val.toExponential(2)},
"position":"right"
}]
Adeno pointed it out already, your JSON syntax is not valid.
Please try to validate your JSON with a linter, like http://jsonformatter.curiousconcept.com/
This is a bit better:
[{"data":[["1","2"],["3","4"]],"function":"function(){return \"foo bar\";}"}]
And the other thing is: you should not manually deserialize the JSON. All newer versions of jQuery will automatically deserialize JSON based on the response's content-type header.
You already set dataType to json for the ajax request.
The response is JSON and will be de-serialized.
So you can directly use
.success: function(response) {
console.log(response.data);
console.log(response.function);
}
Answer for the questions/issue from the comments:
Now you created invalid JSON again, because "tickFormatter" : function(val, axis){return val.toExponential(2)}, misses the quotes around the function string.
Before you insert the string with str_replace(), you need to take care of escaping and quoting.
You may need a little helper function, which properly escapes a string - to be valid JSON.
you need to use str_replace() correctly: not replacing the outer quotes, just the inner $tickFormatter$.
Wait.. i will provide an example:
// we already have an array, which is JSON encoded
// now you want to insert additional JSON content.
// therefore we use a token replace approach.
// valid JSON - with $token$
$json = '[{"data":[["1","2"],["3","4"]],"tickFormatter":"$tickFormatter$"}]';
// the (future) javascript function is a string.
// it's not properly escaped or quoted to be JSON
// this allows for copy and pasting JS into PHP
$unescaped_functionString = 'function(){return "foo bar";}';
// in order escapre properly, we need a json escaping helper
/**
* #param $value
* #return mixed
*/
function escapeJsonString($value) { # list from www.json.org: (\b backspace, \f formfeed)
$escapers = array("\\", "/", "\"", "\n", "\r", "\t", "\x08", "\x0c");
$replacements = array("\\\\", "\\/", "\\\"", "\\n", "\\r", "\\t", "\\f", "\\b");
$result = str_replace($escapers, $replacements, $value);
return $result;
}
// then we escape the function string
$functionString = escapeJsonString($unescaped_functionString);
// now its ready to be inserted into the existing JSON,
// where token $tickFormatter$ is defined
// the token must be in single quotes. you replace just the $token$ and not "$token$".
$json = str_replace('$tickFormatter$', $functionString, $json);
echo $json;
// The result is valid JSON again:
// [{"data":[["1","2"],["3","4"]],"tickFormatter":"function(){return \"foo bar\";}"}]
Next step:
The ajax request is made, the json data is transferred to the client and you want to execute the function you passed in.
So the new question is "How to call/exec a JavaScript function from a string - without using eval?"
In general tunneling is a bad practice, see: Is it valid to define functions in JSON results?
Anyway, there a different ways to do this:
Referencing: http://everythingfrontend.com/posts/studying-javascript-eval.html
eval() - evil, but works.
setTimeout()
setTimeout(" function ", 0);
new Function()
var codeToExecute = "My.Namespace.functionName()";
var tmpFunc = new Function(codeToExecute);
tmpFunc();
document.write
document.write('<script> JS </script>')
data URI
var s = document.createElement('script');
s.src = 'data:text/javascript,' + encodeURIComponent('alert("lorem ipsum")')
document.body.appendChild(s);
JSON cannot contain functions like this.
You can however use Javascript to inject the function into the DOM, so what you want to do is skip the str_replace part and simply create a <script type="text/javascript"></script> element in the DOM and insert the data.function property into there.

How to extract data from this JSON string?

I'm new to JSON and Jquery, and I can't find how to extract the values of ProjectCode from this JSON string.
[
{
"ProjectID": 3,
"CLustomerCode": "XYZ001",
"ProjectCode": "YZPROJ1",
"Description": "Project1",
"IssueManager": "iant",
"NotificationToggle": false,
"ProjectStatus": null,
"Added": "/Date(1400701295853}/",
"Added By": "iant",
"Changed": "/Date(1400701295853)/",
"Changed By": "iant"
},
{
"ProjectID": 4,
"CustomerCode": "XYZ001",
"ProjectCode": "XYXPROJ2",
"Description": "Projecton:Project2",
"IssweManager": "iant",
"NotificationToggle": false,
"Projectstatus": null,
"Added": "lDate(1400701317980)/",
"AddedBy": "iant",
"Changed": "/Date(1400701317980)/",
"Changed By": "iant"
}
]
The string above is from a variable called data that is the return value from stringify. I expected to be able to do something like
string proj = data[i].ProjectCode;
but intellisense doesn't include any of the properties.
I know very little about JSON - any help appreciated.
Thanks for reading.
Use parseJSON:
var obj = jQuery.parseJSON("{ 'name': 'Radiator' }");
alert(obj.name);
You need to loop through each object returned in the response and get the ProjectCode property inside each one. Assuming the data variable is your JSON this should work:
$.each(data, function(i, obj) {
console.log(obj.ProjectCode);
});
Use JSON.parse():
var a; // Your JSON string
var b = JSON.parse(a); //Your new JSON object
//You can access Project code, use index i in b[i].ProjectCode in a loop
var projectCode = b[0].ProjectCode;
You should post the raw code so its easier to visualize this stuff. Since what you are looking for is the list of ProjectCodes (in this case - ["XYZPROJ1", "XYZPROJ2"]).
It seems like what we have is an array or list ([...]) of projects. Where each project has a ProjectID, CustomerCode, ProjectCode, Description and so on...
So lets assume data points at this JSON blob. Here is how you would go about accessing the ProjectCode:
// Access the "i"th project code
var p_i_code = data[i].ProjectCode;
// How many projects?
var num_projects = data.length; // since data is a list of projects
// Want the list of project codes back? (I use underscore.js)
var project_codes = _.map(data, function(project) {
return project.ProjectCode;
});

can somene explain me, why this code result is different?(javascript object and array)

i will ask about this:
i have an javascript object like this:
var stops = [
{"Geometry":{"Latitude":52.1615470947258,"Longitude":20.80514430999756}},
{"Geometry":{"Latitude":52.15991486090931,"Longitude":20.804049968719482}},
{"Geometry":{"Latitude":52.15772967999426,"Longitude":20.805788040161133}},
{"Geometry":{"Latitude":52.15586034371232,"Longitude":20.80460786819458}},
{"Geometry":{"Latitude":52.15923693975469,"Longitude":20.80113172531128}},
{"Geometry":{"Latitude":52.159849043774074, "Longitude":20.791990756988525}},
{"Geometry":{"Latitude":52.15986220720892,"Longitude":20.790467262268066}},
{"Geometry":{"Latitude":52.16202095784738,"Longitude":20.7806396484375}},
{"Geometry":{"Latitude":52.16088894313116,"Longitude":20.77737808227539}},
{"Geometry":{"Latitude":52.15255590234335,"Longitude":20.784244537353516}},
{"Geometry":{"Latitude":52.14747369312591,"Longitude":20.791218280792236}},
{"Geometry":{"Latitude":52.14963304460396,"Longitude":20.79387903213501}}
]
alert(stops);
in first code the alert result is
i have a data from ajax request, so i can make an object like that dynamic.. i call it from my database
var stops=new Array();
var myObject={};
$.ajax({
url: 'http://localhost:5566/Gps/api/rute.php?id='+id,
//url: 'http://localhost:5566/Gps/api/rute.php?id='+id,
dataType: 'jsonp',
jsonp: 'jsoncallback',
timeout: 5000,
async: false,
success: function(data, status){
i=0;
stops+="[";
$.each(data, function(i,item){
stops+="{\"Geometry\":{\"Latitude\":";
stops+=item.latitude;
stops+=",";
stops+="\"Longitude\":";
stops+=item.longitude;
stops+="}}";
stops+=",";
});
stops+=stops.substring(0,stops.length-1);
stops+="];";
alert(stops);
in second code the alert result is
i think the stops variable have same structure,but why the alert result is different?
can i convert second code to object like first code? thank you :)
any help will be appreciated
Your first object is an array the second you appear to be manually building a JSON string into an array?
As stops is an array just add objects to it:
success: function(data, status){
$.each(data, function(i,item){
var stop = {
Geometry: {
Latitude: item.latitude,
Longitude: item.longitude
}
};
stops.push(stop);
});
alert(stops);
}
The second one is a string. Yes, you can decode JSON.
To convert the first like the second use:
JSON.stringify(stops);
To convert the second like the first use:
JSON.parse(stops);
or
$.parseJSON(stops);
edit: As was recommended, since you are using jQuery you can use $.parseJSON(stops) in place of JSON.parse(). It will actually use the native parse if available. There is no equivalent (that I know of) for stringify.

getJSON to fetch data from this json array

This is a sample json array from my code. How can i use getJSON to fetch data from this array.
"Restoration": [
{
"Easy": {
"value": "1",
"info": "This is Easy."
},
"Medium": {
"value": ".75",
"info": "This is Medium."
},
"Difficult": {
"value": ".5",
"info": "This is Difficult."
}
}
]
using jQuery jQuery.getJSON():
$.getJSON('ajax/test.json', function(data) {
console.log(data); //see your data ( works in Chrome / FF with firebug)
console.log(data["Restoration"][0]["easy"]["value"]) //should output 1
});
This is an alternative to use "jQuery.getJSON()" because sometimes we don't have a "domain/file.json" or somewhere to do the $get or we don't want to use jQuery
for this simple process.
This method parses json from string.
You can do it with simple javascript like this:
//json string for testing
var jsonstr = '{"id":"743222825", "name":"Oscar Jara"}';
//parse json
var data = JSON.parse(jsonstr);
//print in console
console.log("My name is: " + data.name + " and my id is: " + data.id);
Hope this helps.
Regards.
This might help you.
http://underscorejs.org/#keys
var list=_.Keys(data["Restoration"][0]);

JSON parsing with javascript

I am trying to parse a JSON response from a server using javascript/jquery. This is the string:
{
"status": {
"http_code": 200
},
"contents": "HTTP/1.1 200 OK\r\nTransfer-Encoding: chunked\r\nDate: Tue, 07 Feb 2012 08:14:38 GMT\r\nServer: localhost\r\n\r\n {\"response\": \"true\"} "
}
I need to get the response value.
Here is what I am trying in the success function of my POST query:
success: function(data) {
var objstring = JSON.stringify(data);
var result = jQuery.parseJSON(JSON.stringify(data));
alert(objstring);
var result1 = jQuery.parseJSON(JSON.stringify(result.contents[0]));
alert(result1.response);
alert(data.contents[0].response);
But so far nothing I have tried returns the correct result' I keep getting undefined, however the contents of objstring are correct and contain the JSON string.
First, set dataType to json. Then data will be an object containing the data specified:
dataType: 'json',
success: function(data) {
alert(data.status.http_code);
alert(data.contents);
}
Read the API for more explanation of what these properties achieve. It would also probably help you to use a Javascript console, so you can use console.log, a much more powerful tool than alert.
Seems like the JSON response itself contains JSON content. Depending on how you call the jQuery.post() method, you'll either get a string or a JSON object. For the first case, use jQuery.parseJSON() to convert the string to a JSON object:
data = jQuery.parseJSON(theAboveMentionedJsonAsString);
Next, get everything inside the contents property after the first \r\n\r\n:
var contentBody = data.contents.split("\r\n\r\n", 2)[1];
Lastly, convert that string to JSON and get the desired value:
var response = jQuery.parseJSON(contentBody).response;
// "true"
try it this way:
var objstring=JSON.stringify(data);
var result=JSON.parse(objstring);
alert("http code:" + result.status.http_code);
alert("contents:" + result.contents);

Categories

Resources