If I run this javascript:
var a,b=Element.prototype;
for(a in b)b[a];
Firefox gives me this error:
TypeError: Value does not implement interface Element.
Here is a test case:
http://codepen.io/WilliamMalo/pen/AJkuE
It works in all other browsers. How can I make it work in firefox? It's driving me nuts!
The Firefox (and recent IE) behavior here is because the property getters for some properties (say firstChild
) are on the prototype object bu the properties make no sense on the prototype itself. Trying to get them on the prototype will throw.
This is the behavior required by the specification, in fact. See http://dev.w3.org/2006/webapi/WebIDL/#dfn-attribute-getter step 2 substep 2 subsubstep 2. Firefox and IE are following the spec here and WebKit-based browsers are not.
Consider the following:
console.log('parentNode' in Element.prototype
? Element.prototype.parentNode
: 'no parentNode here');
Pretty innocent, right? It gives you no parentNode
string in Chrome (and probably in Safari too)... yet it fails both in Firefox (21) and IE (10):
- Firefox:
value does not implement interface Node
- IE10:
invalid calling object
Why is that? See, we've entered the Host Objects Zone, also known as The Zone Of No Rules. The point is that while some properties seem to be attached to Element.prototype
, they're inaccessible from there - only from Element
instances.
What can be done about it? An obvious way out is wrapping the offender in 'try-catch' block:
var a, b = Element.prototype, arr = [];
for (a in b) {
try {
b[a];
arr.push(a);
} catch (e) {}
}
You might want to try using Object.getOwnPropertyDescriptor()
in your loop instead of accessing each property directly using the key on the prototype: http://codepen.io/seraphzz/pen/aJgcr