Reputation: 13
I'm trying to loop some products in JSON. I get many different kinds of JSON files and that's why I made form that I can just manually "patch" the file.
{ "product": [ { "@attributes": { "ID": "123456789" }, "name": "Name of the product"],...}
So I have two input fields in my form:
1. id="product_name" value="name"
2. id="product_id" value="['@attributes']['ID']"
I use ng-repeat to loop throug products. These work fine:
{{product}} //Product object
{{product.name}} //name of the product
{{product[value]}} //if value = name, name of the product
My problem is that I don't know how to get that ['@attribute']['ID'] from the product.
EDIT: I know that this will work:
{{product['@attributes']['ID']}}
but I need to change the value from form input.
EDIT: SOLUTION:
controller.getData = function(object, key) {
var keys = [];
var count = key.replace(/[^.]/g, '').length;
if(count === 4){
keys = key.split(".");
return object[keys[0]][keys[1]][keys[2]][keys[3]][keys[4]];
}else if(count === 3){
keys = key.split(".");
return object[keys[0]][keys[1]][keys[2]][keys[3]];
}else if(count === 2){
keys = key.split(".");
return object[keys[0]][keys[1]][keys[2]];
}else if(count === 1){
keys = key.split(".");
return object[keys[0]][keys[1]];
}else{
return object[key];
}
};
New problem:
{ "product": [
{ "@attributes": { "ID": "12345" },
"name": "productname",
"price": "xx",
"URL": "url",
"images": { "image": "imgUrl" },
"description": {},
"categories": {
"category": "Kesäale" },
"properties": { "property": [
{ "@attributes": { "name": "color" }, "value": "B25 Grisaille" },
{ "0": "\n", "@attributes": { "name": "size" } },
{ "@attributes": { "name": "currency" }, "value": "EUR" },
{ "@attributes": { "name": "brand" }, "value": "brandName" },
{ "@attributes": { "name": "fromPrice" }, "value": "xx" },
{ "@attributes": { "name": "manufacturer" }, "value": "xx" },
{ "@attributes": { "name": "weight" }, "value": "0.5" },
{ "@attributes": { "name": "stock" }, "value": "true" },
{ "@attributes": { "name": "EAN" }, "value": "1234" } ] },
"variations": {} },
How can I get brandName?
Upvotes: 1
Views: 71
Reputation: 12270
This is a problem with some special characters in properties. The same happens if you have a json key like e.g. my-key
which cannot be accessed in a property-way. Therefore you can use the fallback array access to get the value:
var x = { "product": [ { "@attributes": { "ID": "123456789" }, "name": "Name of the product"}]}
// [0] not required when looping through the list...
var id = x.product[0]["@attributes"].ID
console.log(id); // 123456789
EDIT: to read it dynamically, you could use some helper function like so (can be extended, if the path is more dynamic)
var key = "@attributes.ID";
function getData(object, key) {
var keys = key.split(".");
return object[keys[0]][keys[1]];
}
// sample call for demo purpose
var res = getData(x.product[0], key);
console.log(res);
And call the getData() method from your expression like this:
{{ getData(product, value) }}
EDIT2: for a fully dynamic structure:
function getDataDyn(object, keystr) {
var keys = keystr.split(".");
return digg(object, keys);
}
function digg(obj, keys) {
if(keys.length === 1) {
return obj[keys[0]]
} else {
return digg(obj[keys[0]], keys.splice(1));
}
}
// sample call for demo purpose
var result = getDataDyn(x.product[0], key);
console.log(result);
Upvotes: 1
Reputation: 193301
There are no very elegant solution for this problem. However, you can simplify things significantly if you don't parse key manually and just delegate it to existent Angular services. In your case $parse can already do it.
I would wrap this functionality into custom filter so it could be something like this:
.filter('key', function($parse) {
return function(context, name) {
return $parse('this' + name)(context);
};
});
And them in HTML:
{{ product | key:name }} // name is "['@attributes']['ID']"
Demo: http://plnkr.co/edit/jIIhXDW6S62IYrBXIB94?p=preview
Upvotes: 0
Reputation: 1571
You could use {{product['@attributes'].ID}}
Or if the first object key is dynamically named you could do: {{product[Object.keys(product)[0]].ID}}
Object.keys(obj)
returns an array of keys for a given object
https://developer.mozilla.org/en/docs/Web/JavaScript/Reference/Global_Objects/Object/keys
Upvotes: 1