• システム開発に関わる内容をざっくりと書いていく

React エラーハンドリング

エラーハンドリング:失敗しても落ちないアプリを作る

Reactアプリを作っていて、APIエラーで画面が真っ白になったり、原因不明のクラッシュが発生したりしたことはないだろうか?
そんなときに必要なのが、適切なエラーハンドリング

「落ちないアプリ」=現場で信用されるアプリ。そのための考え方と実装をまとめていく。


エラーハンドリングのポイント

Reactにおけるエラー処理は、大きく3つのレイヤーに分けられる。

  1. API呼び出し時のエラー
  2. データ形式・構造のエラー
  3. UIコンポーネントのレンダリングエラー(例外)

1. API呼び出し時のエラー(ネットワーク・Axios)

まずは非同期処理で最もよくあるパターン。AxiosなどでAPIを叩いたときに失敗するケース。

tsx
try {
const res = await axios.get<User[]>('https://jsonplaceholder.typicode.com/users');
setUsers(res.data);
} catch (error) {
setError("データの取得に失敗しました");
}
  • try-catchで囲むだけで通信エラーやレスポンスエラーを捕捉できる
  • error.messageerror.responseを使って詳細表示も可能

2. データ構造やJSONのエラー

取得できたとしても、「中身の構造が違う」「JSONの形式が崩れている」などのエラーもある。

型チェックをしっかりする

tsx
type User = {
id: number;
name: string;
email: string;
};

if (!Array.isArray(data)) throw new Error("データ形式が不正です");

zodio-tsを使えば、データ構造のバリデーションも可能。


3. レンダリング時のクラッシュを防ぐ:Error Boundary

Reactは、レンダリング中のエラーでコンポーネント全体が落ちることがある
そんなときに使うのが ErrorBoundary

tsx
class ErrorBoundary extends React.Component {
state = { hasError: false };

static getDerivedStateFromError() {
return { hasError: true };
}

componentDidCatch(error, info) {
console.error(error, info);
}

render() {
if (this.state.hasError) return <p>エラーが発生しました</p>;
return this.props.children;
}
}
tsx
<ErrorBoundary>
<UserList />
</ErrorBoundary>

UIとしての「エラー表示」も大事

tsx
if (isLoading) return <p>読み込み中...</p>;
if (error) return <p className="text-red-500">{error}</p>;
  • ユーザーは「何が起きたか」が分からないと離脱する
  • 「ちょっと待って」「もう一度やってね」があるだけで印象が大きく違う

状態の整理

tsx
const [users, setUsers] = useState<User[]>([]);
const [error, setError] = useState<string | null>(null);
const [loading, setLoading] = useState<boolean>(true);
  • 3つの状態(データ/エラー/ローディング)を明確に管理
  • 状態ごとにレンダリングを切り替える

よくあるエラーケースまとめ

エラータイプ原因例対策
ネットワークエラー接続タイムアウト・404/500エラーなどtry-catchで包む・タイムアウト設定
JSON構文エラーサーバーが壊れたレスポンスを返してきたresponse.text()で中身をチェック
データ構造不整合必要なプロパティがnull / undefined型ガードやバリデーション(Zodなど)
レンダリング中例外存在しない値を使おうとしてundefined.propになるOptional ChainingErrorBoundaryでガード

👇 サンプル:エラーハンドリング実装付き ユーザー一覧アプリ


まとめ

  • エラーハンドリングは失敗したときにユーザーに安心感を与えるための設計
  • 3つの視点(通信・構造・レンダリング)でそれぞれ対策が必要
  • 状態(ローディング・エラー・成功)ごとにUIを明確に分けて表示するのが鉄則
  • ちゃんとしたエラー処理があるだけで、アプリの信頼性は段違いに上がる