Re: Return values of mutating MOP operations (Was: response chapter 8 except 8.5 (was Re: ES6 Rev13 Review: MOP-refactoring, symbols, proxies, Reflect module))

2013-01-02 Thread Allen Wirfs-Brock

On Dec 31, 2012, at 4:27 AM, Tom Van Cutsem wrote:

 2012/12/31 Allen Wirfs-Brock al...@wirfs-brock.com
 responses for chapter 8, except for 8.5 which will get its own message.
 
 
 On Dec 29, 2012, at 2:37 PM, Tom Van Cutsem wrote:
  Table 8:
* [[PreventExtensions]] internal method: should return a Boolean success 
  value
 
 Why?  no caller of [[PreventExtension]] currently uses such a result.  In 
 general, we did try to make more of the internal methods return true/false 
 success indicators rather than deeply burying the decision of whether or not 
 an exception should be generated on failure.  Do you have something in mind 
 where a caller of [[PreventExtension]] within the spec. (or a caller of 
 Reflect.preventExtensions) needs a true/false success code?  Or maybe we 
 should just do it for consistency sake.
 
 Three reasons:
 1) As you say, consistency with [[DefineOwnProperty]], [[Delete]] and [[Set]] 
 (maybe also [[SetInheritance]]). Every operation that mutates an object 
 returns a success code indicating whether or not the intended change took 
 place.
 
 2) Before proxies and symbols, [[PreventExtensions]] could never fail. With 
 the advent of new exotics, this operation may be rejected. Proxies and 
 symbols need a way to signal this. Essentially Object.preventExtensions 
 should throw a TypeError when [[PreventExtensions]] return false. 
 Object.preventExtensions should never fail silently on a proxy that rejects 
 the operation.

Symbols don't need to fail on [[PreventExtensions]].  It always succeeds for 
them since they are born non-extensible.

The major user facing change here is the possibility that 
Object.preventExtensions will through if the object can not be made 
non-extensible.  This wasn't specified  in ES5, but I'm ok making that change.

 
 3) It would be really useful if Reflect.preventExtensions returned the 
 boolean success code, as this provides an easier way to test if this 
 operation succeeded than is possible with Object.preventExtensions. Compare:
 
 if (Reflect.preventExtensions(obj)) { /* success code */ } else { /* failure 
 code */ }
 
 vs.
 
 try {
   Object.preventExtensions(obj);
   /* success code */
 } catch (e) { if (!(e instanceof TypeError)) throw e; // not even a 
 fool-proof test
   /* failure code */
 }

OK, [[PreventExtensions]] not returns a boolean





  
* [[Delete]]: I would remove because its [[Configurable]] attribute is 
  false. from the description. Proxies and host objects may return false for 
  other reasons as well (cf. the recent discussions about DontDelete vs. 
  configurable:false)
 
 Do you have some alternative wording?  These descriptions (along with 
 whatever eventually goes into 8.1.6.3)  are intended to be the informal 
 description of the contract of these MOP methods.  What is true or false 
 actually intended to mean for [[Delete]]?  Is it that false means:  the 
 property exists but the property wasn't deleted?
 
 The success code for [[Delete]] is indeed fuzzy as it may mean:
 a) the property was/was not successfully deleted
 b) the property is / is no longer present
 
 Since deleting a non-existent property returns true, b) is closer to the 
 existing semantics.
 
 Here's my alternative wording:
 [[Delete]] (propertyKey) - Boolean: Removes the own property indentified by 
 the propertyKey parameter from the object. Return false if the property was 
 not deleted and is still present. Return true if the property was deleted or 
 was not present.

Good, I'll use that language.

Allen


 
 Cheers,
 Tom

___
es-discuss mailing list
es-discuss@mozilla.org
https://mail.mozilla.org/listinfo/es-discuss


Re: Return values of mutating MOP operations (Was: response chapter 8 except 8.5 (was Re: ES6 Rev13 Review: MOP-refactoring, symbols, proxies, Reflect module))

