Bitten by IE8
- web
- ie
- ie8
Yesterday, there was an embarrassing JavaScript error in some piece of functionality in our product at work.
To make it even worse, it appeared I had authored the excact row where things broke. To make it even worse, it was where I had made a somewhat lame effort to be robust.
It was about trying to handle the second (optional) parameter to a function - an options object. Instead of some standard (sloppy) cast-to-boolean check:
options || (options = {}); // kinda works
, I had decided to to act like some kind of grown up or something and avoid traps in the form of true , " " and 1 etc., like so:
function foo(url, options) {
// did we get any options object? if not, create an empty one
"[object Object]" == ({}).toString.call(options) || (options = {});
// append some parameter if it was given in options
"undefined" == typeof options.id || (url += "&id" + options.id);
}
Besides the opportunity to use the ({}) construct, this would also prevent sending in stuff like strings/arrays/functions/etc. that could act like property holders.
Fine, except IE8 gives "[object Object]" for both null and undefined . Waaahhh…
Here’s a rundown of what ({}).toString.call(o); produces for various values of the parameter o:
| IE9+, FF, Chrome, Opera | IE8- | |
|---|---|---|
| void 0 | [object Undefined] | [object Object] |
| null | [object Null] | [object Object] |
| {"{}"} | [object Object] | |
| [] | [object Array] | |
| /foo/ | [object RegExp] | |
| new Date | [object Date] | |
| "foo" | [object String] | |
| true | [object Boolean] | |
| false | [object Boolean] | |
| function() {"{}"} | [object Function] | |
| NaN | [object Number] | |
| 1 | [object Number] | |
| new Error("foo") | [object Error] |
This “class”-checking technique is generally quite useful, since it works with the language’s underlying type for the value. It also works across frames and such, unlike instanceof . Just beware of the described behaviour regarding null and undefined in IE8-.
More reading in this old post (don’ t skip the comments): http://javascriptweblog.wordpress.com/2011/08/08/fixing-the-javascript-typeof-operator/