The other day I had to make a long list of functions where the name was derived from an object key name. Since programming is the art of automating stuff, I thought “There has to be a way to have the code do this!”. Searching on our good friend stackoverflow.com there were plenty of examples of how to set the name of a function by using eval, or the Function constructor. Eval has some security issues, and by extension the constructor that uses it behind the curtains. So, what other way is there?
Well, the name property of functions is read-only, so that cannot be created and just renamed. However, there is more than one way to name a function.
One way is in the declaration, but that name is fixed upon declaration.
function superCoolFunction() { } superCoolFunction.name === 'superCoolFunction';
The same is true for function expressions, where the anonymous function name is derived from the variable name (doesn’t that make it not anonymous though?):
const nameOrigin = function() { }; nameOrigin.name === 'nameOrigin';
Another is through object literal notation:
const objectLiteral = { evenCoolerFunction() { } }; objectLiteral.evenCoolerFunction.name === 'evenCoolerFunction';
But, since object literals can have computed properties we can have:
const dynamicName = 'coolDynamicName'; const objectLiteral = { [dynamicName]() { } }; objectLiteral[dynamicName].name === 'coolDynamicName';
And thus we can have a function that creates a function with a dynamically named method and return that method!
[codepen_embed height=”320″ theme_id=”0″ slug_hash=”JyWoWP” default_tab=”js,result” user=”javver”]See the Pen <a href=’https://codepen.io/javver/pen/JyWoWP/’>JyWoWP</a> by Javier (<a href=’https://codepen.io/javver’>@javver</a>) on <a href=’https://codepen.io’>CodePen</a>.[/codepen_embed]
You may ask, can’t this be done with Object.defineProperty? Well, not really, you can create functions in the object, but the Function.name value returned will not be what you input to that function, since the function in the property descriptor will be named value. You can play around with a near solution in this pen.
Caveat emptor: this has not been benchmarked in any way or tested for JS engine optimization compatibility. Just another tool in the belt, just in case. 😉