第3回まで無料

React 入門コース

Vite での環境構築から、JSX・コンポーネント・props・state・useEffect・フック・React Router・テストまで。全50レッスンで、タスク管理アプリを作ってビルドし、公開するところまで進みます。コードとテストの出力は、すべて React 19.3.0 と Vite 8.3.0 で実際に動かしたものです。

カリキュラム

全50レッスンを7つの章に分けています。第1章から順に進めるのがおすすめですが、 気になるところだけ拾い読みしてもかまいません。 ※ JSX はブラウザ内で実行できないため、第2回で作る Vite のプロジェクトで試してください。前提は JavaScript の基本です。

Chapter 1 — React を始める(第1〜7回)

React が画面の書き換えの何を引き受けてくれるのかを確かめ、Vite で開発環境を作り、JSX とコンポーネントの書き方を押さえます。最後は StrictMode と開発者ツールで、開発中の React の振る舞いを読めるようにします。

1

なぜ React か(DOM を直接書き換える方法との違い)

同じいいねボタンを素の JavaScript と React で作って比べる。「手順を書く」と「状態に対する画面を書く」の違いと、React が引き受けてくれる仕事。

Free
2

Vite で開発環境を作る

npm create vite で React のプロジェクトを作り、開発サーバーの起動、保存するとすぐ変わる HMR、本番用のビルドまで。index.html → main.jsx → App.jsx のつながり。

Free
3

JSX の正体(JSX は JavaScript の式)

JSX が jsx()・jsxs() という関数の呼び出しに変換されることを、Vite の変換器の出力で確かめる。className と書く理由、要素を 2 つ並べるとエラーになる理由まで。

Free
4

JSX に値を埋め込む・条件で出し分ける

JSX の {} に値や計算を埋め込み、関数と if・三項演算子・&& の 3 通りで表示を出し分ける。&& の左が 0 のときに画面に 0 が出てしまう落とし穴まで。

🔒 ベーシック
5

最初のコンポーネントを作る

コンポーネントは大文字で始まる「JSX を返す関数」。プロフィールカードを部品にして export・import で組み立てる。小文字で始めると表示されない理由と、import のエラーまで。

🔒 ベーシック
6

スタイルを当てる(className・CSS Modules・style)

CSS ファイル+className、クラス名をファイル専用にする CSS Modules、オブジェクトで渡す style 属性。3 つの方法が実際にどんな HTML になるかと使い分け。

🔒 ベーシック
7

StrictMode と開発者ツール

開発中に console.log や useEffect が 2 回動くのは StrictMode の働き。わざと不純に書いたコンポーネントで何を見つけてくれるのかを確かめ、React Developer Tools を入れる。

🔒 ベーシック

Chapter 2 — props とコンポーネント設計(第8〜14回)

props で値を渡し、children でレイアウトを組み、配列を map と key でリストにします。最後は商品カタログを部品に分けて組み立てます。

8

props でデータを渡す

親から子へ値を渡す props の書き方と受け取り方。"3" と {3} を取り違えると 3 + 1 が 31 になる理由と、props を書き換えてはいけない理由まで。

🔒 ベーシック
9

props の分割代入・デフォルト値・スプレッド

props を引数の位置で分割代入して受け取り、= でデフォルト値を決める。デフォルト値が null では効かないこと、{...obj} と ...rest で props をまとめて渡す書き方まで。

🔒 ベーシック
10

children でレイアウトを組む

開始タグと終了タグの間に書いた中身を children で受け取り、枠だけを受け持つ部品を作る。差し込み口が複数あるときは JSX をふつうの props で渡す。

🔒 ベーシック
11

配列を map でリスト描画する

配列を map で JSX の配列に変えてリスト表示する。filter と toSorted で整えてから表示し、空のときのメッセージを出す。key を付け忘れたときの警告まで。

🔒 ベーシック
12

key の役割(index を key にすると何が起きるか)

