Указание пути к ключу для фильтрации через переменную
Допустим, что у меня есть массив объектов вида:
[
{
"key1": {
"key2": "test"
}
},
{
"key1": {
"key2": "test1"
}
},
{
"key1": {
"key2": "test2"
}
}
]
Я хочу его отфильтровать в js с помощью функции .filter.
Вроде бы, все просто json.filter(e => e.key1.key2 === 'value').
Но при этом я хочу, чтобы можно было подать путь key1.key2 через переменную, так как путь могут прислать снаружи.
Я хочу понять, реально ли это реализовать без использования eval(). Снаружи этот путь поступает в виде строки. То есть фактически хочу увидеть что-то типа:
let variable = "key1.key2"
json.filter(e => e.variable === 'value')
Но понятно, что это так не работает. :(
Ответы (2 шт):
Автор решения: vsemozhebuty
→ Ссылка
Один из вариантов (если в названиях ключей может быть точка, вместо строки можно сразу передавать массив подключей):
const data = [
{
"key1": {
"key2": "test"
}
},
{
"key1": {
"key2": "test1"
}
},
{
"key1": {
"key2": "test2"
}
}
];
function filterByKeys(array, keys, value) {
return array.filter(
(object) => {
let currentObjectOrValue = object;
for (const key of keys.split('.')) {
currentObjectOrValue = currentObjectOrValue[key];
}
return currentObjectOrValue === value;
}
);
}
console.log(filterByKeys(data, "key1.key2", "test"));
console.log(filterByKeys(data, "key1.key2", "test1"));
console.log(filterByKeys(data, "key1.key2", "test2"));
Автор решения: yar85
→ Ссылка
Array.prototype.filterByNestedProp = function (path, cb) {
path = path.split('.');
const getNestedObjPropValue = obj => path.reduce(
(rslt, prop) => rslt && rslt[prop]
, obj);
return this.filter(obj => cb.call(obj, getNestedObjPropValue(obj)));
};
const arr = [
{ "key1": { "key2": "test" }},
{ "key1": { "key2": "test1" }},
{ "key1": { "key2": "test2" }},
{ "key1": { "key2": "test3" }},
];
// `v => v === значение` как-то скучно, поэтому с регуляркой (найдет 2 объекта)
const testRslt = arr.filterByNestedProp('key1.key2', v => /[12]$/.test(v));
console.log(testRslt);