2013-01-02 Thread Tom Van Cutsem
2013/1/2 Allen Wirfs-Brock al...@wirfs-brock.com


 Symbols don't need to fail on [[PreventExtensions]].  It always succeeds
 for them since they are born non-extensible.


Sounds reasonable.


 The major user facing change here is the possibility that
 Object.preventExtensions will through if the object can not be made
 non-extensible.  This wasn't specified  in ES5, but I'm ok making that
 change.


Ok. Recall that in the old Proxy API, we already had the fix() trap
returning a boolean, and Object.{preventExtensions,seal,freeze} throwing on
false.

Cheers,
Tom
___
es-discuss mailing list
es-discuss@mozilla.org
https://mail.mozilla.org/listinfo/es-discuss


Return values of mutating MOP operations (Was: response chapter 8 except 8.5 (was Re: ES6 Rev13 Review: MOP-refactoring, symbols, proxies, Reflect module))

2012-12-31 Thread Tom Van Cutsem
2012/12/31 Allen Wirfs-Brock al...@wirfs-brock.com

 responses for chapter 8, except for 8.5 which will get its own message.


 On Dec 29, 2012, at 2:37 PM, Tom Van Cutsem wrote:
  Table 8:
* [[PreventExtensions]] internal method: should return a Boolean
 success value

 Why?  no caller of [[PreventExtension]] currently uses such a result.  In
 general, we did try to make more of the internal methods return true/false
 success indicators rather than deeply burying the decision of whether or
 not an exception should be generated on failure.  Do you have something in
 mind where a caller of [[PreventExtension]] within the spec. (or a caller
 of Reflect.preventExtensions) needs a true/false success code?  Or maybe we
 should just do it for consistency sake.


Three reasons:
1) As you say, consistency with [[DefineOwnProperty]], [[Delete]] and
[[Set]] (maybe also [[SetInheritance]]). Every operation that mutates an
object returns a success code indicating whether or not the intended change
took place.

2) Before proxies and symbols, [[PreventExtensions]] could never fail. With
the advent of new exotics, this operation may be rejected. Proxies and
symbols need a way to signal this. Essentially Object.preventExtensions
should throw a TypeError when [[PreventExtensions]] return false.
Object.preventExtensions should never fail silently on a proxy that rejects
the operation.

3) It would be really useful if Reflect.preventExtensions returned the
boolean success code, as this provides an easier way to test if this
operation succeeded than is possible with Object.preventExtensions. Compare:

if (Reflect.preventExtensions(obj)) { /* success code */ } else { /*
failure code */ }

vs.

try {
  Object.preventExtensions(obj);
  /* success code */
} catch (e) { if (!(e instanceof TypeError)) throw e; // not even a
fool-proof test
  /* failure code */
}


* [[Delete]]: I would remove because its [[Configurable]] attribute
 is false. from the description. Proxies and host objects may return false
 for other reasons as well (cf. the recent discussions about DontDelete vs.
 configurable:false)

 Do you have some alternative wording?  These descriptions (along with
 whatever eventually goes into 8.1.6.3)  are intended to be the informal
 description of the contract of these MOP methods.  What is true or false
 actually intended to mean for [[Delete]]?  Is it that false means:  the
 property exists but the property wasn't deleted?


The success code for [[Delete]] is indeed fuzzy as it may mean:
a) the property was/was not successfully deleted
b) the property is / is no longer present

Since deleting a non-existent property returns true, b) is closer to the
existing semantics.

Here's my alternative wording:
[[Delete]] (propertyKey) - Boolean: Removes the own property indentified
by the propertyKey parameter from the object. Return false if the property
was not deleted and is still present. Return true if the property was
deleted or was not present.

Cheers,
Tom
___
es-discuss mailing list
es-discuss@mozilla.org
https://mail.mozilla.org/listinfo/es-discuss