跳至內容

錯誤處理

本文說明如何處理開發、伺服器端和客戶端錯誤。

處理開發中的錯誤

在開發 Next.js 應用程式期間發生執行階段錯誤時,您會遇到一個覆蓋視窗。它是一個覆蓋網頁的模態視窗。它在開發伺服器使用 next dev 透過 pnpm devnpm run devyarn devbun dev 執行時才會顯示,且在正式環境中不會顯示。修正錯誤後,覆蓋視窗會自動關閉。

以下是覆蓋視窗的範例

Example of an overlay when in development mode

處理伺服器錯誤

Next.js 預設提供一個靜態的 500 頁面來處理應用程式中發生的伺服器端錯誤。您也可以透過建立 pages/500.js 檔案來自訂此頁面

在應用程式中設置 500 頁面並不會向應用程式使用者顯示特定的錯誤訊息。

您也可以使用404 頁面來處理特定的執行階段錯誤,例如「找不到檔案」。

處理客戶端錯誤

React 的錯誤邊界是一種優雅地處理客戶端 JavaScript 錯誤的方法,讓應用程式的其他部分可以繼續運作。除了防止頁面崩潰之外,它還允許您提供自訂的後備元件,甚至記錄錯誤資訊。

要在 Next.js 應用程式中使用錯誤邊界,您必須建立一個類別元件 ErrorBoundary,並在 pages/_app.js 檔案中將 Component prop 包裹起來。此元件將負責:

  • 在拋出錯誤後渲染後備 UI
  • 提供重置應用程式狀態的方法
  • 記錄錯誤資訊

您可以透過繼承 React.Component 來建立 ErrorBoundary 類別元件。例如:

class ErrorBoundary extends React.Component {
  constructor(props) {
    super(props)
 
    // Define a state variable to track whether is an error or not
    this.state = { hasError: false }
  }
  static getDerivedStateFromError(error) {
    // Update state so the next render will show the fallback UI
 
    return { hasError: true }
  }
  componentDidCatch(error, errorInfo) {
    // You can use your own error logging service here
    console.log({ error, errorInfo })
  }
  render() {
    // Check if the error is thrown
    if (this.state.hasError) {
      // You can render any custom fallback UI
      return (
        <div>
          <h2>Oops, there is an error!</h2>
          <button
            type="button"
            onClick={() => this.setState({ hasError: false })}
          >
            Try again?
          </button>
        </div>
      )
    }
 
    // Return children components in case of no error
 
    return this.props.children
  }
}
 
export default ErrorBoundary

ErrorBoundary 元件會追蹤 hasError 狀態。此狀態變數的值是一個布林值。當 hasError 的值為 true 時,ErrorBoundary 元件將渲染後備 UI。否則,它將渲染子元件。

建立 ErrorBoundary 元件後,將其匯入 pages/_app.js 檔案中,以在 Next.js 應用程式中包裹 Component prop。

// Import the ErrorBoundary component
import ErrorBoundary from '../components/ErrorBoundary'
 
function MyApp({ Component, pageProps }) {
  return (
    // Wrap the Component prop with ErrorBoundary component
    <ErrorBoundary>
      <Component {...pageProps} />
    </ErrorBoundary>
  )
}
 
export default MyApp

您可以在 React 的文件中了解更多關於錯誤邊界的資訊。

錯誤回報

要監控用戶端錯誤,請使用像是 Sentry、Bugsnag 或 Datadog 之類的服務。