Sometimes it makes sense to add additional properties to a result of a function,
Examples could be enhancing an operation result with some meta data, extending with a timestamp, run time, etc,
Using ES6, we could easily achieve this by:
bindData(oper, props) {
if (typeof oper === 'function') {
return (...args) => ({
...oper(...args),
...props
});
}
if (typeof oper === 'object') {
return Object.keys(oper).reduce((prev, key) => ({
...prev,
[key]: bindData(oper[key], props)
}), {});
}
return oper;
}
Here are some clarifications:
- If
oper
is a function, we decorate the original function by a closure,return (...args)
is the closure (read more about the spread operator.
In general, myFunction(...args);
is equelevent to (args) { oper.apply(null, args); }
,
- When the returned function is invoked, the result of the original function
...oper(...args)
is then merged with theprops
object, in other words:
...oper(), ...props
is equelevent to: Object.assign({}, oper(), props);
Read more about Object.assign
- If
oper
is an object, we bind each of its key’s recursively (assuming each property is a function).