•10 min read

Next.js Server Actions

Next.js Server Actions

Reactがフロントエンドエコシステムに革命をもたらした当初、クライアントサイドロジックとサーバーサイドのデータ取得は厳密に分離されていました。長年にわたり、Next.jsはこのギャップを着実に埋めてきました。最初はgetServerSidePropsとgetStaticPropsで、次にApp RouterとServer Componentsで。しかし、ミューテーションについてはどうでしょうか?クライアントからサーバーへ、独自のAPIエンドポイントを構築する手間なく、シームレスにデータを送信するにはどうすればよいでしょうか?

そこで登場するのがServer Actionsです。Next.js 13でアルファ機能として導入され、Next.js 14で安定版となったServer Actionsは、Reactアプリケーションにおけるフルスタックのデータミューテーションのルールを根本的に書き換えます。この詳細な解説では、Server Actionsの仕組み、そのセキュリティ上の影響、そしてキャッシュ、プログレッシブエンハンスメント、Reactの進化するプリミティブフックとの相互作用について掘り下げていきます。

Audio Briefing
0:00 / 0:00

従来のミューテーションの問題点

Server Actionsが登場する前は、Reactアプリケーションにおける典型的なフォーム送信には、相互接続された多数の要素が必要でした。

  1. クライアントサイドの状態管理: useStateまたはreact-hook-formのような複雑なフォームライブラリを使用した制御された入力。
  2. APIルート: ペイロードを受信して処理するための専用のバックエンドエンドポイント(例: /api/submit)。
  3. フェッチロジック: fetchまたはデータフェッチライブラリ(React QueryやSWRなど)を使用して、ペイロードを送信し、ローディング状態を処理し、レスポンスを解析する。
  4. エラーハンドリング: サーバーサイドの検証エラーをクライアントサイドの状態に同期させる。
  5. 再検証: UIが変更されたデータを反映するように、手動で再フェッチをトリガーする。

このアプローチは機能的ではあるものの、かなりのボイラープレートとネットワークウォーターフォールを発生させました。また、開発者はフロントエンドコンポーネントとバックエンドAPIルートの密結合を強いられました。

Advertisement

Server Actionsの内部動作

Server Actionは、その核となる部分で、サーバー上で定義され、クライアントまたはサーバーコンポーネントから直接呼び出すことができる非同期関数です。"use server"ディレクティブで関数を定義すると、Next.jsはコンパイルステップを実行し、その関数が公開される方法を根本的に変換します。

// actions.ts
"use server";

import { db } from "@/lib/db";
import { revalidatePath } from "next/cache";

export async function createPost(formData: FormData) {
  const title = formData.get("title");
  
  await db.post.create({
    data: { title: title as string }
  });

  revalidatePath("/posts");
}

クライアントコンポーネントからこの関数をインポートして呼び出すと、Next.jsは関数のコードをクライアントバンドルに含めません。代わりに、バンドラーはリモートプロシージャコール(RPC)メカニズムを作成します。クライアントバンドルはプロキシ関数を受け取ります。このプロキシが実行されると、アクションの識別子とその引数を含むHTTP POSTリクエストをNext.jsサーバーに送信します。

サーバーはペイロードをデコードし、元の関数を安全に実行し、結果(およびUIの更新や再検証の指示)を返します。このプロセス全体で明示的なAPIルートは不要になり、ボイラープレートと認知負荷が大幅に削減されます。

Next.jsキャッシュとの深い統合

Server Actionsの最も強力な側面の1つは、Next.js App Routerキャッシュとの深い統合です。従来のRESTまたはGraphQLミューテーションでは、サーバー上のデータを更新すると、クライアントサイドのキャッシュを手動で無効にする必要があります(例: React QueryのinvalidateQueriesを使用)。

Server Actionsでは、キャッシュの無効化はrevalidatePathとrevalidateTagを介してフレームワークに組み込まれています。アクションが完了すると、Next.jsはクライアントルーターに特定のパスを再フェッチするよう指示するレスポンスを返すことができます。これは単一のネットワークラウンドトリップで発生します。

