0
1

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

Next.js App Routerで守るべきページをシンプルに分離する方法

0
Posted at

Next.js 13 以降で導入された App Router は、ページごとに page.tsx を配置するだけで自動的にルーティングが組み立てられます。
しかし、ログインが必要なページと誰でもアクセスできるページを同じプロジェクト内で管理すると、認証ロジックが散在しがちです。そこで ミドルウェア を使って「保護したいルートだけを一括で切り分ける」パターンを紹介します。

1. ミドルウェアの役割をざっくりイメージ

ミドルウェアはリクエストがページに到達する前に実行される関数です。

  • 認証情報(Cookie やヘッダー)をチェック
  • 条件に合わなければ別ページへリダイレクト
  • 条件が合えばそのまま次の処理へ

この仕組みを利用すれば、/dashboard や /profile といった保護ルートだけをまとめてガードできます。

2. ディレクトリ構成の例

app/
├─ layout.tsx          # ルートレイアウト
├─ page.tsx            # トップページ(公開)
├─ login/
│  └─ page.tsx        # ログインページ(公開)
└─ protected/
   ├─ layout.tsx      # 保護レイアウト(ミドルウェアでチェック)
   └─ page.tsx        # 守られたページ
middleware.ts          # グローバルミドルウェア

middleware.ts はプロジェクトのルートに置くだけで全リクエストに適用されます。
ポイントは、保護したいパスだけを正規表現で絞り込むことです。

3. 実装例(TypeScript)

以下はシンプルな認証ミドルウェアです。

  • authToken という名前の Cookie が存在すれば認証成功とみなす
  • それ以外は /login へリダイレクト
// middleware.ts
import { NextResponse } from 'next/server';
import type { NextRequest } from 'next/server';

// 保護したいパスを配列で管理
const protectedPaths = ['/protected', '/dashboard', '/profile'];

export function middleware(request: NextRequest) {
  const { pathname } = request.nextUrl;

  // 保護対象外ならそのまま通す
  if (!protectedPaths.some(p => pathname.startsWith(p))) {
    return NextResponse.next();
  }

  // Cookie からトークン取得
  const token = request.cookies.get('authToken')?.value;

  // トークンが無ければログインページへリダイレクト
  if (!token) {
    const loginUrl = new URL('/login', request.url);
    loginUrl.searchParams.set('callbackUrl', pathname);
    return NextResponse.redirect(loginUrl);
  }

  // 認証成功 → 次の処理へ
  return NextResponse.next();
}

// ミドルウェアが適用されるパスを明示(オプション)
export const config = {
  matcher: ['/protected/:path*', '/dashboard/:path*', '/profile/:path*'],
};

コードのポイント

  1. protectedPaths でガードしたいルートを列挙。増減があればここだけ修正すれば OK。
  2. request.cookies.get で Cookie を安全に取得。?.value で未定義時もエラーにならないようにしています。
  3. callbackUrl をクエリに入れてリダイレクトすれば、ログイン後に元のページへ戻すことができます。
  4. config.matcher を設定すると、不要なリクエストまでミドルウェアが走らずパフォーマンスが向上します。

4. 初心者がハマりやすいポイント

つまずきやすい点 対策
Cookie 名を間違える ブラウザの DevTools で実際に送られている名前を確認
正規表現でパスが抜ける matcher に /:path* を付けてサブパスも網羅
リダイレクトが無限ループになる /login 自体は protectedPaths に入れない
TypeScript の型エラー NextRequest と NextResponse のインポートは必ず next/server から

5. まとめ

  • App Router でページ構造をシンプルに保ちつつ、ミドルウェアで認証ロジックを一元管理できる
  • 保護したいルートだけを matcher で絞ると、余計な処理が走らず高速化
  • 初心者でも TypeScript の型補完があるので、実装ミスを減らしながら安全に認証フローを構築できる

実際に手を動かしてみると、ミドルウェアの挙動がすぐに分かります。ぜひ自分のプロジェクトに取り入れて、保護ルートの管理を楽にしてみてください。

詳しい手順はこちら → https://felixstudio0.gumroad.com/?utm_source=qiita&utm_medium=github_actions&utm_campaign=2026-q1&utm_content=qiita-footer

0
1
1

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
1

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?