Accessing data in a multidimensional JSON array with jQuery - javascript

I am trying to work out how to access data in an essentially multidimensional JSON array.
My jQuery AJAX request looks like this:
$("#login-form").submit(function(e) {
e.preventDefault();
$.ajax({
type: 'POST',
url: '/ajax/login',
data: 'email='+$("#email").val()+'&password='+$("#password").val(),
success: function(data){
// FIRE ALERT HERE
alert(data.firstname);
},
dataType: 'json'
});
});
This is what i am getting back. User account details, plus a list of products they have against their account.
{
"logged_in":true,
"firstname":"Joe",
"surname":"Bloggs",
"Full_name":"Joe Bloggs",
"email":"email#website.com",
"phone":"+123456789",
"website":"",
"age":"26-35",
"street":"1 Street Ave",
"city":"Townland",
"state":"NA",
"postcode":"1234",
"country":"Australia",
"products":2,
"0":{
"product_no":"1087",
"customer":"2",
"bought_from":"1",
"date_of_purchase":"2011-04-08",
"method":"instore",
"invoice":"0",
"current":"1"
},
"1":{
"product_no":"24",
"customer":"2",
"bought_from":"1",
"date_of_purchase":"2011-04-08",
"method":"instore",
"invoice":"0",
"current":"1"
}
}
As you can see, i am alerting the first name, which is fine. I can access everything in the first dimension by using data.key but i'm not sure how then i need to index the next dimension. Obviously I would like to display each of the products somehow.
Suggestions would be most welcome.

Inside your success function you can treat the JSON data as a JavaScript object. You can access the product array and objects inside it like this:
console.log(data.products + " product(s) in data"); // data.products is 2 (integer)
for(var i = 0; i < data.products; i++) { //
var product = data[i.toString()]; // 0.toString() is "0"
// data["0"] is what you want
// now product points to the property "0"
console.log(product.product_no); // so you can use product.xxx
// or product["xxx"]
} // likewise for "1", "2", "3" and so on
Replace console.log with alert if you do not know what console is.

Each of the product details can be accessed through data[iProductIndex.toString()] member. Data is stored inside data["0"] and data["1"], therefore to access them you need to convert integer value to string. Unfortunately you won't be able to use $.each loop because "0" and "1" are separate member objects. Use for loop with iProductIndex.

Data supplied does not allow for your answer, Salman A. See JSON Arrays for array definition, to have it work your way it must've been defined as
{"products" : [ {"product_no":"1087",
"customer":"2",
"bought_from":"1",
"date_of_purchase":"2011-04-08",
"method":"instore",
"invoice":"0",
"current":"1"} ] }
To OP:
alert(data["0"].product_no);
alert(data["1"]["date_of_purchase"]);

try this
<script type="text/javascript">
var json_string={
"logged_in":true,
"firstname":"Joe",
"surname":"Bloggs",
"Full_name":"Joe Bloggs",
"email":"email#website.com",
"phone":"+123456789",
"website":"",
"age":"26-35",
"street":"1 Street Ave",
"city":"Townland",
"state":"NA",
"postcode":"1234",
"country":"Australia",
"products":2,
"0":{
"product_no":"1087",
"customer":"2",
"bought_from":"1",
"date_of_purchase":"2011-04-08",
"method":"instore",
"invoice":"0",
"current":"1"
},
"1":{
"product_no":"24",
"customer":"2",
"bought_from":"1",
"date_of_purchase":"2011-04-08",
"method":"instore",
"invoice":"0",
"current":"1"
}
};
for (key in json_string) {
// Most modern browsers should have hasOwnProperty by now.
// This keeps us from getting farther up the chain.
if (json_string.hasOwnProperty(key)) {
document.write(key + "->" + json_string[key]);
document.write("<br>");
}
};
var pro_1= json_string[0]; // here u change 0 with 1 and get the data of "1"
for (key in pro_1) {
if (pro_1.hasOwnProperty(key)) {
document.write(key + "->" + pro_1[key]);
document.write("<br>");
}
};
</script>

Related

Javascript (Ajax) Parse JSON value

