What you're pretty much doing here is iterating through values at the third level of an object. You could create an iterator to do this for you. Generator functions are ideal for this, as you can easily use them recursively. The following code (in Typescript) will allow you to easily do this:
type NestedObjects <T> = {
[key: string]: NestedObjects <T> | T
}
/**
* Iterates through all values nested at n levels deep.
* Every iteration yields an array containing all keys looped through, in reverse.
* This means that the first entry will be the value at n levels, followed by keys at n-1, n-2, etc.
*
* Example:
* <pre>
* for (const x of NestedObjectIterator(a, 3)) ...
* </pre>
*
* is equivalent to three nested for loops:
* <pre>
* for (const x of Object.keys(a))
* for (const y of Object.keys(a[x]))
* for (const z of Object.keys(a[x][y])) ...
* </pre>
*/
function * NestedObjectIterator <T> (obj: NestedObjects<T>, levels: number, ...prevKeys: string[]): Iterable<[T, ...string[]]> {
for (const key of Object.keys(obj)) {
if (levels === 1) yield [obj[key] as T, key, ...prevKeys]
else if (obj[key]) yield * NestedObjectIterator(obj[key] as NestedObjects<T>, levels - 1, key, ...prevKeys)
}
}
The equivalent in pure Javascript:
function * NestedObjectIterator (obj, levels, ...prevKeys) {
for (const key of Object.keys(obj)) {
if (levels === 1) yield [obj[key], key, ...prevKeys]
else if (obj[key]) yield * NestedObjectIterator(obj[key], levels - 1, key, ...prevKeys)
}
}
You can now loop through your object like this:
const myObj = {
firstObj: {
nested: {
anotherNest: 'i want to get this value'
},
again: {
'i want this value ->': ':D'
}
}
}
for (const [value] of NestedObjectIterator(myObj, 3)) {
console.log(value)
}