Handling optional parameters in javascript
You can know how many arguments were passed to your function and you can check if your second argument is a function or not:
function getData (id, parameters, callback) {
if (arguments.length == 2) { // if only two arguments were supplied
if (Object.prototype.toString.call(parameters) == "[object Function]") {
callback = parameters;
}
}
//...
}
You can also use the arguments object in this way:
function getData (/*id, parameters, callback*/) {
var id = arguments[0], parameters, callback;
if (arguments.length == 2) { // only two arguments supplied
if (Object.prototype.toString.call(arguments[1]) == "[object Function]") {
callback = arguments[1]; // if is a function, set as 'callback'
} else {
parameters = arguments[1]; // if not a function, set as 'parameters'
}
} else if (arguments.length == 3) { // three arguments supplied
parameters = arguments[1];
callback = arguments[2];
}
//...
}
If you are interested, give a look to this article by John Resig, about a technique to simulate method overloading on JavaScript.
Er - that would imply that you are invoking your function with arguments which aren't in the proper order... which I would not recommend.
I would recommend instead feeding an object to your function like so:
function getData( props ) {
props = props || {};
props.params = props.params || {};
props.id = props.id || 1;
props.callback = props.callback || function(){};
alert( props.callback )
};
getData( {
id: 3,
callback: function(){ alert('hi'); }
} );
Benefits:
- you don't have to account for argument order
- you don't have to do type checking
- it's easier to define default values because no type checking is necessary
- less headaches. imagine if you added a fourth argument, you'd have to update your type checking every single time, and what if the fourth or consecutive are also functions?
Drawbacks:
- time to refactor code
If you have no choice, you could use a function to detect whether an object is indeed a function ( see last example ).
Note: This is the proper way to detect a function:
function isFunction(obj) {
return Object.prototype.toString.call(obj) === "[object Function]";
}
isFunction( function(){} )
You should check type of received parameters. Maybe you should use arguments
array since second parameter can sometimes be 'parameters' and sometimes 'callback' and naming it parameters might be misleading.