例:

export async function updateProfile(data: UserData) {
  "use server"
  await updateDb(data);
  revalidateTag("user-profile");
}

実行されると、Next.jsはuser-profileタグのサーバーサイドキャッシュを自動的にパージし、クライアントルーターに更新されたServer Componentペイロードをシームレスに適用するよう指示します。これにより、可能な限りクライアントサイドの状態が維持されます。

セキュリティに関する考慮事項: 見えないAPI

Server Actionsは「魔法」であり、したがって安全ではないという誤解がよくあります。実際には、Server ActionsはパブリックAPIエンドポイントと機能的に同じです。Server Actionを公開すると、ドメインにHTTPリクエストを行うことができる人なら誰でもそれを呼び出すことができます。

このため、すべてのServer Actionを信頼できないエントリポイントとして扱う必要があります。

  1. 認証と認可: すべてのアクション内でユーザーのセッションと権限を明示的に確認する必要があります。
  2. 入力検証: FormDataやServer Actionに渡される引数を決して信頼しないでください。データベースとやり取りする前に、Zodのようなスキーマ検証ライブラリを使用して入力をサニタイズし、検証することを常に心がけてください。
  3. クロスサイトリクエストフォージェリ(CSRF): Next.jsは、厳格なオリジンチェックを強制し、特定のヘッダーを利用することで、Server ActionsのCSRF保護を自動的に実装し、最も一般的なWeb脆弱性の1つを軽減します。
export async function secureAction(data: unknown) {
  "use server";
  
  const session = await getSession();
  if (!session) throw new Error("Unauthorized");

  const parsed = mySchema.safeParse(data);
  if (!parsed.success) throw new Error("Invalid input");

  // Safe to proceed
}
Advertisement

プログレッシブエンハンスメントとフォーム送信

Server Actionsは、HTMLフォームとネイティブに使用される場合に最も輝きます。Server Actionを<form>要素のaction属性に直接渡すことで、プログレッシブエンハンスメントがすぐに利用できます。

import { createPost } from "./actions";

export default function PostForm() {
  return (
    <form action={createPost}>
      <input type="text" name="title" required />
      <button type="submit">Create</button>
    </form>
  );
}

JavaScriptが無効になっているか、読み込みに失敗した場合、ブラウザは標準のURLエンコードされたフォーム送信にフォールバックします。Next.jsはこれをシームレスに処理し、アクションを実行してユーザーをレンダリングされたページにリダイレクトします。JavaScriptが有効な場合、Reactは送信をインターセプトし、ページ全体の再読み込みを防ぎ、fetchを介してリクエストを処理するため、スムーズなSPAのような遷移が可能になります。

React 19では、保留中の状態やオプティミスティックUIの更新をネイティブに処理するためのuseActionStateやuseFormStatusのようなフックが導入されています。これにより、外部の状態管理ライブラリへの依存がさらに減り、ミューテーションロジックがプラットフォームに戻されます。

Reactアーキテクチャの未来

Next.js Server Actionsは、フルスタックのReactアプリケーションを構築する方法に根本的な変化をもたらします。クライアントとサーバー間の距離を縮め、明示的なAPIルートの必要性を減らし、キャッシュメカニズムと深く統合することで、Server Actionsは信じられないほどモダンでありながら、基本的なWeb標準に基づいた開発者エクスペリエンスを提供します。

セキュリティと検証には規律あるアプローチが必要ですが、生産性とシンプルさのトレードオフは否定できません。Reactエコシステムが進化し続けるにつれて、Server Actionsによって開拓されたRPCスタイルのミューテーションパターンは、フレームワーク全体のデータミューテーションの標準となる態勢が整っています。

こちらもおすすめ

Share this article:

Stay Updated

Get the latest posts delivered straight to your inbox.

Free Developer Utilities

Free In-Browser Developer Tools

Clean AI CLI logs, build cron expressions, decode JWTs, and calculate chmod permissions offline.

Explore Tools
Advertisement