index を key にしたリストの先頭に行を足すと、入力欄の中身が別の行にずれる。key が「どの行がどのデータか」の目印であることと、key に使ってよい値。

🔒 ベーシック
13

コンポーネントの分け方

1 つの関数に全部入った注文画面を、見た目のまとまり・繰り返す単位・計算の 3 つの目安で分ける。分ける前と後で HTML が変わらないことをテストで確かめる。

🔒 ベーシック
14

【実践】商品カタログを組み立てる

props・children・リスト・key・分け方だけで、カテゴリ別の商品カタログを作りきる。セール価格と割引率、在庫バッジの出し分けまで。

🔒 ベーシック

Chapter 3 — state とイベント(第15〜22回)

useState で状態を持ち、イベントとフォームで画面を動かします。state がスナップショットであることとイミュータブルな更新を押さえ、最後は ToDo リストを作ります。

15

useState で状態を持つ

ふつうの変数を書き換えても画面が変わらない 2 つの理由と、それを引き受ける useState。state は置いた場所ごとに別々で、フックはトップレベルで呼ぶ。

🔒 ベーシック
16

イベントハンドラ(onClick・onChange・イベントオブジェクト)

onClick には関数そのものを渡す。() を付けたときの誤動作と Too many re-renders、e.target.value・preventDefault・stopPropagation の使い方、ハンドラを props で渡す命名まで。

🔒 ベーシック
17

state はスナップショット(更新関数で直す)

setCount(count + 1) を 3 回呼んでも 1 しか増えず、set の直後に読んでも古い値のまま。state がそのレンダーの時点の値であることと、更新関数・バッチ処理。

🔒 ベーシック
18

オブジェクトと配列の state をイミュータブルに更新する

直接書き換えて set しても画面が変わらない理由(Object.is の比較)と、スプレッドで新しいオブジェクトを作る書き方。配列の追加・削除・変更・並べ替えの型。

🔒 ベーシック
19

フォーム入力を制御コンポーネントで扱う

入力欄の値を state が決める制御コンポーネント。テキスト・セレクト・ラジオ・チェックボックスを 1 つの state とハンドラで扱い、値を加工してから入れる。よく出る 2 つの警告の原因まで。

🔒 ベーシック
20

フォーム送信とバリデーション

バリデーションを画面から切り離した関数にし、onSubmit と preventDefault で送信を受け取る。エラーを入力欄の近くに出し、aria-invalid・aria-describedby で読み上げにも伝える。

🔒 ベーシック
21

state のリフトアップ

兄弟のコンポーネントで同じ値を使いたいときは、state を共通の親に移して props で配る。アコーディオンと検索できる商品表で、リフトアップの前後を比べる。

🔒 ベーシック
22

【実践】ToDo リストを作る

何を state にしてどこに置くかを先に表で決めてから、追加・完了・削除・絞り込み・完了したものの一括削除までを組み立てる、第3章のまとめ。

🔒 ベーシック

Chapter 4 — 副作用とライフサイクル(第23〜30回)

useEffect を「外部システムとの同期」の道具として押さえ、依存配列・クリーンアップ・データ取得の競合状態まで扱います。最後は Suspense とエラーバウンダリも使って、検索できるユーザー一覧を作ります。

23

useEffect で外部と同期する

useEffect は React の外にあるもの(タブのタイトル・localStorage・タイマー・通信)を state に合わせるための場所。Effect が DOM に反映したあとに動くことまで。

🔒 ベーシック
24

依存配列と useEffectEvent

依存配列なし・[]・[a] で Effect がいつ動くかをログで比べる。依存配列に入れるのは読んでいる値すべて。オブジェクトで毎回動く理由と、React 19.2 からの useEffectEvent。

🔒 ベーシック
25

クリーンアップ関数(タイマー・イベントリスナー)

Effect から返す関数が後片付けになる。タイマー・window のイベント・接続を題材に、書いた版と書き忘れた版を比べる。StrictMode が書き忘れを見つける理由と、async 関数の落とし穴。

