Created
December 16, 2014 18:25
-
-
Save ssube/b4e1e827e14105313312 to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
/** | |
* Uses map syntax to retrieve the given object, or return null if any | |
* portion of the chain is null or undefined. The chain should be given with one | |
* field or method per argument. Methods will be called with the previous step as | |
* `this` and no arguments; this can be used for many string and array methods, as | |
* well as getters from various libraries. | |
* | |
* For example, given the object `foo = {bar: function (x) { return x+3; }};`, then | |
* `objectDig(foo, "bar.toExponential", [[2], [1]])` would return "5.0e+0". | |
* | |
* @param {Object} b The base object to work from. | |
* @param {String} h The chain of fields/methods to access, seperated by dots | |
* (eg, "foo.bar"). Any links in this chain may be prefixed with '!' to be not-ed | |
* while resolving. | |
* @param {Array} a An array containing arguments to any methods in the chain. | |
* Each method, when found, will be called with the then-head of this array, and the | |
* array moved to the next element. Null may be given to call a method without | |
* arguments, otherwise each function found in the chain will be passed one element | |
* from this array. This must be an array of arrays (standard `apply` semantics). | |
* @param {Object} df The default value. If any link in the chain is missing or | |
* no chain is given and `b` is undefined, this will be returned. | |
* | |
* @returns The last link in the given chain, or `df` if the chain could not be completed. | |
*/ | |
function objectDig(b, h, a, df) { | |
if (typeof b == "undefined" || !h) { | |
return b; | |
} | |
var l = h.split('.'), c = _.clone(a || []), ll = l.length; | |
df = df || null; | |
for (var i = 0; i < ll; ++i) { | |
if (_.isUndefined(b) || _.isNull(b)) { | |
return df; | |
} | |
var li = l[i], f = false; | |
if (li[0] == '!') { | |
f = true; | |
li = li.substr(1); | |
} | |
var d = b[li]; | |
if (_.isFunction(d)) { | |
d = d.apply(b, _.first(c) || []); | |
c = c ? _.rest(c) : null; | |
} | |
b = f ? !d : d; | |
} | |
if (_.isUndefined(b)) { | |
b = df; | |
} | |
return b; | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment