Closed Bug 960508 Opened 10 years ago Closed 10 years ago

Reimplement DOMException by hand as a subclass of Error so that DOMException.prototype.toString() stops throwing

Categories

(Core :: DOM: Core & HTML, defect)

26 Branch
x86_64
Windows 7
defect
Not set
normal

Tracking

()

RESOLVED WONTFIX

People

(Reporter: vkhomyackov, Unassigned)

References

(Blocks 1 open bug)

Details

User Agent: Mozilla/5.0 (Windows NT 6.1; WOW64; rv:26.0) Gecko/20100101 Firefox/26.0 (Beta/Release)
Build ID: 20131205075310

Steps to reproduce:

Evaluate in Firefox 26 following JavaScript snippet:
    DOMException.prototype.toString()
or
    DOMException.prototype + ''

Test page: http://jsfiddle.net/K6zbm/


Actual results:

Exception is thrown:
TypeError: 'toString' called on an object that does not implement interface DOMException.


Expected results:

Expression should return string 'DOMException' or something like.
Works fine with current Nightly.
> Works fine with current Nightly.

Uh... no, it does not.

It's not clear to me what it should do per spec (e.g. should DOMException even have non-default toString per spec?), but the reason it doesn't work right now is that it's a WebIDL interface with a stringifier, and the toString expects a DOMException object.  And DOMException.prototype is not a DOMException object...
(In reply to Boris Zbarsky [:bz] from comment #2)
> It's not clear to me what it should do per spec (e.g. should DOMException
> even have non-default toString per spec?),

Not according to the spec.  All that information that gets returned by the stringifier, can we make it part of the object's message, so that it can be exposed just via Error.prototype.toString?  Blink seems to have a DOMException.prototype.toString but it looks like it has the same behaviour as Error.prototype.toString.
That wouldn't actually help this particular case on its own, because:

  Error.prototype.toString.call(DOMException.prototype)
  TypeError: 'name' getter called on an object that does not implement interface
             DOMException.

We'd need to make DOMException an actual Error subclass to make this work right (and in particular give the proto an own "name" property.  Worth doing, I guess, if we don't have an existing bug on this.

Moving stuff into the message is a PITA from a performance standpoint, because it forces eager creation of the string, which is not cheap if we want to include things like the filename/lineno/etc in it.  :(
Component: General → DOM
(In reply to Boris Zbarsky [:bz] from comment #4)
> That wouldn't actually help this particular case on its own, because:
> 
>   Error.prototype.toString.call(DOMException.prototype)
>   TypeError: 'name' getter called on an object that does not implement
> interface
>              DOMException.

Oh, sure.  I should've said I think this exception being thrown is correct.

> We'd need to make DOMException an actual Error subclass to make this work
> right (and in particular give the proto an own "name" property.  Worth
> doing, I guess, if we don't have an existing bug on this.

The spec already does require DOMException.prototype.__proto__ == Error.prototype.

> Moving stuff into the message is a PITA from a performance standpoint,
> because it forces eager creation of the string, which is not cheap if we
> want to include things like the filename/lineno/etc in it.  :(

True, that's not great.
> The spec already does require DOMException.prototype.__proto__ == Error.prototype.

Sure; I mean we'd need to make it not a WebIDL interface; it needs quite different behavior from those.
Whiteboard: [mentor=bz][lang=python][lang=c++]
I think that is the main reason why we use "exception" and not "interface" in the specification. It's also the main reason I've been pushing to get DOMException defined in the IDL specification directly, as we do not really want to mint other exceptions going forward.
Is DOMException is going to be the only exception type we need to introduce like this?  If so, it's simpler to just hand-code it up than setting up codegen based on IDL, for sure...
Yes, Allen (Mozilla, TC39) is pushing to use standard JavaScript exceptions. On the DOM side we've been pushing people to not go beyond DOMException.
Sounds great.  

I'm going to be a bad person and morph this bug.  ;)

Unfortunatelyy, we still need to figure out what to do about the message...  I wish we could just use a getter on instances instead of a value property and compute it lazily.
Status: UNCONFIRMED → NEW
Ever confirmed: true
Summary: DOMException.prototype.toString() throws error → Reimplement DOMException by hand as a subclass of Error so that DOMException.prototype.toString() stops throwing
I guess one issue with hand-coding this is xrays; do we need xrays for DOMException in general?
Flags: needinfo?(bobbyholley+bmo)
(In reply to Boris Zbarsky [:bz] from comment #11)
> I guess one issue with hand-coding this is xrays; do we need xrays for
> DOMException in general?

Yes, I think we want them. Exceptions are the exact kind of thing that tend to bubble up into privilege scopes, and Xrays to them are important.
Flags: needinfo?(bobbyholley+bmo)
Also, reimplementing by hand would be annoying given all the ExceptionMembers bits.  :(
One other note: this doesn't work in Chrome either.  Or in Safari.  Or IE.

Given that, I'm going to wontfix this bug, though note that the changes in bug 997285 will make this not throw anyway (but return "Error" instead).
Status: NEW → RESOLVED
Closed: 10 years ago
Resolution: --- → WONTFIX
Whiteboard: [mentor=bz][lang=python][lang=c++]
Seems like there is still some follow up in the specification to be done. E.g. whether "exception" should be kept around next to "interface".
Sure.  Note that in bug 997285 I'm mostly ignoring what the spec has to say for the moment in favor of improving the status quo incrementally...
Component: DOM → DOM: Core & HTML
You need to log in before you can comment on or make changes to this bug.