🔒 ベーシック
26

Effect が要らない場面

計算できる値はレンダー中に計算し、props が変わったときの state のリセットは key で、操作がきっかけの処理はイベントハンドラで。よくある 3 つの「要らない Effect」を比べる。

🔒 ベーシック
27

useEffect でデータを取得する(競合状態の対策)

あとから頼んだ返事が先に届くと、古い返事で表示が上書きされる。返事の順番を入れ替えた偽の API で競合状態を起こし、ignore フラグと AbortController で防ぐ。

🔒 ベーシック
28

ローディングとエラーを表示する

読み込み中・エラー・0 件・成功の 4 つの表示を、1 つの status で持つ。boolean を別々に持つと生まれる「ありえない組み合わせ」と、依存配列を使った再試行まで。

🔒 ベーシック
29

Suspense と use() とエラーバウンダリ

React 19 の use() で Promise を読み、読み込み中の表示を <Suspense>、エラーをエラーバウンダリに任せる。use() に渡す Promise のキャッシュと、テストでの act の落とし穴まで。

🔒 ベーシック
30

【実践】検索できるユーザー一覧

打ち終わってから検索するデバウンスと、古いリクエストの中止を 2 つの Effect に分けて書く、社員検索の画面。状態ごとの表示と、一致した部分の強調まで。

🔒 ベーシック

Chapter 5 — フックを使いこなす(第31〜38回)

useRef・useMemo・useCallback・useReducer・useContext とカスタムフックで、コンポーネントのロジックを整理します。主要な例には TypeScript 版も並べ、最後は useReducer と Context を組み合わせます。

31

useRef で DOM を操作する

useRef と ref 属性で DOM の要素を受け取り、フォーカスやスクロールに使う。React 19 の ref を props で渡す書き方、リストの要素ごとの ref、React 19.3 の Fragment の ref、TypeScript 版まで。

🔒 ベーシック
32

useRef で再レンダーしない値を持つ

useRef はレンダーをまたいで値を覚えておける入れ物。ストップウォッチのタイマーの ID を ref に持ち、ref を変えても画面が変わらないことを state と比べる。使い分けの基準と TypeScript 版。

🔒 ベーシック
33

useMemo で計算結果を覚えておく

useMemo で重い計算の結果を覚え、関係のない再レンダーで計算し直さない。絞り込みの関数が呼ばれた回数を数えて効き目を確かめ、使うべき場面と React Compiler に触れる。

🔒 ベーシック
34

memo と useCallback で再レンダーを抑える

memo で包むと props が同じときに子の描き直しを飛ばせる。ただし親が毎回新しい関数を渡すと効かない。子のレンダー回数を数え、memo なし・memo だけ・memo+useCallback を比べる。

🔒 ベーシック
35

useReducer で状態の更新をまとめる

state の更新の仕方を reducer という 1 つの関数にまとめ、コンポーネントは dispatch で「何が起きたか」を伝えるだけにする。カートを題材に、reducer を画面なしで試し、TypeScript で action の書き間違いを防ぐ。

🔒 ベーシック
36

useContext で深い階層に値を渡す

props のバケツリレーをせずに、上で決めた値を下のどこからでも読める Context。作る・渡す・読むの 3 手順と、いちばん近い Provider が勝つ性質、React 19 の書き方の変化まで。

🔒 ベーシック
37

カスタムフックでロジックを再利用する

フックを使ったロジックを use で始まる関数に切り出す。オンライン状態・localStorage への保存・入力の待ち合わせをフックにし、renderHook でフックだけをテストする。フックのルールを破ったときのエラーまで。

🔒 ベーシック
38

useReducer と Context を組み合わせる

useReducer の結果を Context で配る Provider を作り、アプリのどこからでも state を読み、dispatch で更新できるようにする。tasks と dispatch を分ける理由と、包み忘れをエラーにするカスタムフック。

🔒 ベーシック

Chapter 6 — ルーティングと状態管理(第39〜45回)

