
Error Handling in React 16 - darwhy
https://facebook.github.io/react/blog/2017/07/26/error-handling-in-react-16.html
======
dguo
It's interesting that this is a case where React does need to somewhat
reinvent the wheel. The best aspect of JSX is that you can use native JS
constructs. So instead of a custom HTML attribute (e.g. ng-if in Angular, v-if
in Vue), you can just use a JS if statement.

It makes me wonder what a UI language/system would look like if it were
designed from the ground up to be declarative. Would it end up just looking a
lot like React?

Anyway, this looks useful. Error handling is one of the harder aspects of
programming in my experience, so I'm glad this exists now.

~~~
jordwest
> It makes me wonder what a UI language/system would look like if it were
> designed from the ground up to be declarative. Would it end up just looking
> a lot like React?

You could find one answer to that question in Elm[1], and indeed it does look
a lot like React. Although it generally handles exceptions by never letting
them happen in the first place :)

[1] [http://elm-lang.org/](http://elm-lang.org/)

~~~
i6ruce
I would say, React looks like Elm but more imperative.

------
tobyjsullivan
This is awesome! I'm relatively new to React - just a few months in - but have
already hit these cryptic errors and struggled to diagnose. This will help not
just general stability of apps, but probably troubleshooting these errors as
well (via ability to reduce the impact area of crashes).

------
armandososa
Thanks Dan and React team!

Question: Will this resolve these cases:
[https://twitter.com/dan_abramov/status/770917958713544704](https://twitter.com/dan_abramov/status/770917958713544704)?
or we should keep catching immediately after an ajax request?

~~~
danabramov
If you don't add an error boundary, and you get an exception, then the app
will unmount. The error will get logged to console in development even if the
app swallows the error. So yes, it will help notice (and fix) such issues
sooner. But I still recommend the explicit then(onSuccess, onError) form so
that unhandled exceptions go through the top of the stack and register as
uncaught errors in DevTools.

------
rawrmaan
I love it! So clean and well thought out. Great job as always, React team.

------
hungerstrike
Why not let components catch their own errors?

~~~
mattashii
When a component throws, it means the user's code has encountered an
unexpected error. That means the component is in an unexpected state, and you
cannot reasonably say that that component can rebuild it's (internal) state to
a stable (and renderable) state.

~~~
rtpg
but in theory at that point in the operation, we're still in the process of
building a new DOM (hence the old DOM is still around)? So you could replace
the component with an error node and during the diffing process replace with
the old node?

Not great but if you hit a fatal error you hit a fatal error

~~~
beaconstudios
personally I would rather a website tell me that an error occurred using the
new mechanism than fall back to a previous version of the DOM and have me
wondering why clicking that button isn't doing anything.

------
pspeter3
Is there a way to wrap event listeners as well?

~~~
danabramov
Not currently. This might be on the table in the future but it's less clear
what semantics would be desirable. Feel free to open an issue.

~~~
pspeter3
Thanks! We wrap handlers for Asana since we're unsure if our data store is in
a sane state after an error. The logic is much the same as the error boundary

------
grandalf
This looks great. It's a smart way to use the encapsulation offered by
components in a sensible way for error handling.

------
joshuahutt
I was skeptical at first, but after reading through how it works and why it
was done, I love it. In fact, it would have made quite a few bugs much easier
to track down.

------
skratlo
This is not very useful because it only allows for error handling based on JS
exceptions, which is rarely used (and in fact shouldn't be) for user defined
error states. It also won't work with Promises, generators, async functions,
etc. unless you setState({hasError: true}) on your error boundary differently
than with componentDidCatch(). I'm not sure how this is useful in dev time, or
how this is useful in productions. Throw when input invalid?

~~~
danabramov
This is not meant for user errors.

This feature is for gracefully recovering from JavaScript errors that occur in
production as a result of programmer mistakes.

For example, Facebook heavily uses error boundaries in ads code. Even if one
widget fails rendering, it doesn’t take down the entire page. You’re _going_
to have some runtime errors if you use JavaScript, but this feature ensures
you can gracefully recover from them (instead of just breaking the whole app
as React 15 and earlier did).

There are two other effects of this change:

* React no longer has its own cryptic errors (because it doesn’t get “confused” when user code throws, and can cleanly fail fast if there is no error boundary).

* Errors reported to the boundaries have a _component_ stack trace attached to that, so you can know where exactly in the hierarchy the failure occurred. This can be pretty useful when debugging.

I hope this helps!

