如何在 next-auth 中将数据添加到客户端 API?

deb*_*bug 6 javascript node.js next.js next-auth

我目前正在使用凭据提供程序使用 next-auth 进行授权,我有会话正在运行并且用户可以登录等。但是,在会话中我需要使用客户端 API、用户、名字、姓氏传递一些数据,用户名和电子邮件。

默认情况下,客户端 API 传递名称、电子邮件和图像,但是,我如何更改它以添加上述数据,这是我到目前为止所拥有的。

索引.js

import { useState, useEffect  } from 'react';
import { getSession } from 'next-auth/client'
import { useRouter } from 'next/router';
import Link from 'next/link';
import Head from 'next/head';
import Sidebar from '../components/Sidebar';

export default function Dashboard({ user}) {
  return (
    <div>
      <Head>
        <title>Dashboard</title>
      </Head>

      <Sidebar />

      <section className="content dashboard-content">
        <h1>Dashboard</h1>

        <h3>Welcome to Ellis development {user.firstname }</h3>
      </section>
    </div>
  )
}

export async function getServerSideProps(ctx) {
  const session = await getSession(ctx);
  
  if (!session) {
    return {
      redirect: {
        destination: '/dashboard/auth/login',
        permanent: false
      },
    }
  }

  console.log(session);

  return {
    props: {
      user: {
        firstname: session.user.firstname,
        lastname: session.user.lastname,
        username: session.user.username,
        email: session.user.email,
      }
    },
  }
}
Run Code Online (Sandbox Code Playgroud)

[...nextauth.js]

import NextAuth from 'next-auth';
import Providers from 'next-auth/providers';

import { verifyPassword } from '../../../lib/auth';
import { connectToDatabase } from '../../../lib/mongodb';

export default NextAuth({
  session: {
    jwt: true,
  },
  providers: [
    Providers.Credentials({
      async authorize(credentials) {
        const client = await connectToDatabase();
        const usersCollection = client.db().collection('users');

        const user = await usersCollection.findOne({
          email: credentials.email,
        });

        if (!user) {
          client.close();
          throw new Error('No user found!');
        }

        const isValid = await verifyPassword(
          credentials.password,
          user.password
        );

        if (!isValid) {
          client.close();
          throw new Error('Could not log you in!');
        }

        client.close();

        return {
          firstname: user.firstname,
          lastname: user.lastname,
          username: user.username,
          email: user.email
        };
      },
    }),
  ],
});
Run Code Online (Sandbox Code Playgroud)

任何帮助都会很棒,谢谢。

编辑

我已将以下内容添加到 [...next-auth] 页面

callbacks: {
  session: async (session) => {
    if (!session) return;

    const client = await connectToDatabase();
    const usersCollection = client.db().collection('users');
    
    const userData = await usersCollection.findOne({
      email: session.user.email,
    });

    return {
      session: {
        user: {
          id: userData._id,
          firstname: userData.firstname,
          lastname: userData.lastname,
          username: userData.username,
          email: userData.email
        }
      }
    };
  },
},
Run Code Online (Sandbox Code Playgroud)

这给了我以下结果

{
  session: {
    user: {
      id: '61a107f29ca24c12146d1b22',
      firstname: 'Ben',
      lastname: 'Bagley',
      username: 'benbagley',
      email: 'benbagley@pm.me'
    }
  }
}
Run Code Online (Sandbox Code Playgroud)

所以我现在有了我需要的值,但是,如何将数据渲染到页面上我现在有以下内容

import { getSession } from 'next-auth/client'
import Head from 'next/head';
import Sidebar from '../components/Sidebar';

export default function Dashboard({ session }) {
  return (
    <div>
      <Head>
        <title>Dashboard</title>
      </Head>

      <Sidebar />

      <section className="content dashboard-content">
        <h1>Dashboard</h1>

        <h3>Welcome {session.user.firstname} to Ellis development</h3>
      </section>
    </div>
  )
}

export async function getServerSideProps(ctx) {
  const session = await getSession(ctx);
  
  if (!session) {
    return {
      redirect: {
        destination: '/dashboard/auth/login',
        permanent: false
      },
    }
  }

  console.log(session);

  return {
    props: {
      session: {
        user: {
          id: session.user.id,
          firstname: session.user.firstname,
          lastname: session.user.lastname,
          username: session.user.username,
        }
      }
    },
  }
}
Run Code Online (Sandbox Code Playgroud)

然而,我得到TypeError: Cannot read properties of undefined (reading 'id')

deb*_*bug 5

这里的问题有两个方面,

a) 没有使用正确的回调来添加和覆盖 next-auth api,例如:

callbacks: {
  session: async (session) => {
    if (!session) return;

    const client = await connectToDatabase();
    const usersCollection = client.db().collection('users');
    
    const userData = await usersCollection.findOne({
      email: session.user.email,
    });

    return {
      session: {
        user: {
          id: userData._id,
          firstname: userData.firstname,
          lastname: userData.lastname,
          username: userData.username,
          email: userData.email
        }
      }
    };
  },
},
Run Code Online (Sandbox Code Playgroud)

现在正在传递值,下一个问题就会出现......

b) 传递 props 时不使用展开运算符

export async function getServerSideProps(ctx) {
  const session = await getSession(ctx);
  
  if (!session) {
    return {
      redirect: {
        destination: '/dashboard/auth/login',
        permanent: false
      },
    }
  }

  return {
    props: {
      ...session,
    }
  }
}
Run Code Online (Sandbox Code Playgroud)

调用...session获取所有返回对象并允许它这样传递session.user.firstname,非常方便。

  • “每当检查会话时都会调用会话回调。” 所以它会多次调用会话回调,也会调用数据库查询。 (2认同)