React Router でページを分け、URL パラメータ・ネストしたルート・loader と action でデータを扱います。グローバル状態、React 19 のフォーム、Vitest と Testing Library によるテストまで進みます。

39

React Router でページを分ける

URL に応じて表示するコンポーネントを切り替えるルーティング。React Router 8 でルートの表を作り、Link・NavLink・useNavigate で移動し、404 のページとテストでの描き方まで。

🔒 ベーシック
40

URL パラメータと動的ルート

/products/:productId のように URL の一部が変わるルートを作り、useParams で読み取る。並び順を ?sort=price のクエリ文字列に持たせる useSearchParams と、URL に持たせる利点まで。

🔒 ベーシック
41

ネストしたルートと Outlet

ルートを入れ子にして、親のコンポーネントを共通の枠にし、子を <Outlet /> に表示する。設定ページのタブ(入れ子の入れ子)、移動しても枠が作り直されないこと、useOutletContext まで。

🔒 ベーシック
42

loader と action でデータを扱う

ページを出す前にデータを読む loader と、フォームの送信を受け取る action。連絡先アプリで検索・詳細・新規作成・削除を作り、保存後に一覧が自動で読み直されることを確かめる。

🔒 ベーシック
43

グローバル状態を管理する(useSyncExternalStore)

React の外に「値を持ち、変わったら知らせる」小さなストアを作り、useSyncExternalStore で読む。Provider なしで離れた部品どうしが値を共有し、選んだ値が変わった部品だけが描き直される。

🔒 ベーシック
44

React 19 のフォーム(useActionState・useOptimistic)

<form action> に関数を渡す React 19 のフォーム。送信の結果を受け取る useActionState、送信中を知る useFormStatus、返事を待たずに画面に出す useOptimistic を、メッセージとチャットで確かめる。

🔒 ベーシック
45

コンポーネントをテストする(Vitest・Testing Library)

利用者から見て画面がどう動くかを確かめるコンポーネントのテスト。Vitest と Testing Library の設定、render → 探す → 操作 → 確かめるの 4 手順、getBy・queryBy・findBy、API の差し替えまで。

🔒 ベーシック

Chapter 7 — アプリを仕上げる(第46〜50回)

これまでの部品を使ってタスク管理アプリを設計し、追加・編集・削除と保存、URL での絞り込みを実装します。最後は Profiler で再レンダリングを測って減らし、ビルドして公開します。

46

タスク管理アプリを設計する

コードを書く前に、できること・コンポーネントの木・どれが state か・どこに置くかを表にする。state を 1 つも持たない「静的な版」で見た目を完成させるところまで。

🔒 ベーシック
47

タスクの追加・編集・削除と保存

静的な版に state をつなぎ、タスクの追加・完了・編集・削除と localStorage への保存を作る。保存データを読むときに形を確かめ、壊れていても止まらないようにする。今日の日付の作り方まで。

🔒 ベーシック
48

絞り込み・並べ替えを URL で持つ

状態・並び順・検索語での絞り込みを URL のクエリに持たせる。絞り込みは画面と関係のない関数で毎回計算し、URL の知らない値はデフォルトに戻し、setSearchParams で前の値を引き継ぐ。

🔒 ベーシック
49

再レンダリングを減らす(Profiler で測る)

描き直しの回数を数えてから、state の置き場所と memo で減らす。入力のたびに全行が描き直される遅い版と比べ、<Profiler> で描き直しの時間を受け取る方法と置き場所の注意まで。

🔒 ベーシック
50

ビルドして公開する(総まとめ)

タスク管理アプリを本番用にビルドし、ハッシュ付きのファイル・サブパス用の base・VITE_ の環境変数・SPA を配信するサーバーの設定を押さえる。公開前のチェックとシリーズ全体の振り返り。

🔒 ベーシック

全50レッスンを終えたら、次はサーバーまで含めてアプリを作る Next.js へ。メンバーシップで全コースが解放されます。