local storage not identifying array name - javascript

I am trying to save an array of "items" in the cart. but when it goes on else section an error occur "Uncaught TypeError: Cannot read property 'items' of null" please help what's wrong with the code
var existing_cart = localStorage.getItem("cart");
existing_cart = JSON.parse(existing_cart);
console.log(existing_cart);
if (existing_cart.items instanceof Array) {
existing_cart.items.push({
'article_number': article_no,
'quantity': quantity,
'item_name ': item_name
});
console.log(existing_cart);
localStorage.setItem("cart", JSON.stringify(existing_cart));
} else {
var products = [{
'article_number': article_no,
'quantity': quantity,
'item_name ': item_name
}];
var cart = {
'items': products
}
localStorage.setItem("cart", JSON.stringify(cart));
toastr.success('Have fun storming the castle!', 'Miracle Max Says');
}

The first time you run the code there won't be anything in the local storage, so existing_cart will be null. You need to check for this.
Change
if (existing_cart.items instanceof Array) {
to:
if (existing_cart) {

var existing_cart = localStorage.getItem("cart") || '{"items":[]}';
In the case that it is the first time the code runs, the localStorage may not have the element, in which case it will return null or undefined. In that case you can default it to a JSON that will allow the logic to flow without encountering null pointer exceptions.

Related

Complex JSON obj and jQuery or Javascript map to specific key, value

I am banging my head trying to figure this out. And it should not be this hard. I am obviously missing a step.
I am pulling data from: openaq.org
The object I get back is based on a JSON object.
For now, I am using jQuery to parse the object and I am getting to the sub portion of the object that hold the specific parameter I want but I can't get to the specific key,value pair.
The object does not come back in the same order all the time. So when I tried to originally set up my call I did something like
obj.results.measurements[0].
Well since the obj can come back in an random order, I went back to find the key,value pair again and it was the wrong value, throwing my visual off.
That said, I have looked at use jQuery's find() on JSON object and for some reason can not get what I need from the object I am given by openaq.org.
One version of the object looks like this:
{"meta":{"name":"openaq-api","license":"CC BY 4.0d","website":"https://u50g7n0cbj.execute-api.us-east-1.amazonaws.com/","page":1,"limit":100,"found":1},"results":[{"location":"Metro Lofts","city":null,"country":"US","coordinates":{"latitude":39.731,"longitude":-104.9888},"measurements":[{"parameter":"pm10","value":49.9,"lastUpdated":"2021-08-09T20:49:38+00:00","unit":"µg/m³"},{"parameter":"pm1","value":24,"lastUpdated":"2021-08-09T20:49:38+00:00","unit":"µg/m³"},{"parameter":"um100","value":0,"lastUpdated":"2021-08-09T20:49:38+00:00","unit":"particles/cm³"},{"parameter":"um025","value":0.28,"lastUpdated":"2021-08-09T20:49:38+00:00","unit":"particles/cm³"},{"parameter":"um010","value":4.1,"lastUpdated":"2021-08-09T20:49:38+00:00","unit":"particles/cm³"},{"parameter":"pm25","value":41.1,"lastUpdated":"2021-08-09T20:49:38+00:00","unit":"µg/m³"}]}]}
I am trying to get the "pm25" value.
The code I have tried is this:
function getAirQualityJson(){
$.ajax({
url: 'https://api.openaq.org/v2/latest?coordinates=39.73915,-104.9847',
type: 'GET',
dataType: "json"
// data: data ,
}).done(function(json){
console.log("the json is" + JSON.stringify(json));
console.log("the json internal is" + JSON.stringify(json.results));
var obj = json.results;
var pm25 = "";
//console.log(JSON.stringify(json.results.measurements[0]["parameter"]));
$.each(json.results[0], function(i,items){
//console.log("obj item:" + JSON.stringify(obj[0].measurements));
$.each(obj[0].measurements, function(y,things){
//console.log("each measurement:" + JSON.stringify(obj[0].measurements[0].value));//get each measurement
//pm 2.5
//Can come back in random order, get value from the key "pm25"
// pm25 = JSON.stringify(obj[0].measurements[2].value);
pm25 = JSON.stringify(obj[0].measurements[0].value);
console.log("pm25 is: " + pm25); // not right
});
});
//Trying Grep and map below too. Not working
jQuery.map(obj, function(objThing)
{ console.log("map it 1:" + JSON.stringify(objThing.measurements.parameter));
if(objThing.measurements.parameter === "pm25"){
// return objThing; // or return obj.name, whatever.
console.log("map it:" + objThing);
}else{
console.log("in else for pm25 map");
}
});
jQuery.grep(obj, function(otherObj) {
//return otherObj.parameter === "pm25";
console.log("Grep it" + otherObj.measurements.parameter === "pm25");
});
});
}
getAirQualityJson();
https://jsfiddle.net/7quL0asz/
The loop is running through I as you can see I tried [2] which was the original placement of the 'pm25' value but then it switched up it's spot to the 3rd or 4th spot, so it is unpredictable.
I tried jQuery Grep and Map but it came back undefined or false.
So my question is, how would I parse this to get the 'pm25' key,value. After that, I can get the rest if I need them.
Thank you in advance for all the help.
You can use array#find and optional chaining to do this,
because we are using optional chaining, undefined will be returned if a property is missing.
Demo:
let data = {"meta":{"name":"openaq-api","license":"CC BY 4.0d","website":"https://u50g7n0cbj.execute-api.us-east-1.amazonaws.com/","page":1,"limit":100,"found":1},"results":[{"location":"Metro Lofts","city":null,"country":"US","coordinates":{"latitude":39.731,"longitude":-104.9888},"measurements":[{"parameter":"pm10","value":49.9,"lastUpdated":"2021-08-09T20:49:38+00:00","unit":"µg/m³"},{"parameter":"pm1","value":24,"lastUpdated":"2021-08-09T20:49:38+00:00","unit":"µg/m³"},{"parameter":"um100","value":0,"lastUpdated":"2021-08-09T20:49:38+00:00","unit":"particles/cm³"},{"parameter":"um025","value":0.28,"lastUpdated":"2021-08-09T20:49:38+00:00","unit":"particles/cm³"},{"parameter":"um010","value":4.1,"lastUpdated":"2021-08-09T20:49:38+00:00","unit":"particles/cm³"},{"parameter":"pm25","value":41.1,"lastUpdated":"2021-08-09T20:49:38+00:00","unit":"µg/m³"}]}]}
let found = data?.results?.[0]?.measurements?.find?.(
({ parameter }) => parameter === "pm25"
);
console.log(found);
You can iterate over measurements and find the object you need:
const data = '{"meta":{"name":"openaq-api","license":"CC BY 4.0d","website":"https://u50g7n0cbj.execute-api.us-east-1.amazonaws.com/","page":1,"limit":100,"found":1},"results":[{"location":"Metro Lofts","city":null,"country":"US","coordinates":{"latitude":39.731,"longitude":-104.9888},"measurements":[{"parameter":"pm10","value":49.9,"lastUpdated":"2021-08-09T20:49:38+00:00","unit":"µg/m³"},{"parameter":"pm1","value":24,"lastUpdated":"2021-08-09T20:49:38+00:00","unit":"µg/m³"},{"parameter":"um100","value":0,"lastUpdated":"2021-08-09T20:49:38+00:00","unit":"particles/cm³"},{"parameter":"um025","value":0.28,"lastUpdated":"2021-08-09T20:49:38+00:00","unit":"particles/cm³"},{"parameter":"um010","value":4.1,"lastUpdated":"2021-08-09T20:49:38+00:00","unit":"particles/cm³"},{"parameter":"pm25","value":41.1,"lastUpdated":"2021-08-09T20:49:38+00:00","unit":"µg/m³"}]}]}';
const json = JSON.parse(data);
let value = null;
const measurements = json?.results?.[0]?.measurements ?? null;
if(measurements)
for (const item of measurements)
if (item.parameter === 'pm25') {
value = item.value;
break;
}
if (value) {
// here you can use the value
console.log(value);
}
else {
// here you should handle the case where 'pm25' is not found
}

Array as key and value but value is undefined

I don't know what's wrong with the code. it works fine and both array have data. but i don't understand why the output found undefined from var _city array as it passed data to the city field.
How can I fix this?
var city = {
_country : _city
};
I'm wondering what you read that made you possibly believe that by writing what you did you would magically have an object keyed with one array with values from a second...
Essentially what is happening when you did when you
var city = {
_country : _city
};
is create an object that looks like
var city = {
'_country' : ['your', 'array', 'of', 'cities']
};
that is to say, an object with one key, '_country' mapped to an array of cities.
This explains why you get undefined... city['any string that isn't exactly " _country"'] == undefined
What you want to do is more likely,
var city = _country.reduce(function(acc, cur, idx) { acc[cur] = _city[idx]; return acc; }, {});
It's because _country is already defined above:
var _country = ["Afghanistan","Bahrain","Canada","Denmark","Ethiopia","France","Germany","Hong Kong","India","Japan"];
Change the definition within city to something else (maybe country):
var city = {
country: _city,
};
And it'll work.

Cannot add into an already initialized array

document.getElementById('form').addEventListener('submit', saveItem);
function saveItem(e){
var items= document.getElementById('items').value;
var date= document.getElementById('date').value;
var price= document.getElementById('price').value;
var expense= {
items: items,
date: date,
price: price
}
if(localStorage.getItem('bill')==null){
var bill=[];
bill.push(expense);
localStorage.setItem('bill', JSON.stringify(expense));
} else{
var bill = JSON.parse(localStorage.getItem('bill'));
bill.push(expense);
localStorage.setItem('bill', JSON.stringify(expense));
console.log(bill);
}
e.preventDefault();
}
there is no error if
if(localStorage.getItem('bill')==null)
but there comes error at else as
Uncaught TypeError: Cannot read property 'push' of undefined
at HTMLFormElement.saveItem
the data is stored when the local storage is empty but cannot add data if it is not.
Your expense is a object, you need to save the bill inside the local storage.
if(localStorage.getItem('bill')==null){
var bill=[];
bill.push(expense);
localStorage.setItem('bill', JSON.stringify(bill));
}
Can you please check what is the result of JSON.parse(localStorage.getItem('bill'));? Is its a valid array?

Dynamic Value in json array using Angularjs

So I have an empty array defined.
admin.links = [];
I then push items to it like so.
angular.forEach(links, function(value, key) {
var title = value.title;
var url = value.url;
admin.links.counter.push({
'parent' : counter,
'name' : title,
'url' : url
})
})
When I run the code above I get an error
Cannot read property 'push' of undefined
counter is a dynamic value. How would I do this?
I want it to be something like admin.links.0
What you mean with:
counter is a dynamic value.
admin.linksis an array, so if you want to add items you must use:
admin.links.push
if, instead, you want links to be an object you should initialize it with:
admin.links = {
counter: []
}
admin.links.counter.push()

Saving Object Array to local storage not working

Hello i am trying to create a simple client side cart, in my controller when the page loads i define the array objects that will hold my items, if they are undefined or have a length of 0 i set them to '[]' by default:
$scope.cart = JSON.parse($window.localStorage.getItem('cart')) || [];
$scope.cart.items = $scope.cart.items || [];
This is the function that adds the item to the cart:
$scope.addItem = function(item) {
if (item.quantity > 0)
{
var cartItem = {
id: item.id,
description: item.class + ' item' + (item.quantity > 1 ? 's' : '') + ' to ' + $scope.details.name,
quantity: item.quantity
}
// Adding item to cart array
$scope.cart.items.push(cartItem)
// Saving cart to storage
$window.localStorage.setItem('cart', JSON.stringify($scope.cart));
// Checking to see if data has indeed been stored in localstorage
console.log(JSON.parse($window.localStorage.getItem('cart')));
}
}
Now my cart in storage always turns up as empty, there were times i played around with the code and got it to work(dunno what i did) but when i reloaded the page everything got cleared.
You are initializing cart as array but then assigning properties to it.
It should be an object:
$scope.cart = JSON.parse($window.localStorage.getItem('cart')) || {};
Also before you can push to an array within cart that array needs to be defined.
Simplest might be to have all the properties available in one object first:
var newCart = {
tickets:[],
items:[]
}
$scope.cart = JSON.parse($window.localStorage.getItem('cart')) || newCart ;
You should check if there is already a value stored as
if(!$window.localStorage.getItem('cart'))
{
// Saving cart to storage
$window.localStorage.setItem('cart', JSON.stringify($scope.cart));
}

Categories