Open
Bug 520882
Opened 15 years ago
Updated 2 years ago
Object.getOwnPropertyDescriptor treats properties with native getter/setter as data properties
Categories
(Core :: JavaScript Engine, defect)
Tracking
()
NEW
People
(Reporter: jorendorff, Unassigned)
References
Details
The JSAPI makes it easy to define properties that are neither ES5 data properties nor exactly ES5 accessor properties. In fact any property with a JSPropertyOp getter or setter is such a beast; but there are also properties that have both a native getter/setter *and* a slot, like expando properties on DOM objects.
The code in obj_getOwnPropertyDescriptor seems to ignore this possibility. The results are weird.
Properties with native (JSPropertyOp) getters/setters are treated as data properties. To get the value for such a property, we call the getter. The native getter might do anything, including deleting the property; it seems odd for Object.getOwnPropertyDescriptor to have that kind of side effect.
js> it.noisy = true;
true
js> Object.getOwnPropertyDescriptor(it, "noisy")
getting its property noisy, initial value true
({value:true, writable:true, enumerable:true, configurable:true})
I think the weird way this behaves when applied to DOM properties is related to this. Ordinary XPConnect properties representing XPIDL attributes are JSPROP_GETTER|JSPROP_SETTER and thus are treated as accessor properties:
> Object.getOwnPropertyDescriptor(document.body.__proto__, "children")
({get:getter function children() {[native code]},
set:(void 0), enumerable:true, configurable:true})
(The stray "getter" there seems like a bug too, unrelated maybe.)
But quick-stubbed properties have JSPropertyOp getters/setters, so they are treated as data properties.
> Object.getOwnPropertyDescriptor(document.body.__proto__, "firstChild")
NS_ERROR_XPC_BAD_OP_ON_WN_PROTO on line 1: Illegal operation on
WrappedNative prototype object
That's the same error you get for `document.body.__proto__.firstChild`, so I think it's caused by trying to get the value.
We should reflect this kind of property as an accessor property instead. That way we don't have to get the value. Desired behavior:
js> Object.getOwnPropertyDescriptor(it, "noisy")
({get:function () {[native code]}, set: function () {[native code]},
enumerable:true, configurable:true})
mrbkap has expressed some paranoia about reflecting arbitrary native getters and setters as JS functions before. I don't remember why. If we want to maintain maximum paranoia, we could create functions here that always throw if they're applied to any object other than the one you extracted them from.
Comment 1•15 years ago
|
||
Bug 430133 has more comment on this, as well as on its interaction with shared-permanent properties with native getters. For the cases described here it does make sense to expose native getters/setters as accessor descriptors, but for others it does not. There doesn't seem to be a simple or obvious solution unless I'm missing something.
Comment 2•15 years ago
|
||
(In reply to comment #1)
> Bug 430133 has more comment on this, as well as on its interaction with
> shared-permanent properties with native getters. For the cases described here
> it does make sense to expose native getters/setters as accessor descriptors,
> but for others it does not. There doesn't seem to be a simple or obvious
> solution unless I'm missing something.
Right, it will require case analysis. We could retrofit a case-labeling system on top of the otherwise-unconstrained JSPropertyOp getters and setters, but it may not be worth the trouble. Not sure.
/be
Updated•13 years ago
|
Assignee | ||
Updated•10 years ago
|
Assignee: general → nobody
Updated•2 years ago
|
Severity: normal → S3
You need to log in
before you can comment on or make changes to this bug.
Description
•