Você deve fazer isso passo a passo se não quiser um, TypeErrorporque se um dos membros for nullor undefinede tentar acessar um membro, uma exceção será lançada.
Você pode simplesmente fazer catcha exceção ou criar uma função para testar a existência de vários níveis, algo como isto:
function checkNested(obj /*, level1, level2, ... levelN*/) {
var args = Array.prototype.slice.call(arguments, 1);
for (var i = 0; i < args.length; i++) {
if (!obj || !obj.hasOwnProperty(args[i])) {
return false;
}
obj = obj[args[i]];
}
return true;
}
var test = {level1:{level2:{level3:'level3'}} };
checkNested(test, 'level1', 'level2', 'level3'); // true
checkNested(test, 'level1', 'level2', 'foo'); // false
ATUALIZAÇÃO ES6:
Aqui está uma versão mais curta da função original, usando os recursos e a recursão do ES6 (também está no formulário de chamada de cauda apropriado ):
function checkNested(obj, level, ...rest) {
if (obj === undefined) return false
if (rest.length == 0 && obj.hasOwnProperty(level)) return true
return checkNested(obj[level], ...rest)
}
No entanto, se você deseja obter o valor de uma propriedade aninhada e não apenas verificar sua existência, aqui está uma função simples de uma linha:
function getNested(obj, ...args) {
return args.reduce((obj, level) => obj && obj[level], obj)
}
const test = { level1:{ level2:{ level3:'level3'} } };
console.log(getNested(test, 'level1', 'level2', 'level3')); // 'level3'
console.log(getNested(test, 'level1', 'level2', 'level3', 'length')); // 6
console.log(getNested(test, 'level1', 'level2', 'foo')); // undefined
console.log(getNested(test, 'a', 'b')); // undefined
A função acima permite que você obtenha o valor das propriedades aninhadas, caso contrário, retornará undefined.
ATUALIZAÇÃO 2019-10-17:
A proposta de encadeamento opcional chegou ao Estágio 3 no processo do comitê ECMAScript , permitindo acessar com segurança propriedades profundamente aninhadas, usando o token ?., o novo operador de encadeamento opcional :
const value = obj?.level1?.level2?.level3
Se algum dos níveis acessados for nullou undefineda expressão será resolvida undefinedpor si mesma.
A proposta também permite lidar com chamadas de método com segurança:
obj?.level1?.method();
A expressão acima produzirá undefinedse obj, obj.level1ou obj.level1.methodsão nullou undefined, caso contrário irá chamar a função.
Você pode começar a jogar com esse recurso com Babel usando o plug-in de encadeamento opcional .
Desde o Babel 7.8.0 , o ES2020 é suportado por padrão
Veja este exemplo no Babel REPL.
🎉🎉UPDATE: dezembro de 2019 🎉🎉
A proposta de encadeamento opcional finalmente chegou ao Estágio 4 na reunião de dezembro de 2019 do comitê do TC39. Isso significa que esse recurso fará parte do Padrão ECMAScript 2020 .