如何使用RTK查询更新NextAuth会话对象客户端?

gajydyqb  于 2023-10-18  发布在  其他
关注(0)|答案(1)|浏览(108)

我在我的应用程序中设置了next-auth,我使用reduxjs工具包和RTK查询来进行API调用。在后端设置了一个刷新令牌路由来刷新jwt令牌。
我试图从RTK基本查询方法更新session.jwt属性,但getSession中的session对象是只读的,因此我无法直接从基本查询更新jwt令牌。有一个useSession钩子提供了一个update方法,但这将不起作用,因为我不能在基本查询中使用钩子。

import { createApi, fetchBaseQuery } from "@reduxjs/toolkit/query";
import { getSession } from "next-auth/react";

const baseQuery = fetchBaseQuery({
  baseUrl: "http://localhost:1337/",
  prepareHeaders: async (headers) => {
    const session = await getSession();
    if (session) {
      headers.set("Authorization", `Bearer ${session.jwt}`);
      return headers;
    }
  },
});

const baseQueryWithReauth = async (args: any, api: any, extraOptions: any) => {
  const session = await getSession();
  let result: any = await baseQuery(args, api, extraOptions);
  if (
    result.error &&
    (result.error.status === 401 || result.error.status === 403)
  ) {
    const data = await baseQuery(
      {
        url: "token/refresh",
        method: "POST",
        body: { refreshToken: session?.refreshToken },
      },
      api,
      extraOptions
    );
    if (data) {
      //Trying to update the session property to take the new jwt but does not work.
      session.jwt = data.jwt;
      result = await baseQuery(args, api, extraOptions);
    }
  }
  return result;
};

export const api = createApi({
  reducerPath: "api",
  baseQuery: baseQueryWithReauth,
  tagTypes: ["Orders"],
  endpoints: (builder) => ({
    getOrders: builder.query({
      query: () => {
        return {
          url: "api/orders?populate[products][populate][0]=*",
        };
      },
      providesTags: ["Orders"],
    }),
  }),
});

我尝试用从token/refresh端点接收到的新jwt直接更新session.jwt属性,但这不起作用,因为session对象是只读的。
我试图只在基本查询方法中使用刷新标记逻辑,而不是在组件中使用useSession钩子中的update方法。

x759pob2

x759pob21#

如果你想使用getSession()更新会话,请尝试以下操作:

import { getSession, getCsrfToken } from 'next-auth/react'
... 
const csrfToken = await getCsrfToken()
const updatedSession = await getSession({ req: {
                  body: {
                    csrfToken,
                    data: { user: { accessToken: "newToken" } },
                  },
                },
              })
...

在callbacks中:

async jwt({ token, session, trigger }) {
   if (trigger === 'update' && session?.user?.accessToken) {
   token.accessToken= session.user.accessToken
  }

  return token
},

async session({ session, token }) {
  session.user = token
  return session
},

相关问题