错误边界

React 16 增加

  • 防止某个组件的 UI 渲染错误导致整个应用崩溃
  • 子组件发生 JS 的错误,有备用的渲染 UI
  • 错误边界是一个组件,且只能用 class 组件来写

例子:

  1. class Test extends React.Component{
  2. render(){
  3. return (
  4. <div>{data.title}</div> // 这里出错
  5. );
  6. }
  7. }
  8. class Test extends React.Component{
  9. render(){
  10. return (
  11. <p>Thins is content</p>
  12. );
  13. }
  14. }
  15. class App extentds React.Component{
  16. render(){
  17. return (
  18. <div>
  19. <Sub />
  20. <Test />
  21. </div>
  22. )
  23. }
  24. }
  25. ReactDOM.render(
  26. <App />,
  27. document.getElementById('app')
  28. );

整个应用是崩溃了,由 Test 组件引用一个未定义的 data 引起。

加上错误边界例子:

static getDerivedStateFromError(error) 生命周期函数

  • 参数: 子组件抛出的错误
  • 返回值: 新的 state
  • 作用:获取捕获错误,修改错误状态
    • 渲染备用的 UI
    • 渲染阶段调用 、不允许出现副作用(主要是操作 DOM 或异步的操作 setTimeout 等)

componentDidCatch(error, info) 原型上的方法
边界错误组件捕获异常,并进行后续处理

  • 参数:
    • error 抛出的错误
    • info 组件引发错误相关的信息 组件栈
  • 作用:
    • 错误信息获取
    • 运行副作用
  • 在组件抛出错误后调用
  • 在开发环境中 componentDidCatch 会把错误向上冒泡到 window,
    window.onerror = function(err){console.log(err);}
    在生产环境是不行的 ```jsx / mistake 是人为的导致的失误, error 是客观引起偏离轨道的 bound -> bind 绑定 带子 线 bund -> ou ->o ->i ary 名词后缀 -> 边界 / class ErrorBoundary extends React.Component { state = { hasError: false, };

    static getDerivedStateFromError(error) { console.log(error); // data is not defined return { hasError: true }; }

    componentDidCatch(error, info){

    1. console.log(error, info); // data is not defined
    2. // info: componentStack

    }

    render() { if (this.state.hasError) {

    1. return <h1>This is Error UI</h1>;

    }

    return this.props.children; } }

class Test extends React.Component{ render(){ return (

{data.title}
// 这里出错 ); } }

class Sub extends React.Component{ render(){ return (

Thins is content

); } }

class App extentds React.Component{ render(){ return (

) } }

```

无法捕获的场景

  1. 事件处理函数
  2. 异步代码
  3. 服务端渲染
  4. 错误边界内部的错误

    1. 错误边界有冒泡机制

      错误边界组件捕获错误的时机

  5. 渲染时

  6. 生命周期函数中
  7. 组件树的构造函数中

如果多个嵌套错误边界组件,则从最里层错误出发,向上冒泡出发捕获,
即错误边界公可以捕获其子组件的错误

组件栈追踪

显示出在哪里现在错误,从里到外一层一层地定位。
其依赖 @babel/plugin-transform-react-jsx-source 这个插件,仅用于开发环境。生产环境禁用。

try / catch

仅用于命令代码 (imperative code)
而错误边界是保留 React 的声明性质。错误边界是针对于渲染时的错误,所以事件处理函数的错误是不会被捕获的。
如果用对事件处理函数捕获错误,用 try / catch 即可。