Skip to content

Instantly share code, notes, and snippets.

@kylejeske
Created February 7, 2019 16:17
Show Gist options
  • Save kylejeske/6255147874678e4402870cf05b7f5c16 to your computer and use it in GitHub Desktop.
Save kylejeske/6255147874678e4402870cf05b7f5c16 to your computer and use it in GitHub Desktop.
flatten object test
/**
* Takes a deeply nested object, `source`, and returns an object with
* dot-separated paths pointing to all primitive values from `source`.
*
* Examples:
*
* flatten({ foo: { bar: 1 } })
* //=> { 'foo.bar': 1 }
*
* flatten({ foo: [{ bar: 1 }, { bar: 2 }] })
* //=> { 'foo.0.bar': 1, 'foo.1.bar': 2 }
*/
function flatten(source) {
// hashtable .. sort of
let container = {};
function updateKey(key, data) {
if (container.hasOwnProperty(key) === true) {
container[key] = [].concat(container[key], data);
} else {
container[key] = data;
}
}
// traverseObject ([object], string: optional)
function traverseObject (o, k) {
// edge-case for null objects {'foo.bar':null}
if (typeof o == "object" && o == null) {
updateKey(k, o);
}
for (var prop in o) {
let key = prop;
if (typeof k != "undefined") {
key = [k, prop].join(".");
}
if (typeof o[prop] == "array" || typeof o[prop] == "object") {
traverseObject(o[prop], key);
} else {
updateKey(key, o[prop]);
}
}
return container;
};
return traverseObject(source);
}
<!DOCTYPE HTML>
<html>
<head>
<title>Elastic Coding Exercise</title>
<link href="https://cdnjs.cloudflare.com/ajax/libs/mocha/2.2.5/mocha.css" rel="stylesheet" />
</head>
<body>
<div id="mocha"></div>
<script src="https://cdnjs.cloudflare.com/ajax/libs/mocha/2.2.5/mocha.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/chai/2.3.0/chai.js"></script>
<script src="flatten.js"></script>
<script src="test.flatten.js"></script>
</body>
</html>
mocha.setup('bdd');
const expect = chai.expect;
describe('flatten()', function () {
it('should flatten a simple nested object', function () {
const source = {
foo: {
bar: 1
}
};
const expected = {
'foo.bar': 1
};
expect(flatten(source)).to.deep.equal(expected);
});
it('should flatten an object with nested arrays', function () {
const source = {
foo: [{
bar: 1
}, {
bar: 2
}]
};
const expected = {
'foo.0.bar': 1,
'foo.1.bar': 2
};
expect(flatten(source)).to.deep.equal(expected);
});
it('should flatten a complex nested object', function () {
const source = {
a: 1,
b: {
c: true,
d: {
e: 'foo'
}
},
f: false,
g: ['red', 'green', 'blue'],
h: [{
i: 2,
j: 3
}]
};
const expected = {
'a': 1,
'b.c': true,
'b.d.e': 'foo',
'f': false,
'g.0': 'red',
'g.1': 'green',
'g.2': 'blue',
'h.0.i': 2,
'h.0.j': 3
};
expect(flatten(source)).to.deep.equal(expected);
});
it('should flatten an object with null values', function () {
const source = {
foo: {
bar: null
}
};
const expected = {
'foo.bar': null
};
expect(flatten(source)).to.deep.equal(expected);
});
});
mocha.run();
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment