コンテンツにスキップ
NextAuth.js v4 からの移行ですか?以下をお読みください 移行ガイド.
ガイドロールベースアクセス制御

ロールベースアクセス制御

Auth.jsを使用して、ロールベースアクセス制御(RBAC)をアプリケーションに追加する方法は、選択したセッション戦略に基づいて2つあります。それぞれの例を見てみましょう。

ロールを取得する

まず、ユーザーロールを決定するために、プロバイダーの構成にprofile()コールバックを追加します。

./auth.ts
import NextAuth from "next-auth"
import Google from "next-auth/providers/google"
 
export const { handlers, auth } = NextAuth({
  providers: [
    Google({
      profile(profile) {
        return { role: profile.role ?? "user", ... }
      },
    })
  ],
})
💡

ユーザーのロールを決定するのはあなたの責任です。独自のロジックを追加するか、プロバイダーがロールを返す場合は代わりにそれを使用できます。

ロールを永続化する

ロールの永続化は、使用しているセッション戦略によって異なります。使用しているセッション戦略がわからない場合は、おそらくJWT(デフォルト)を使用しています。

JWTを使用する

データベースが構成されていない場合、jwt()コールバックを使用することにより、ロールはCookieに永続化されます。サインイン時に、roleプロパティは、userオブジェクトのprofileコールバックから公開されます。user.role値をtoken.roleに割り当てることで永続化します。以上です!

クライアントでロールを使用したい場合は、sessionコールバックを介してロールを公開できます。

./auth.ts
import NextAuth from "next-auth"
import Google from "next-auth/providers/google"
 
export const { handlers, auth } = NextAuth({
  providers: [
    Google({
      profile(profile) {
        return { role: profile.role ?? "user", ... }
      },
    })
  ],
  callbacks: {
    jwt({ token, user }) {
      if(user) token.role = user.role
      return token
    },
    session({ session, token }) {
      session.user.role = token.role
      return session
    }
  }
})

この戦略では、ロールを更新したい場合は、ユーザーに再度サインインを強制する必要があります。

データベースを使用する

データベースがある場合は、Userモデルにユーザーロールを保存できます。以下の例は、Prismaでこれを行う方法を示していますが、考え方はすべてのアダプターで同じです。

まず、role列をUserモデルに追加します。

/prisma/schema.prisma
model User {
  id            String    @id @default(cuid())
  name          String?
  email         String?   @unique
  emailVerified DateTime?
  image         String?
  role          String?  // New column
  accounts      Account[]
  sessions      Session[]
}

profile()コールバックの戻り値は、データベースでユーザーを作成するために使用されます。以上です!新しく作成されたユーザーには、ロールが割り当てられます。

クライアントでロールを使用したい場合は、sessionコールバックを介してロールを公開できます。

./auth.ts
import NextAuth from "next-auth"
import Google from "next-auth/providers/google"
import prisma from "lib/prisma"
 
export const { handlers, auth } = NextAuth({
  adapter: PrismaAdapter(prisma),
  providers: [
    Google({
      profile(profile) {
        return { role: profile.role ?? "user", ... }
      }
    })
  ],
  callbacks: {
    session({ session, user }) {
      session.user.role = user.role
      return session
    }
  }
})

ロールの更新をどのように管理するか(データベースへの直接アクセス、またはロール更新APIの構築)は、あなた次第です。

ロールを使用する

ユーザーは、各フレームワークの構成ファイルからエクスポートされた認証関数を介して、現在のセッションに保存された情報にアクセスできます。この関数は、構成ファイルのsessionおよびjwtコールバックを介して公開された情報を取得します。この情報を使用して、ニーズに基づいてUIを表示するためのさまざまな戦略とロジックを実装できます。

サーバー側でデータを取得するには、構成ファイルからauth関数をインポートし、ユーザーが予期されたロールを持っているかどうかを確認する必要があります。

./app/admin/page.tsx
import { auth } from "@/auth";
 
export default async function Page() {
  const session = await auth();
 
  if (session?.user?.role === "admin") {
    return <p>You are an admin, welcome!</p>;
  }
 
  return <p>You are not authorized to view this page!</p>;
}
💡

Next.jsとJWTを使用している場合は、Middlewareを使用して、ページをレンダリングする前でも、ロールに基づいてユーザーをリダイレクトすることもできます。

リソース

Auth.js © Balázs Orbán およびチーム -2024