JSON parse variable result - javascript

I have a JSON which I query with xhr. The objects (person) contain a key-value pair called "serviceLevel" that I have to split.
When I stack this in a variable (services) and log it like this:
let main = document.getElementsByTagName('main');
getXHR("GET", './db/orga.json', (success) => {
format(success)
}, (error) => {
console.error(error)
});
function format() {
let people = arguments[0];
for (let i in people) {
let person = people[i];
let services = person.serviceLevel.split(".");
console.log(services);
console.log(person.serviceLevel.split("."));
let idCard = document.createElement('div');
idCard.id = person.firstName + person.familyName;
idCard.classList.add('person');
idCard.innerHTML = "<div class=\"item nom\"><span class=\"prenom\">" + person.firstName + "</span><span class=\"famille\">" + person.familyName + "</span></div>";
idCard.innerHTML += "<span class=\"job\">" + person.jobTitle_1 + "</span>";
idCard.innerHTML += "<span class=\"mail\"><a href=\"mailto:" + person.mail + "\">" + person.mail + "</span>";
idCard.innerHTML += "<span class=\"tel\"><a href=\"tel:" + person.phone_1 + "\">" + person.phone_1 + "</span>";
idCard.innerHTML += "<span class=\"tel\"><a href=\"tel:" + person.mobile + "\">" + person.mobile + "</span>";
for (let j in services) {
let serviceElement = document.getElementById(services[j]);
if (!serviceElement) {
let serviceElement = document.createElement('div');
serviceElement.id = services[j];
serviceElement.classList.add('n' + j, "service");
serviceElement.innerHTML = "<span class=\"title\">" + services[j] + "</span>";
if (j == 0) {
if (services[services.length - 1] = j) {
serviceElement.appendChild(idCard);
main[0].appendChild(serviceElement);
}
} else {
let parent = services[j - 1],
parentService = document.getElementById(parent);
if (services[services.length - 1] = j) {
serviceElement.appendChild(idCard);
}
parentService.appendChild(serviceElement);
}
} else {
serviceElement.appendChild(idCard);
}
}
}
}
const data = [{
"Tri": "blablablabla, CSMSI.SAFS, n, XXXX, YYYY",
"Department": "The best department",
"serviceLevel": "CSMSI.SAFS",
"organisationLevel": "blablablabla",
"rang": "n",
"familyName": "XXXX",
"firstName": "YYYY",
"jobTitle_2": "Directeur",
"jobTitle_1": "Directeur",
"phone_1": "nn nn nn nn nn",
"phone_2": "",
"mobile": "nn nn nn nn nn",
"mail": "xxxx.yyyy#zzzz.fr",
"location": "france"
}];
format(data);
The results are different:
(2) ["CSMSI", "SAFS"]
0: "CSMSI"
1: "SAFS"
length: 2
(2) ["CSMSI", "SAFS"]
0: "CSMSI"
1: "1"
length: 2
As we can see, content of "services" are good, but when I extend the tree, the value of the second key value is "1" ... which is a problem. Is there a way to change this?

when I use a for loop with "classical" (i = 0; i < people.length; i++), i don't have the problem....

Related

Basic JavaScript - How to randomly compare two properties from an array of objects

