This question already has answers here:
How to iterate over a JavaScript object?
(19 answers)
Closed 1 year ago.
I'm having trouble to iterate over JSON file and get his parameters, this is an example of JSON file i created:
{
"One": { "Username": "", "Password": "", "unique3": "", "unique4": "", "unique5": "", "freeTextArea": "" },
"Two": { "Username": "", "Password": "", "SecretKey":"", "Autologinurl":"", "CrmUid":"", "freeTextArea":"" },
"Three": { "Username": "", "Password": "", "freeTextArea": "" }
}
I have this HTML input attribute:
<input type="text" name="platform" placeholder="Platform" id="platform"/>
What I want is to check if the Input is matching "one"/"two"/"three" from the JSON, and then create new input elements using DOM based on the parameters "one"/"two"/"three" have.
This is how I'm getting the JSON data using AJAX:
var platformJson = $.getJSON("platform.json");
How can I iterate correctly over this JSON file?
Get value of #platform input using .val()
Search for this value in data object and get the target
If the latter exists, iterate over it using $.each and append a new input to #platformForm using .append
const data = {
"One": { "Username": "1", "Password": "1", "AffiliateID": "1", "GI": "1", "CI": "1", "freeTextArea": "1" },
"Two": { "Username": "2", "Password": "2", "SecretKey":"2", "Autologinurl":"2", "CrmUid":"2", "freeTextArea":"2" },
"Three": { "Username": "3", "Password": "3", "freeTextArea": "3" }
};
const platform = $('#platform').val();
const props = data[platform];
if (props) {
$.each(props, function(prop, value) {
$('#platformForm').append(
`<input id="${prop}" value="${value}" />`
);
});
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<form id="platformForm">
<input type="text" name="platform" placeholder="Platform" id="platform" value="One"/>
</form>
You could try
$.getJSON('https://jsonplaceholder.typicode.com/todos/1', function (data) {
$.each(data, function (key, val) {
console.log(key);
});
});
Basically you need to provide a callback to the getJSON() method, which will be run with the JSON that you got back.
Then you should iterate via $.each() which will restructure and give you the key and value of the JSON.
Then you could manipulate and do what you need to do.
You don't need to "iterate" access the value from a JavaScript object by key. You can do the following:
const response = {
"One": {
"Username": "one",
"Password": "",
"AffiliateID": "",
"GI": "",
"CI": "",
"freeTextArea": ""
},
"Two": {
"Username": "",
"Password": "",
"SecretKey": "",
"Autologinurl": "",
"CrmUid": "",
"freeTextArea": "",
},
"Three": {
"Username": "",
"Password": "",
"freeTextArea": ""
}
}
const inputValue = $('#platform').val();
const keys = Object.keys(response);
console.log(keys.includes(inputValue));
const obj = response[inputValue];
console.log(obj);
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<input type="text" name="platform" placeholder="Platform" id="platform" value="One" />
I recommend using lowerCase keys for your JSON, so that it'll be easier for you to match throughout the application.
Related
I'm trying to build a custom connector on GDS for an external API.
I've configured the schema with all the fields coming from the API and I can see that correctly when I deploy and try the connector. However when I try to run the "Explore" I get a generic "Data Set Configuration Error - Data Studio cannot connect to your data set". I am passing an array of key value pairs as requested... so not sure what's going on.
This is the code I am using in the getData function
function getData(request) {
try {
request.configParams = validateConfig(request.configParams);
var requestedFields = getFields().forIds(
request.fields.map(function(field) {
return field.name;
})
);
var data = JSON.parse(jsonSample).Table
return {
schema: requestedFields.build(),
rows: data
};
}
catch (e) {
cc.newUserError()
.setDebugText('Error fetching data from API. Exception details: ' + e)
.setText(
'The connector has encountered an unrecoverable error. Please try again later, or file an issue if this error persists.'
)
.throwException();
}
}
Where jsonSample is a text string contain the following json (raw, not beautified):
{
"Table": [
{
"Entity": "Houston Heights",
"EntityD": "",
"Consolidation": "USD",
"ConsolidationD": "United States of America, Dollars",
"Scenario": "Actual",
"ScenarioD": "",
"Time": "2010M1",
"TimeD": "Jan 2010",
"View": "Periodic",
"ViewD": "",
"Account": "IFRS Balance Sheet",
"AccountD": "",
"Flow": "None",
"FlowD": "",
"Origin": "BeforeAdj",
"OriginD": "",
"IC": "None",
"ICD": "",
"UD1": "None",
"UD1D": "",
"UD2": "None",
"UD2D": "",
"UD3": "None",
"UD3D": "",
"UD4": "None",
"UD4D": "",
"UD5": "None",
"UD5D": "",
"UD6": "None",
"UD6D": "",
"UD7": "None",
"UD7D": "",
"UD8": "None",
"UD8D": "",
"CellValue": 2.25000000000000000000
},
{
"Entity": "Houston Heights",
"EntityD": "",
"Consolidation": "USD",
"ConsolidationD": "United States of America, Dollars",
"Scenario": "Actual",
"ScenarioD": "",
"Time": "2010M1",
"TimeD": "Jan 2010",
"View": "Periodic",
"ViewD": "",
"Account": "IFRS Balance Sheet",
"AccountD": "",
"Flow": "None",
"FlowD": "",
"Origin": "BeforeAdj",
"OriginD": "",
"IC": "None",
"ICD": "",
"UD1": "Admin",
"UD1D": "Admin",
"UD2": "None",
"UD2D": "",
"UD3": "None",
"UD3D": "",
"UD4": "None",
"UD4D": "",
"UD5": "None",
"UD5D": "",
"UD6": "None",
"UD6D": "",
"UD7": "None",
"UD7D": "",
"UD8": "None",
"UD8D": "",
"CellValue": 2.240000000000000000000
}
]
}
To solve this issue, the code should be like this because you are passing an array of objects:
function getData(request) {
try {
request.configParams = validateConfig(request.configParams);
var requestedFields = getFields().forIds(
request.fields.map(function (field) {
return field.name;
})
);
var data = JSON.parse(jsonSample).Table;
return {
schema: requestedFields.build(),
rows: data.map(function (row) {
var values = [];
requestedFields.asArray().forEach(function (field) {
values.push(row[field.getId()]);
});
return { values: values };
}),
};
} catch (e) {
cc.newUserError()
.setDebugText("Error fetching data from API. Exception details: " + e)
.setText(
"The connector has encountered an unrecoverable error. Please try again later, or file an issue if this error persists."
)
.throwException();
}
}
How to target a key when I have multiple alike keys in an object. If I try to target my desired key, it shows a syntax error.
const [modifiedNonFormData, setModifiedNonFormData] = useState({
"author": {
"lastName": "",
"location": {
"latitude": 49.3542671,
"longitude": 8.133071
},
"shippingAddress": {
"postalCode": "",
"name": "",
"address": "",
"location": {
"longitude": "",
"latitude": ""
},
"email": "",
"phone": "+14356234653"
},
"phone": "+14356234653",
"firstName": e.target.value
},})
const phoneHandler = (e) => {
let val = e.target.value
setModifiedNonFormData(modifiedNonFormData => {
return (
...modifiedNonFormData,
...modifiedNonFormData.author.phone:val
)
})}
I am trying to update/modify onChange input value
You need to do this instead:
setModifiedNonFormData(data => {
return ({
...data,
author: {
...data.author,
phone: val
}
})
})}
Explanation
You need to return a new object to a state setter in react. A common way to do this is through object destructuring. Let's say you have data and you want to clone it. You can do:
const newData = { ...data }
This would copy all of the values from data to a new object. This is also the reason why modifying data works - you are copying the values but also setting a new value for a property:
const newData = { ...data, newProperty: newValue }
However, this syntax is limited to replacing the value of a property. Therefore, if you want to modify the value of a property in an nested object, you have to also use the same syntax inside.
I am preparing an array like this
datas[5] = { "qty_sized": "1", "resolution": "5", "status": "", "order": 1342 };
where [5] is dynamic from response.
I have and object mydata and inside that I have a object items.
I push array to object items, with assign
Object.assign(mydatadata.items, datas);
Now mydata.items has an array set,
`
items{
1 {qty_auth: "", resolution: "4", status: "", order: "1495"},
5 {qty_sized: "1", resolution: "4", status: "", order: "1485"}
}`
Now if qty_auth: "" , from which i need to check if qty_ is empty then remove the array . So expected output is something like this:
Note: qty_ is dynamic here.
items{ 5 {qty_sized: "1", resolution: "4", status: "", order: "1485"} }
and i want to result inside same object mydata.items
I tried something like this
const mydatadata.items = mydata.items.filter((o) =>
Object.keys(o).some((k) => k.startsWith("qty") && o[k])
);
console.log(result);
but its now giving me any output
Using Object#entries, get the key-value pairs of items
Using Array#filter, iterate over the above array
In each iteration, check if the current item has a key starting with qty_ whose value is not empty. You can do this using Object#keys, Array#some, and String#startsWith.
Using Object#fromEntries, convert the filtered pairs to an object again.
const obj = {
items: {
1: {qty_auth: "", resolution: "4", status: "", order: "1495"},
5: {qty_sized: "1", resolution: "4", status: "", order: "1485"}
}
};
obj.items = Object.fromEntries(
Object.entries(obj.items)
.filter(([_, item]) =>
Object.keys(item).some(key => key.startsWith('qty_') && item[key])
)
);
console.log(obj);
You're talking about an array, but using curly brackets instead of square brackets. For filter() to work it would have to look like:
mydata = {
items: [
{qty_auth: "", resolution: "4", status: "", order: "1495"},
{qty_sized: "1", resolution: "4", status: "", order: "1485"}
]
}
Assuming it is an actual array there's still a problem with "const mydatadata.items", or at least it throws an error for me because mydatadata is not initialized. Unless it's a typo and it should be mydata, but then you'd be redeclaring it. So depending on what you want:
mydata.items = mydata.items.filter((o) =>
Object.keys(o).some((k) => k.startsWith("qty") && o[k])
);
or
let mydatadata = {};
mydatadata.items = mydata.items.filter((o) =>
Object.keys(o).some((k) => k.startsWith("qty") && o[k])
);
Furthermore you're storing the result in mydatadata but you're logging the variable result.
So depending on the previous answer:
console.log(mydatadata);
or
console.log(mydata);
Here's a fiddle: https://jsfiddle.net/b57qa82d/
You should probably just be using an array rather than an object. It's not really clear from your question what structure you need as you keep changing the terminology to describe your data. For example: "Now mydata.items has an array set" but your code says that it should be object with keys, not an array.
So I suggest: get your data in an array, and filter it by iterating over each object's entries and checking to see if any of the keys starting with "qty" has a value that isn't an empty string. You can then assign that filtered array to myObject.items.
const data = [
{ "qty_sized": "0", "resolution": "5", "status": "", "order": 2 },
{ "qty_auth": "", "resolution": "5", "status": "", "order": 3 },
{ "qty_auth": "1", "resolution": "5", "status": "", "order": 1342 },
{ "qty_sized": "", "resolution": "2", "status": "", "order": 1 },
{ "qty_sized": "1", "resolution": "1", "status": "", "order": 142 }];
const filtered = data.filter(obj => {
return Object.entries(obj).find(([key, value]) => {
return key.startsWith('qty') && value;
});
});
const myObject = { items: filtered };
console.log(myObject);
Additional documentation
Object.entries
find
I have this variable inside data():
jsonStatham: {
"uniqueOne": {
"field1": "",
"field2": "",
"field3": "",
"field4": "",
"field5": "",
"freeTextArea": ""
},
"uniqueTwo": {
"field1": "",
"field2": "",
"field3":"",
"field4":"",
"field5":"",
"freeTextArea":""
},
"uniqueThree": {
"field1": "",
"field2": "",
"freeTextArea": ""
}
},
What I want is to check if a value from this input field:
<input type="text" name="platform" placeholder="Platform" id="platform" v-model="platform" required/>
is matching one of the keys of "jsonStatham" (uniqueOne/Two/Three) and then push the keys of the matching key into an array. so if the input === uniqueOne, so this array:
inputFields: [
],
Will look like this: inputFields["field1","field2","field3","field4","field5"]
That's what I tried:
appendFields() {
for (const [key, value] of Object.entries(this.jsonStatham)) {
if(this.brand === this.jsonStatham[key]){
//console.log("Brand =>", this.brand)
}
//console.log(`${key}: ${value}`);
this.inputFields.push({
[key]:value
})
}
//console.log("ALL input Fields: \n",this.inputFields)
},
What I get in inputFields is "uniqueOne","uniqueTwo","uniqueThree"
if (this.jsonStatham.hasOwnProperty(this.brand)) {
this.inputFields.push(...Object.keys(this.jsonStatham[this.brand]));
}
this should do the trick:
Condition:
if(Object.keys(this.jsonStatham).includes(this.brand) )
this will be True array ["uniqueOne","uniqueTwo","uniqueThree", ..etc] will include this.brand
Pushing to array:
this.inputFields.push(...Object.keys(value))
I'm having hard time in success to iterate over my external json file in Vue.
I'm importing the file like this:
import json from '../../public/platform.json'
export default {
data: () => ({
currentPage: 0,
brand: '',
platform: '',
affiliate: '',
myJson: json,
}),
Json file looking like this:
{
"Example": {
"Username": "",
"Password": "",
"AffiliateID": "",
"GI": "",
"CI": "",
"freeTextArea": ""
},
"ExampleTwo": {
"Username": "",
"Password": "",
"freeTextArea": ""
}
}
My goal is to do as follows:
I want to check if the "platform" from data is matching "Example" or "ExampleTwo" and if it does, I want to access the fields within either of them.
How can I do it?
You can use a computed property as follows:
computed: {
myPlatform: function () { return json[this.platform] || {}; },
}
Here is a demo: https://codesandbox.io/s/clever-gould-3hkbl?fontsize=14&hidenavigation=1&theme=dark