Nextauth と next.js を使用したロールベースの認証

WBOY
リリース: 2024-07-22 10:15:31
オリジナル
722 人が閲覧しました

Roles based authentication using Nextauth and next.js

こんにちは、あなたも独自の認証とロールベースのソリューションを探してインターネットの暗い味方を探し回ったものの、何も見つからなかった、またはおそらく見つけたかもしれませんが、それは単に見つかりませんでしたもう作業できない場合は、機能コードが正しい場所にあります。皆さんにとって簡単になるように、パッケージのバージョンも示します。

それでは、まず必要なパッケージをすべてインストールしましょう

  npm install next-auth@beta
  npm install drizzle-orm zod react-hook-form
ログイン後にコピー

次に、nextAuth の認証プロバイダーをセットアップしましょう。

にファイルが作成されます。

lib/auth/index.ts

デフォルトでは OAuth はロールを返さないため、このファイルでは資格情報プロバイダーを使用しますが、oAuth を使用してロールを割り当てる方法も説明します

  export const { handlers, signIn, signOut, auth } = NextAuth({
 adapter: DrizzleAdapter(db),
  providers: [
    Credentials({
      name: "credentials",
      credentials: {
        email: {
          type: "email",
          label: "Email Address",
          placeholder: "Email Address",
        },
        password: {
          type: "password",
          label: "Password",
        },
      },
      async authorize(credentials) {
        const { email, password } = await signInSchema.parseAsync(credentials);

        const user = await db
          .select()
          .from(users)
          .where(eq(users.email, email))
          .execute()
          .then((res) => res[0]);

        if (!user || !user.password) return null;

         const isValidPassword = await bcryptjs.compare(password, user.password);

         if (!isValidPassword) return null;

        return {
          id: user.id,
          name: user.name,
          email: user.email,
        };
      },
    }),
    GoogleProvider({
      clientId: process.env.GOOGLE_CLIENT_ID,
      clientSecret: process.env.GOOGLE_CLIENT_SECRET,

      profile(profile: GoogleProfile) {
        return { ...profile, role: "user" };
      },
    })
  ],
});
ログイン後にコピー

この情報を DB に保存したり取得したりするために postgres と drizzle ORM を使用していることを言及する良い機会かもしれません。

霧雨アダプターを使用していますので、次の方法で取り付けることができます

npm install drizzle-orm @auth/drizzle-adapter
npm install drizzle-kit --save-dev
ログイン後にコピー

認証が機能するための霧雨に適したスキーマは、ここのリンクで見つけることができます。あとは、API ルートでこのハンドラーを使用して機能させるだけです。

import { handlers } from "@/lib/auth";

export const { GET, POST } = handlers;
ログイン後にコピー

認証は機能するようになりましたが、まだロールがありません。まず霧雨スキーマを変更し、次に nextAuth オプションを変更します。

これは、文字列値を保持する users テーブル内のロールとしての単純なフィールドである可能性があることに注意してください。しかし、私はこのようにして、必要なだけロールを作成し、それに権限を追加できるようにしました

export const roles = pgTable("roles", {
  id: text("id")
    .primaryKey()
    .$defaultFn(() => createId()),
  name: text("name").notNull(),
  description: text("description"),
});

export const permissions = pgTable("permissions", {
  id: text("id")
    .primaryKey()
    .$defaultFn(() => createId()),
  name: text("name").notNull(),
  description: text("description"),
});

export const rolePermissions = pgTable("role_permissions", {
  roleId: text("roleId").references(() => roles.id, { onDelete: "cascade" }),
  permissionId: text("permissionId").references(() => permissions.id, {
    onDelete: "cascade",
  }),
});

export const userRoles = pgTable("user_roles", {
  userId: text("userId").references(() => users.id, { onDelete: "cascade" }),
  roleId: text("roleId").references(() => roles.id, { onDelete: "cascade" }),
});
ログイン後にコピー

次に、役割と権限がユーザー セッションに含まれるように NextAuthOption を変更する必要があります。

まず、ロールを取得するためのコールバック関数を定義します。

 callbacks: {
    async jwt({ token, user }) {
      if (user && user.id) {
        const { role, permissions } = await getUserRoleAndPermissions(user.id);
        token.role = role;
        token.permissions = permissions;
      }
      return token;
    },
    async session({ session, token }) {
      if (token && session.user) {
        session.user.id = token.id;
        session.user.role = token.role;
        session.user.permissions = token.permissions;
      }
      return session;
    },
  },
ログイン後にコピー

getRolesandPermission 関数は、その名の通り、drizzle を使用して db からロールと権限をクエリします。デフォルトでは、これだけでは機能しません。タイプにいくつかの変更を加える必要もあります。

declare module "next-auth" {
  interface Session {
    user: {
      id: string;
      role: string;
      permissions: string[];
    } & DefaultSession["user"];
  }
}

declare module "next-auth/jwt" {
  interface JWT {
    id: string;
    role: string;
    permissions: string[];
  }
}
ログイン後にコピー

セッションにアクセスすることで、役割と権限を取得できるようになりました。これを使用すると、ページ レベルでユーザーをブロックしたり、ミドルウェアを使用してルート グループ全体を保護したりできます。

この方法はマルチテナント Sass で非常に役立ちます。ユーザーを他の場所に保存したくない場合、これは完璧なソリューションです。読んでいただきありがとうございます

以上がNextauth と next.js を使用したロールベースの認証の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。

ソース:dev.to
このウェブサイトの声明
この記事の内容はネチズンが自主的に寄稿したものであり、著作権は原著者に帰属します。このサイトは、それに相当する法的責任を負いません。盗作または侵害の疑いのあるコンテンツを見つけた場合は、admin@php.cn までご連絡ください。
人気のチュートリアル
詳細>
最新のダウンロード
詳細>
ウェブエフェクト
公式サイト
サイト素材
フロントエンドテンプレート