I have an exercise where from an object constructor, I have created several objects, all with an ID property.
The first part of the exercise consist in pairing each object, compare their markAv properties and print the one that had it bigger.
[ a vs b => b wins]
They suggested to do so by using the ID property but I didn't know how to do it that way... so I tried a workaround, as you will see in the code below.
However, the second part of the exercise wants me to do the same but, this time, creating the pairs randomly. Here I have tried to use the ID property by generating a random number that matches the ID but I don´t know how to structure the code for it to work.
The output for the second part should be the same as above, with the only difference that the pairing is now randomly generated.
I have added a partial solution for the second part, partial because from time to time it throws an error that I can´t identify. However, I think I'm getting close to get my desired output.
I would really appreciate if anyone could give me a hint for me to crack the code below and to get it working because I really want to understand how to do this.
class Avenger {
constructor(name, classRoom, city, job, studies, markAv, id) {
this.name = name;
this.classRoom = classRoom;
this.city = city;
this.job = job;
this.studies = studies;
this.markAv = markAv;
this.id = id;
}
heroList() {
return this.name + " " + this.classRoom + " " + this.city + " " + this.job + " " + this.studies + " " + this.markAv + " " + this.id
}
}
const tonyStark = new Avenger("Tony Stark", "XI", "NYC", "Ingeneer", "MIT", 10, 1)
const hulk = new Avenger("Hulk", "X", "Toledo", "Destroyer", "Scientific", 7, 2)
const daredevil = new Avenger("Daredevil", "IX", "NYC", "Lawyer", "Fighter", 2, 3)
const magneto = new Avenger("Magneto", "XXI", "SBD", "Unemployed", "Driver", 5, 4)
const unknown = new Avenger("Unknown", "L", "CDY", "President", "Clerck", 17, 5)
const xavi = new Avenger("Xavi", "XX", "BCN", "Analist", "Calle", 7, 6)
let heroes = [daredevil, hulk, tonyStark, magneto, unknown, xavi]
function getPairs(array) {
function getPairs(array) {
for (let i = 0; i < array.length; i += 2) {
if (array[i].markAv < array[i + 1].markAv) {
console.log(array[i].name + " vs " + array[i + 1].name + " " + array[i + 1].name + " Wins")
} else if (array[i].markAv > array[i + 1].markAv) {
console.log(array[i].name + " vs " + array[i + 1].name + " " + array[i].name + " Wins")
}
}
}
getPairs(heroes)
///
function randomAv(array) {
let result = []
let hero1 = heroes[Math.floor(Math.random() * 6) + 1]
for(let i = 0; i<array.length; i++){
if (array[i].markAv <= hero1.markAv && array[i].id != hero1.id) {
result.push(console.log(array[i].name + " vs " + hero1.name + " " + array[i].name + " Wins"))
} else if(array[i].markAv >= hero1.markAv && array[i].id != hero1.id) {
result.push(console.log(array[i].name + " vs " + hero1.name + " " + hero1.name + " Wins"))
}
}
console.log(result)
}
First shuffle the array:
let heroes = [daredevil, hulk, tonyStark, magneto, unknown, xavi]
let heroes_shuffle = heroes.sort((a, b) => 0.5 - Math.random())
Then do as normal
getPairs(heroes_shuffle )
All Possible Combination :
function allPairs(heroes) {
while (heroes) {
[hero, ...heroes] = heroes
for (enemy of heroes) {
if (hero.markAv === enemy.markAv)
console.log(hero.name + " vs " + enemy.name + ": draw")
else if (hero.markAv < enemy.markAv)
console.log(hero.name + " vs " + enemy.name + ": " + enemy.name + " Wins")
else
console.log(hero.name + " vs " + enemy.name + ": " + hero.name + " Wins")
}
}
}
You can take the function from here https://stackoverflow.com/a/7228322/1117736
And do something like this:
class Avenger {
constructor(name, classRoom, city, job, studies, markAv, id) {
this.name = name;
this.classRoom = classRoom;
this.city = city;
this.job = job;
this.studies = studies;
this.markAv = markAv;
this.id = id;
}
heroList() {
return this.name + " " + this.classRoom + " " + this.city + " " + this.job + " " + this.studies + " " + this.markAv + " " + this.id
}
}
const tonyStark = new Avenger("Tony Stark", "XI", "NYC", "Ingeneer", "MIT", 10, 1)
const hulk = new Avenger("Hulk", "X", "Toledo", "Destroyer", "Scientific", 7, 2)
const daredevil = new Avenger("Daredevil", "IX", "NYC", "Lawyer", "Fighter", 2, 3)
const magneto = new Avenger("Magneto", "XXI", "SBD", "Unemployed", "Driver", 5, 4)
const unknown = new Avenger("Unknown", "L", "CDY", "President", "Clerck", 17, 5)
const xavi = new Avenger("Xavi", "XX", "BCN", "Analist", "Calle", 7, 6)
let heroes = [daredevil, hulk, tonyStark, magneto, unknown, xavi]
function randomIntFromInterval(min, max) { // min and max included
return Math.floor(Math.random() * (max - min + 1) + min)
}
let hero1 = heroes[randomIntFromInterval(1, 6)]
let hero2 = heroes[randomIntFromInterval(1, 6)]
if (hero1.markAv < hero2.markAv) {
console.log(hero1.name + " vs " + hero2.name + " " + hero1.name + " Wins")
} else if(hero1.markAv > hero2.markAv) {
console.log(hero1.name + " vs " + hero2.name + " " + hero2.name + " Wins")
}

Looping over JavaScript object and adding string to end if not the last item

{
field_country: ["England", "Netherlands", "India", "Italy"],
field_continent: ["Europe"],
field_group: ["Building", "People", "Landscape"
}
I want to loop over each item and return the key and the array together with ending 'OR' for example:
field_country: "England" OR field_country: "Netherlands"
The last item should not end with 'OR' in the loop. I am not sure what the best process is for this using vanilla JS. So far my code is as follows:
Object.keys(facets).forEach(function(facetKey) {
if (facets[facetKey].length > 1) {
facetResults = facets[facetKey];
for (var i = 0; i < facetResults.length; i ++) {
if (i == 1) {
filter = "'" + facetKey + "'" + ":'" + facetResults[i] + " OR";
return filter;
} else {
filter = "'" + facetKey + "'" + ":'" + facetResults[i];
}
}
} else {
filter = "'" + facetKey + "'" + ": " + facets[facetKey] + "'";
return filter;
}
});
I would be very grateful for any assistance.
Thanks in advance.
You can do something like this with Object.entries and Array.reduce if you would like to get the final result in the form of an object:
const data = { field_country: ["England", "Netherlands", "India", "Italy"], field_continent: ["Europe"], field_group: ["Building", "People", "Landscape"] }
const result = Object.entries(data).reduce((r, [k, v]) => {
r[k] = v.join(' OR ')
return r
}, {})
console.log(result)
It is somewhat unclear what is the final format you need to result in but that should help you to get the idea. If ES6 is not an option you can convert this to:
const result = Object.entries(data).reduce(function(r, [k, v]) {
r[k] = v.join(' OR ')
return r
}, {})
So there are is no arrow function etc.
The idea is to get the arrays into the arrays of strings and use the Array.join to do the "replacement" for you via join(' OR ')
Here's the idea. In your code you are appending " or " at the end of your strings starting at index 0. I suggest you append it at the the beginning starting at index 1.
var somewords = ["ORANGE", "GREEN", "BLUE", "WHITE" ];
var retval = somewords[0];
for(var i = 1; i< somewords.length; i++)
{
retval += " or " + somewords[i];
}
console.log(retval);
//result is: ORANGE or GREEN or BLUE or WHITE
Your conditional expression if (i == 1) would only trigger on the second iteration of the loop since i will only equal 1 one time.
Try something like:
if (i < (facetResults.length - 1)) {
// only add OR if this isn't the last element of the array
filter = "'" + facetKey + "'" + ":'" + facetResults[i] + " OR";
return filter;
}
Here's your updated code:
Object.keys(facets).forEach(function(facetKey) {
if (facets[facetKey].length > 1) {
facetResults = facets[facetKey];
for (var i = 0; i < facetResults.length; i ++) {
if (i < (facetResults.length - 1)) {
filter = "'" + facetKey + "'" + ":'" + facetResults[i] + " OR";
return filter;
} else {
filter = "'" + facetKey + "'" + ":'" + facetResults[i];
}
}
} else {
filter = "'" + facetKey + "'" + ": " + facets[facetKey] + "'";
return filter;
}
});

Trace on nested objects couchdb update handler

i need to edit nested objects with unique key's! in couhdb document, but i can't do it.
my doc structure:
{
"_id":"20",
"_rev":"rev",
tasks": {
"20.t01": {
"name": "test",
"status": [],
"tasks": {
"20.t01t01": {
"status": [
],
"name": "name",
"tasks": {
"20.t01t01t01": {
"status": [],
"name": "name",
"tasks": {
"20.t01t01t01t01": {
"name": "name",
"status": [],
"tasks": {
}
}
}
}
}
}
}
}
}
}
I nedd to push some objects into status array's.
The update handler function:
"status": function(doc, req) {
var data = JSON.parse(req.body);
var value = data.value;
var path = data.path;
var message = 'set ' + path + ' status ' + value;
var pathar = path.split(".");
var level;
var body = doc;
var evalstr = "body.";
if (pathar[1].length > 2) {
level = (pathar[1].length) / 3;
for (var i = 1; i <= level - 1; i++) {
evalstr += "tasks[\"" + pathar[0] + "." + pathar[1].substring(0, i * 3) + "\"].";
}
evalstr += "tasks[\"" + pathar[0] + "." + pathar[1] + "\"].status.push(" + JSON.stringify(value) + ");";
} else {
level = 1;
evalstr += "tasks[\"" + pathar[0] + "." + pathar[1] + "\"].status.push(" + JSON.stringify(value) + ");";
}
eval([evalstr]);
doc = body;
//doc.tasks["20.t01"].tasks["20.t01t01"].status.push(value);
return [doc, JSON.stringify({
reg: evalstr,
doc: body
})];
}
how i write the design document update function for this structure in couchdb?
Tanks!

Javascript object returns undefined

var movies =
[
{name: "In Bruges", rating:"4.7", seen:false},
{name: "Frozen", rating: "4.5", seen:true},
{name: "Lion King", rating:"5", seen:true},
]
for (var i = 0; i < movies.length; i++) {
var result = "You have ";
if(movies.seen === true){
result += "watched ";
}
else{
result += "not seen ";
}
result += "\"" + movies.name + "\" - ";
result += movies.rating + " stars"
console.log(result)
};
You have not seen "undefined" - undefined stars is the result in chrome however you should see You have seen/not seen "movie name" - "rating" stars.
I need to use for loop to print out what each movie I have watched and rating and if I have seen it or not. Question is why is it undefined? Should the code see movies.rating and just substitute the value there? Can some one check my code and help me with my for loop?
movies is an array movies.seen won't work use movies[i].seen and like wise for other properties
Change movies.seen, movies.rating and movies.name to movies[i].seen, movies[i].rating, and movies[i].name.
Use index to access item of array; e.g. movies[i]:
for (var i = 0; i < movies.length; i++) {
var result = "You have ";
if(movies[i].seen === true){
result += "watched ";
}
else{
result += "not seen ";
}
result += "\"" + movies[i].name + "\" - ";
result += movies[i].rating + " stars"
console.log(result)
}
Or you could store the array item in a variable and use it like this:
for (var i = 0; i < movies.length; i++) {
var movie = movies[i];
var result = "You have ";
if (movie.seen) {
result += "watched ";
}
else {
result += "not seen ";
}
result += '"' + movie.name + '" - ';
result += movie.rating + " stars";
console.log(result);
}
Here is a working Plunker for you to see it working. :)
var movies =
[
{name: "In Bruges", rating:"4.7", seen:false},
{name: "Frozen", rating: "4.5", seen:true},
{name: "Lion King", rating:"5", seen:true},
]
for (var i = 0; i < movies.length; i++) {
var result = "You have ";
if(movies[i].seen === true){
result += "watched ";
}
else{
result += "not seen ";
}
result += "\"" + movies[i].name + "\" - ";
result += movies[i].rating + " stars"
alert(result)
}
You were trying to access properties of movies called seem, name and rating, but movies has 3 objects indexed from 0 to 2.
You are using movies inside loop and movies do not contain those properties.
And it is allways safe to use forEach loop while iterating arrays
Do something like
movies.forEach(function(movie){
var result = "You have ";
if(movie.seen === true){
result += "watched ";
}
else{
result += "not seen ";
}
result += movie.name + " - ";
result += movie.rating + " stars";
console.log(result);
});
I suggest to use a little other approach to iterate over the array and for the check if a movie has been seen.
var movies = [
{ name: "In Bruges", rating: "4.7", seen: false },
{ name: "Frozen", rating: "4.5", seen: true },
{ name: "Lion King", rating: "5", seen: true },
];
movies.forEach(function (movie) {
var result = "You have ";
result += movie.seen ? "watched " : "not seen ";
result += "\"" + movie.name + "\" - ";
result += movie.rating + " stars"
document.write(result + '<br>');
});