total javascript noob here. Just trying to get an understanding for the language.
I'm requesting a JSON request using the following code:
function request(){
$.ajax({
dataType: "jsonp",
type: 'GET',
url: "getWebsite",
success: function(result){
data = result;
$('.data').text(data);
console.log(data);
}});
The get request returns something like this:
"items": [
{
"topLevelComment": {
"authorDisplayName": "a"
"textDisplay": "b"
},
{
"topLevelComment": {
"authorDisplayName": "c"
"textDisplay": "d"
}
I would like to cycle through the AuthorDisplayName and textDisplay and randomly pick one from each. The best way to do this would probably be to put them both into arrays if I had to guess. I'm not sure how to even go about this.
var json={
"items": [{
"topLevelComment": {
"authorDisplayName": "a",
"textDisplay": "b"
}
}, {
"topLevelComment": {
"authorDisplayName": "c",
"textDisplay": "d"
}
}, {
"topLevelComment": {
"authorDisplayName": "e",
"textDisplay": "f"
}
}, {
"topLevelComment": {
"authorDisplayName": "g",
"textDisplay": "h"
}
}]
};
$("input:button").on("click",function(){
selectRand = Math.floor((Math.random() * json.items.length))
var r=json.items[selectRand].topLevelComment.textDisplay;
console.log(r);
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<input type="button" value="selectRand"/>
If your data is already in Object format, and you only want to get one from random pick. Then you don't have to loop for all the data. Just randomly select one index from your total data.
function request(){
$.ajax({
dataType: "jsonp",
type: 'GET',
url: "getWebsite",
success: function(result){
data = result;
$('.data').text(data);
console.log(data);
var randomIndex = Math.floor((Math.random() * data.items.length));
console.log("Selected data authorDisplayName: " + data.items[randomIndex].topLevelComment.authorDisplayName);
console.log("Selected data textDisplay: " + data.items[randomIndex].topLevelComment.textDisplay);
}
});
}
items is already an array. So you do the following:
Parse the result to json (Only if a string is returned)
items = JSON.parse(items)
Get a random index
let index = Math.floor((Math.random() * items.length))
Get the random data
let authorDisplayName = items[index].topLevelComment.authorDisplayName
let textDisplay = items[index].topLevelComment.textDisplay
As far as i understood you are trying to display a random object from the items array?
The items variable is already an array, so you don't need to create one. To get a random element of the array you can use the following code:
var item = result.items[Math.floor(Math.random()*items.length)];
I'm not sure where exactly the items array is located, let's say it's on the root of the result. You will probably also need to run the array through the method JSON.parse() to make it a valid JavaScript object.
And then to get the text and display name you can do this:
var authour = item.topLevelComment.authorDisplayName;
var text = item.topLevelComment.textDisplay;

how to build json array dynamically in javascript

I receive a json object with some number of quick reply elements from wit.ai, like this:
"msg": "So glad to have you back. What do you want me to do?
"action_id": "6fd7f2bd-db67-46d2-8742-ec160d9261c1",
"confidence": 0.08098269709064443,
"quickreplies": [
"News?",
"Subscribe?",
"Contribute?",
"Organize?"
],
"type": "msg"
I then need to convert them to a slightly different format as they are passed to FaceBook Messenger as described in the code below. Wit only exposes 'msg' and 'quickreplies.' Can you suggest a good way to do this? It goes after "console.log(element)" as far as I understand.
if (quickreplies){
// got simple array of quickreplies
// need to format quickreplies for FB:
// "quick_replies":[
// {
// "content_type":"text",
// "title":"Red",
// "payload":"DEVELOPER_DEFINED_PAYLOAD_FOR_PICKING_RED"
// },
// {
// "content_type":"text",
// "title":"Green",
// "payload":"DEVELOPER_DEFINED_PAYLOAD_FOR_PICKING_GREEN"
// }
console.log('we got quickreplies, here they are:');
var quick_replies = []; // ??
quickreplies.forEach(function(element) {
console.log(element)
});
}
else (console.log('no quickreplies'));
In the above example, the end result should be this:
"recipient":{
"id":"USER_ID"
},
"message":{
"text":"Pick a color:",
"quick_replies":[
{
"content_type":"text",
"title":"Red",
"payload":"DEVELOPER_DEFINED_PAYLOAD_FOR_PICKING_RED"
},
{
"content_type":"text",
"title":"Green",
"payload":"DEVELOPER_DEFINED_PAYLOAD_FOR_PICKING_GREEN"
}
]
}
I am not sure if this has been a course of confusion, but there is no such thing as a "JSON object". One works with data objects returned by JSON.parse in the same manner as working with any other object. Before sending to FB, of course, data objects have to be converted into JSON string format using JSON.stringify. This might occur automatically in some code libraries depending on how the data is sent.
Here's an example of preparing a quick-replies array - I simply chose an example structure for the payload and went with it. The quick_replies array is still an object and has not been converted to a JSON string.
Edit the format of a text only payload, shown in the first text only example for quick replies indicates the payload is a string. The code below had been updated to meet with this requirement.
// test values for quickreplies:
var quickreplies= [ "News?", "Subscribe?", "Contribute?", "Organize?" ];
/********
convert quickreplies to quick_replies array
using an example payload of:
{ "text" : "text string", // button text
"index" : index, // index into quickreply for button
"other": "tbd" // anything else needed in a reply
}
*********/
var quick_replies;
if (quickreplies) {
console.log('we got quickreplies, here they are:');
quick_replies = quickreplies.map( function(element, index) {
var payload = {
text: element,
index: index,
other: "tbd" // example value only.
};
var payloadString = JSON.stringify( payload);
console.log(element);
var quick_reply = {
content_type: "text",
title: element,
payload: payloadString
};
console.log("** converted to : " + JSON.stringify(quick_reply));
});
quickreplies=null; // housekeeping
}
else {
console.log('no quickreplies');
quick_replies = undefined; // or [] ?
}

Convert JSON to HTML: Uncaught TypeError: json.forEach is not a function

I want to convert JSON to HTML to display it on website. I've googled, and this error occurs when when json is a string, and first I need to parse. But when I use JSON.parse, the console says it is already an object (Unexpected token o in JSON at position 1).
$(document).ready(function() {
$("#getMessage").on("click", function() {  
$.getJSON("http://quotes.rest/qod.json", function(json) {
var html = "";
json.forEach(function(val) {
var keys = Object.keys(val);
html += "<div class = 'blabla'>";
keys.forEach(function(key) {
html += "<b>" + key + "</b>: " + val[key] + "<br>";
});
html += "</div><br>";
});
$(".message").html(html);
});
});
});
json is an object, not an array. You can use forEach only on arrays.
As you have done already, you can iterate over the object's keys like this:
Object.keys(json).forEach(function(key) {
var value = json[key];
...
});
In addition to what everyone else said, it appears that the JSON response does not look like you think it does.
var json = {
"success": {
"total": 1
},
"contents": {
"quotes": [{
"quote": "It's not whether you get knocked down, it...s whether you get up.",
"length": "65",
"author": "Vince Lombardi",
"tags": [
"failure",
"inspire",
"learning-from-failure"
],
"category": "inspire",
"date": "2016-08-09",
"title": "Inspiring Quote of the day",
"background": "https://theysaidso.com/img/bgs/man_on_the_mountain.jpg",
"id": "06Qdox8w6U3U1CGlLqRwFAeF"
}]
}
};
var messageEl = document.querySelector('.message');
messageEl.innerText = json.contents.quotes[0].quote;
<div class="message"></div>
$.getJson already transforms a JSON object into a javascript object, so you would not need to parse it again.
However, your problem starts with forEach, which is an Array method, not an Object method, therefor it will not work in your use case.
var jsonKeys = Object.keys(json); jsonKeys.forEach(...) will work, as Object.keys returns an array of Object keys.

How to separate a JSON.stringify result

Related Retrieve two lists, sort and compare values, then display all the results
The question in the related post was how to combine two lists and sort them. The code referenced each item on each list. So, when I got the result, I could manipulate it.
The best solution used console.log(JSON.stringify(result,null,2)); to return the result, nicely combined and sorted.
Trouble for me is being able to translate that back into something I can work with. I can get the result into a variable and display it on the page, but it's the raw output : [ { "Title": "apple", "Type": "rome", "State": null }, ...
Have tried 'JSON.parse(result);' where result is the variable that is used to handle the combination and sorting of the two lists. All that gives is an invalid character error on the line. Also looked at the 'replace' option. That just confused me, tmi. Tried setting a variable directly on the result (so those who know are laughing) 'var foo = result;' That returns object, object.
The desired end result would be to end up with each item separate so I can put them in a table (or a list) on my html page with blanks in any column where there is no data.
I know there has to be a simple, easy way to do this without 200 lines of transformation code. But I can't find a clear example. Everything I'm seeing is for +experts or uses a super simple array that's typed into the code.
Is there a way to attach something like this (from my original) to the result instead of using JSON.stringify? What other step(s) am I missing in being able to extract the fields from JSON.stringify using JSON.parse?
}).success(function (data) {
var title = '';
var type = '';
$.each(data.d.results,
function (key, value) {
title += "Title: " + value.Title + "<br/>";
type += "Type: " + value.Type + "<br/>";
});
$("#tdtitle").html(title);
$("#tdtype").html(type);
Terry, you wrote: "All that gives is an invalid character error on the line"? Then result is not a valid json. Test it here: http://jsonlint.com/, fix it, then try again.
var data = {
d:{
results: [
{ "Title": "apple", "Type": "rome", "State": null },
{ "Title": "grape", "Type": "fruit", "State": null }
]
}
};
var title = '';
var type = '';
$.each(data.d.results, function (index, value) {
title += "Title: " + value.Title + "<br/>";
type += "Type: " + value.Type + "<br/>";
});
alert(title + type);
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>

Change DIV color background depending on MIN and MAX array values?

In brief explanation, I am retrieving values from an array by using an AJAX call. Green to Red colors background will be displayed depending on the number "aht_value". The colors are being displayed correctly because I manually putted the values in the calculation below. That being said, in my "function conv(x)" I want the values to be dynamic.
Theres 3 things that I am trying to achieve in my code but can't get it to work. So, here is my fiddle for better understanding
Fetch MIN and MAX value from the array in "aht_value". For later use in the conv(x) function.
If aht_value is equal to "NA" display a white background.
Make the values not surpass the little squares.. how can I center them so the number doesnt overlap?
and here is an array example being retrieved from my "show_aht.php".
Array:
[
{
"username":"OXGOR",
"aht_value":"241",
"station":"B20"
}
{
"username":"AISAI2",
"aht_value":"199",
"station":"B21"
},
{
"username":"CAPAP3",
"aht_value":"NA",
"station":"B10"
}
]
AJAX call:
<script type="text/javascript">
$(document).ready(function() {
$('#aht').click(function(){
$.ajax({
type:"GET",
url : "show_aht.php",
data:{ } , // do I need to pass data if im GET ting?
dataType: 'json',
success : function(data){
//going through all DIVs only once with this loop
for(var i = 0; i < data.length; i++) { // loop over results
var divForResult = $('#desk_' + data[i]['station']); // look for div for this object
if(divForResult.length) { // if a div was found
Here I output the background color and aht_value
divForResult.html(data[i]['aht_value']).css("background-color", colorMe(data[i]['aht_value']));
}//end if
}//end for
}//end success
});//end ajax
});//end click
});//end rdy
//function for background color
function colorMe(v){
return "rgb(" + conv(v) + "," + (255-conv(v)) + ",0)";
}
here I want to check the lowest value from the array and highest to make the calculation
I added 1800 as t he highest and 100 as the lowest but I want it to be the values from the array
//function for calculation of background color depending on aht value
function conv(x){
return Math.floor((x - 100) / (1800-100) * 255);
}
</script>
your json file is not valid.
Ajax calls are using strict method, so if the json is not valid it will not get to your success function.
try debugging the json file here first: http://jsonlint.com/
try using this json (fixed):
[
{
"username": "OXGOR",
"aht_value": "241",
"station": "B20"
},
{
"username": "AISAI2",
"aht_value": "199",
"station": "B21"
},
{
"username": "CAPAP3",
"aht_value": "NA",
"station": "B10"
}
]

Categories

Resources