开发者

Object.defineProperty(obj, "prop", desc) behaving strangely

If I define an object and set its configurable property to false, but leave all other props alone, and later attempt to set that object's writable prop to false, then back to true, a TypeError is thrown.

Here's a breakdown of how I'm doing this, although I have attempted this by altering only one object data descriptor in dot notation, and also by altering all data descriptors of the object in object literal, and neither form has worked.

// simple object, and the data descriptor
var o = {name : "tom"},
    dataDesc = Object.getOwnPropertyDescriptor(o, "name");

noConfig();
alert(dataDesc.writable);  // alerts true

readOnly();
alert (dataDesc.writable); // alerts false

writable();
alert (dataDesc.writable); // error is thrown within writable() - alerts true

// early in the script, alte开发者_开发知识库ring only configurable property
function noConfig(){
  dataDesc.configurable = false;
}

// later in the script, altering only writable property
function readOnly(){

  dataDesc.writable = false; // configurable = false; writable = false;
  Object.defineProperty(o, "name", dataDesc); // works finely
}

function writable(){
    try{
      dataDesc.writable = true; // configurable = false; writable = true;
      Object.defineProperty(o, "name", dataDesc); // throws TypeError
    }catch(e){
      alert(e); // alerts: "TypeError: Cannot redefine property: defineProperty"
    }
}

I could find nothing to help in the spec, but the MDC article for defineProperty states that, even after an object property is rendered unconfigurable, the writable data descriptor can still be modified. All others cannot, but writable can.

So, is this something in Chrome, or am I doing this wrong?

/* UPDATE */

This has been resolved - just read the spec 8.12.9 section 10.a.i


The error isn't coming from dataDesc.writable = true;, it's coming from Object.defineProperty(o, "name", dataDesc);...which is correct, since {name : "tom"} does already have a name property defined.

This is the correct behavior, you are able to change writable and not able to redefine the name property.

I think the confusion comes from the behavior, you don't need to call .defineProperty() for .writable to take effect, you can test it here.

Note: I commented out .configurable = false in the above example, which would lock the property attributes and not allow you to change writable further, leaving it stuck in false in your original code.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