C
React/状態管理/Lesson 08

フォーム処理

30分·theory
このチャプター
2/2
JavaScript

フォーム処理

💡 なぜ学ぶべきか?

🎯 ログイン、会員登録、検索など、あらゆるウェブサイトの入力フォームを作成するために不可欠です。
💼 ユーザーが入力した値をリアルタイムで検証し、エラーをすぐに表示できます。
フォームデータをサーバーへ送信する前に正しいかどうかを確認するための基礎技術です。
🏢 실무에서는
実務では、会員登録フォームでパスワード入力時に「8文字以上必要」といったリアルタイムフィードバックを表示したり、メールアドレス重複確認ボタンを押した際に入力値をサーバーへ送信したりするために使われます。ECサイトの決済フォームもすべてこのパターンで構築されています。

フォーム処理パターン

Reactフォーム処理

制御コンポーネント vs 非制御コンポーネント

方式特徴用途
制御 (Controlled)Reactが値を管理リアルタイムバリデーション
非制御 (Uncontrolled)DOMが値を管理シンプルなフォーム
React 19 Actionsサーバーアクション連携Next.js App Router

2025年のフォームライブラリ

  • React Hook Form: パフォーマンス最適化、非制御ベース
  • Zod: スキーマベースのバリデーション
  • React 19 Actions: 組み込みフォーム処理
💻 フォーム処理の実践
import { useState, useActionState } from "react";

// 1. 制御コンポーネント
function LoginForm() {
  const [email, setEmail] = useState("");
  const [password, setPassword] = useState("");
  const [errors, setErrors] = useState<Record<string, string>>({});

  const validate = () => {
    const errs: Record<string, string> = {};
    if (!email.includes("@")) errs.email = "有効なメールアドレスを入力してください";
    if (password.length < 8) errs.password = "8文字以上入力してください";
    setErrors(errs);
    return Object.keys(errs).length === 0;
  };

  const handleSubmit = (e: React.FormEvent) => {
    e.preventDefault();
    if (validate()) {
      console.log("ログイン:", { email, password });
    }
  };

  return (
    <form onSubmit={handleSubmit} className="space-y-4">
      <div>
        <input type="email" value={email} onChange={e => setEmail(e.target.value)}
          className={`border rounded px-3 py-2 w-full ${errors.email ? "border-red-500" : ""}`}
          placeholder="メールアドレス" />
        {errors.email && <p className="text-red-500 text-sm">{errors.email}</p>}
      </div>
      <div>
        <input type="password" value={password} onChange={e => setPassword(e.target.value)}
          className="border rounded px-3 py-2 w-full" placeholder="パスワード" />
        {errors.password && <p className="text-red-500 text-sm">{errors.password}</p>}
      </div>
      <button type="submit" className="bg-blue-500 text-white px-4 py-2 rounded w-full">
        ログイン
      </button>
    </form>
  );
}

// 2. React 19 Actions (Next.js)
async function submitForm(prevState: any, formData: FormData) {
  const email = formData.get("email") as string;
  const password = formData.get("password") as string;
  if (!email.includes("@")) return { error: "有効なメールアドレスを入力してください" };
  // API呼び出し
  return { success: true };
}

function ActionForm() {
  const [state, action, isPending] = useActionState(submitForm, null);
  return (
    <form action={action}>
      <input name="email" type="email" />
      <input name="password" type="password" />
      <button disabled={isPending}>{isPending ? "処理中..." : "送信"}</button>
      {state?.error && <p className="text-red-500">{state.error}</p>}
    </form>
  );
}

💡 💡 フォーム処理のヒント

  • シンプルなフォーム: useState + 手動バリデーション
  • 複雑なフォーム: React Hook Form + Zod
  • Next.js: Server Actions + useActionState
  • React 19: <form action={fn}> パターンが標準化

この概念はReactコンポーネント開発において核心的なものです。Reactの宣言的UIパラダイムを理解し、propsとstateの違いを明確に区別してください。コンポーネントは、同じ入力(props)に対して常に同じ出力(JSX)を返す純粋関数のように動作する必要があります。

⚛️ Reactパターン — フォーム処理

フォーム処理をReactでどのように使うか、コードとともにステップごとに学んでいきましょう。
1 🧩 1. フォーム処理を使うシナリオ
この機能が必要な場面。
2 💻 2. コードを書く
フォーム処理の基本的な使い方。
3 🎨 3. レンダリング結果
ユーザーが見る画面。
4 💡 4. 実践的なヒント
よくある落とし穴とベストプラクティス。

📝 フォーム — 制御コンポーネント

コードを直接編集すると、0.7秒後に自動的に反映されます。React 18 + Babelによってブラウザ上で即座に実行されます。
🖥️ 実行結果 — レンダリングされたReactコンポーネント
✏️ React 코드 수정하기 (클릭해서 열기)
⚛️ React 18 + Babel Standalone — まず結果を確認し、エディタで自由に編集できます。

理解度チェック

制御コンポーネント (Controlled Component) とは何ですか?
💡 制御コンポーネントは、input の value を state で管理します。onChange -> setState -> value というフローで React が入力値を完全に制御します。非制御コンポーネントは ref を使って DOM から直接値を読み取ります。
先に読むとよい概念: useState
次のおすすめ: useEffect
フォーム処理 - React