在react尋找錯誤處理,看到一個有趣的名詞叫Error Boundaries,好像沒有中文名詞但大致的意思是錯誤的邊界。當發生錯誤時限縮錯誤範圍,不會影響到其它UI原件仍可繼續操作。而 Error Boundaries 也可定義成元件形成一個新的lifecycle,稱為 componentDidCatch(error, info) ,這比以往傳統的 try{}catch{} 方便操作。以下簡單修改官方範例,讓大家體會一下Error Boundaries與 try{}catch{} ,但在handle發生錯誤還是需要靠 try{}catch{} 才有辦法進行捕捉。
src/ErrorBoundary.js
import React, { Component } from 'react';
class ErrorBoundary extends React.Component {
  constructor(props) {
    super(props);
    this.state = { error: null, errorInfo: null };
  }
  componentDidCatch(error, errorInfo) {
    // Catch errors in any components below and re-render with error message
    this.setState({
      error: error,
      errorInfo: errorInfo
    })
    // You can also log error messages to an error reporting service here
  }
  render() {
    if (this.state.errorInfo) {
      // Error path
      return (
        <div>
          <h2>Something went wrong.</h2>
          <details style={{ whiteSpace: 'pre-wrap' }}>
            {this.state.error && this.state.error.toString()}
            <br />
            {this.state.errorInfo.componentStack}
          </details>
        </div>
      );
    }
    // Normally, just render children
    return this.props.children;
  }
}
export default ErrorBoundary;
src/ErrorCounter.js
import React, { Component } from 'react';
class ErrorCounter extends React.Component {
  constructor(props) {
    super(props);
    this.state = { counter: 0, error: null };
    this.handleClick = this.handleClick.bind(this);
  }
  handleClick() {
    this.setState(({counter}) => ({
      counter: counter + 1
    }),
    function(){
      console.log(this.state.counter)
      try {
        if(this.props.action === "handleClick" && this.state.counter === 3) {
          throw new Error('handleClick error!!');
        }
      } catch (error) {
        this.setState({ error: error });
      }
    });
  }
  render() {
    if (this.state.counter === 5) {
      throw new Error('error!!');
    } else if(this.state.error !== null) {
      return <h1>{this.state.error}</h1>;
    }
    return <h1 onClick={this.handleClick}>{this.state.counter}</h1>;
  }
}
export default ErrorCounter;
src/index.js
import React from 'react';
import ReactDOM from 'react-dom';
import ErrorBoundary from './ErrorBoundary';
import ErrorCounter from './ErrorCounter';
import registerServiceWorker from './registerServiceWorker';
const App = () => (
  <div>
    <ErrorBoundary>
      <ErrorCounter />
    </ErrorBoundary>
    <ErrorBoundary>
      <ErrorCounter action={"handleClick"} />
    </ErrorBoundary>
  </div>
)
ReactDOM.render(
  <App /> ,
  document.getElementById('root'));
registerServiceWorker();
輸出畫面
此error畫面開發模式才會顯示
ErrorBoundary補捉畫面
try{}catch{}補捉畫面
參考資料:Error Boundaries
https://reactjs.org/docs/error-boundaries.html