Preserving arity in function wrappers
# Rick Waldron (12 years ago)
They won't be writable, but they will be configurable: rwaldron/tc39-notes/blob/master/es6/2013-07/july-25.md#consensusresolution-3, which meets the need you've described.
# Bruno Jouhier (12 years ago)
Configurable will do it. Thanks.
# Andrea Giammarchi (12 years ago)
when I've seen this ...
On Sat, Sep 14, 2013 at 1:49 PM, Bruno Jouhier <bjouhier at gmail.com> wrote:
- inside wrap, call F.toString(), replace F() by F(a1, a2, ...), eval and return the new function.
I wondered why this would not be enough ...
function wrap(Function) {
for(var i = 0, a = []; i < Function.length; a[i] = 'a' + i++);
return eval('('.concat(
'function ',
Function.name || '',
'(', a.join(','), ') {',
// do some magic here
'return Function.apply(this, arguments);',
'})'
));
}
function first(one, two, three) {
return one + two + three;
}
wrap(first)(1, 2, 3); // 6
... if you parse to string you loose the scope plus most testing frameworks out there use the with statement, eval, Function, etc ... so why do you feel like eval is not a solution? Is is a JSLint VS testing code the problem or something else I cannot think about right now?
Cheers
The classical pattern for function wrappers is the following
function wrap(fn) { return function F() { ... var result = fn.apply(this, arguments); ... return result; }; }
This pattern has one problem though: the returned function has a different arity than the original function. This causes problems with libraries that test fn.length; for example with express and moccha in node.js.
I found two ways to restore the arity:
I find it rather clumsy to have to call eval to solve this. Maybe there is a better solution without eval but if there isn't it may be interesting to improve the language for this. Some ideas (probably naive):
WDYT?