eBay API -- can't print buyItNowPrice using Javascript

I'm trying to build a simple site that will check and print out "Buy It Now Prices" for cars. I can't get the JavaScript push function to print out anything but strings.
The eBay API says that buyItNowPrice returns an Amount.
I have experimented with the other Item functions, and the only ones that are working for me are ones that return a String.
The question is, how should the line var itemPrice = item.buyItNowPrice; be formatted to output a number?
function _cb_findItemsByKeywords(root) {
var items = root.findItemsByKeywordsResponse[0].searchResult[0].item || [];
var html = [];
html.push('<table width="100%" border="0" cellspacing="0" cellpadding="3"><tbody>');
for (var i = 0; i < items.length; ++i) {
var item = items[i];
var title = item.title;
var pic = item.galleryURL;
var viewitem = item.viewItemURL;
var itemPrice = item.buyItNowPrice;
var timeLeft = item.watchCount;
if (title != null && null != viewitem) {
html.push('<tr><td>' + '<img src="' + pic + '" border="1">' + '</td>' +
'<td><a href="' + viewitem + '" target="_blank">' +
title + '</a>' // end hyperlink
+
'<br>Item Price: ' + itemPrice +
'<br>Time Remaining: ' + timeLeft +
'</td></tr>');
}
}
html.push('</tbody></table>');
document.getElementById("results").innerHTML = html.join("");
}
// Create a JavaScript array of the item filters you want to use in your request
var filterarray = [{
"name": "MaxPrice",
"value": "250000",
"paramName": "Currency",
"paramValue": "USD"
},
{
"name": "MinPrice",
"value": "15000",
"paramName": "Currency",
"paramValue": "USD"
},
//{"name":"FreeShippingOnly", "value":"false", "paramName":"", "paramValue":""},
{
"name": "ListingType",
"value": ["AuctionWithBIN", "FixedPrice", /*"StoreInventory"*/ ],
"paramName": "",
"paramValue": ""
},
];
// Generates an indexed URL snippet from the array of item filters
var urlfilter = "";
function buildURLArray() {
for (var i = 0; i < filterarray.length; i++) {
var itemfilter = filterarray[i];
for (var index in itemfilter) {
// Check to see if the paramter has a value (some don't)
if (itemfilter[index] !== "") {
if (itemfilter[index] instanceof Array) {
for (var r = 0; r < itemfilter[index].length; r++) {
var value = itemfilter[index][r];
urlfilter += "&itemFilter\(" + i + "\)." + index + "\(" + r + "\)=" + value;
}
} else {
urlfilter += "&itemFilter\(" + i + "\)." + index + "=" + itemfilter[index];
}
}
}
}
}
buildURLArray(filterarray);
// Construct the request
var url = "http://svcs.ebay.com/services/search/FindingService/v1";
url += "?OPERATION-NAME=findItemsByKeywords";
url += "&SERVICE-VERSION=1.0.0";
url += "&SECURITY-APPNAME=REDACTED";
url += "&GLOBAL-ID=EBAY-MOTOR";
url += "&RESPONSE-DATA-FORMAT=JSON";
url += "&callback=_cb_findItemsByKeywords";
url += "&REST-PAYLOAD";
//url += "&categoryId=6001";
url += "&keywords=Ferrari 575";
url += "&paginationInput.entriesPerPage=12";
url += urlfilter;
// Submit the request
s = document.createElement('script'); // create script element
s.src = url;
document.body.appendChild(s);
You are reading the wrong eBay documentation. FindItemsByKeywords is part of the Finding API service. The buyItNowPrice field is found in the item.listingInfo field. Changing the code to the following will output the price.
var itemPrice = '---';
// buyItNowPrice may not be returned for all results.
if(item.listingInfo[0].buyItNowPrice) {
itemPrice = item.listingInfo[0].buyItNowPrice[0]['#currencyId'] + ' ' + item.listingInfo[0].buyItNowPrice[0].__value__;
} else if(item.sellingStatus[0].currentPrice) {
itemPrice = item.sellingStatus[0].currentPrice[0]['#currencyId'] + ' ' + item.sellingStatus[0].currentPrice[0].__value__;
}

Categories

Resources