gpt4 book ai didi

typescript - 如何在 nextauthjs 的 typescript 中正确编写授权函数

转载 作者:行者123 更新时间:2023-12-02 01:45:11 25 4
gpt4 key购买 nike

我正在尝试使用 Credentials Provider使用 NextJs ("next": "^12.0.7") 和 NextAuth ("next-auth": "^4.1.2")。我正在用 typescript 写这篇文章,并面临正确获取功能的问题。

这是我的 /pages/api/[...nextauth].ts

import NextAuth, {  } from "next-auth";
import CredentialsProvider from "next-auth/providers/credentials";
import { verifyOTP } from "@/lib/otp";

// {
// user: {
// id: 1,
// username: null,
// phone: '+919876543210',
// phoneVerified: true,
// email: null,
// emailVerified: false,
// active: true,
// token: 'SOME TOKEN',
// createDate: null
// },
// result: 'approved'
// }

export default NextAuth({
pages: {
signIn: '/signup',
newUser: '/signup',
error: '/signup'
},
debug: false,
secret: "SOME_SECRET",
// Configure one or more authentication providers
providers: [
CredentialsProvider({
credentials: {
username: {label: "username", type: "text", placeholder: "markandre"},
phone: { label: "Phone ", type: "text", placeholder: "+919876543210" },
otp: { label: "OTP", type: "text" }
},
authorize: async (credentials, _req) => {
try {
const res = await verifyOTP(credentials!.phone,
credentials!.otp, credentials?.username);
if (res.result === "approved") {
return Promise.resolve( {
id: res.user.id,
email: res.user.email,
name: res.user.phone,
token: res.user.token
});
}
} catch (e: any) {
//const errorMessage = e.response.data.message;
//throw new Error(errorMessage);
return Promise.reject(null);
}
}
})
],
session: {
strategy: 'jwt',
maxAge: 3 * 60 * 60, // 3 hours
},
callbacks: {
jwt: async ({token, user}) => {
if (user) {
token.accessToken = user.token
}

return token;
},
session:async ({session, token}) => {
if (token) {
session.accessToken = token.accessToken;
}
return session;
}
},
events: {
signIn: async (message) => {
console.log('signIn', message);
},
signOut: async (message) => {
console.log('signOut', message);
},
createUser: async(message) => {
console.log('createUser', message);
},
updateUser: async(message) => {
console.log('updateUser', message);
},
linkAccount: async(message) => {
console.log('linkAccount',message);
},
session: async(message) => {
// console.log('session', message);
}
}
})

当我构建这个应用程序时,我不断收到错误

./src/pages/api/auth/[...nextauth].ts:36:7
Type error: Type '(credentials: Record<"username" | "phone" | "otp", string> | undefined, _req: Pick<IncomingRequest, "headers" | "body" | "query" | "method">) => Promise<...>' is not assignable to type '(credentials: Record<"username" | "phone" | "otp", string> | undefined, req: Pick<IncomingRequest, "headers" | "body" | "query" | "method">) => Awaitable<...>'.
Type 'Promise<Omit<User, "id"> | null | undefined>' is not assignable to type 'Awaitable<Omit<User, "id"> | { id?: string | undefined; } | null>'.
Type 'Promise<Omit<User, "id"> | null | undefined>' is not assignable to type 'Omit<User, "id">'.
Index signature for type 'string' is missing in type 'Promise<Omit<User, "id"> | null | undefined>'.

34 | otp: { label: "OTP", type: "text" }
35 | },
> 36 | authorize: async (credentials, _req) => {
| ^
37 | try {
38 | const res = await verifyOTP(credentials!.phone,
39 | credentials!.otp, credentials?.username);
info - Checking validity of types .%

我的 .tsconfig 如下所示

{
"compilerOptions": {
"lib": ["dom", "dom.iterable", "esnext"],
"module": "esnext",
"moduleResolution": "node",
"resolveJsonModule": true,
"removeComments": true,
"preserveConstEnums": true,
"strict": true,
"alwaysStrict": false,
"strictNullChecks": true,
"noUncheckedIndexedAccess": true,

"noImplicitAny": true,
"noImplicitReturns": true,
"noImplicitThis": true,
"noUnusedLocals": true,
"noUnusedParameters": true,
"allowUnreachableCode": false,
"noFallthroughCasesInSwitch": true,

"target": "es5",
"outDir": "out",
"declaration": true,
"sourceMap": true,

"esModuleInterop": true,
"allowSyntheticDefaultImports": true,
"allowJs": true,
"skipLibCheck": true,
"forceConsistentCasingInFileNames": true,

"jsx": "preserve",
"noEmit": true,
"isolatedModules": true,
"incremental": true,

"baseUrl": ".",
"paths": {
"@/*": ["./src/*"],
"@/public/*": ["./public/*"]
}
},
"exclude": ["./out/**/*", "./node_modules/**/*"],
"include": ["next-env.d.ts", "**/*.ts", "**/*.tsx"]
}

最佳答案

authorize 函数需要返回代表用户的对象,或者如果凭证无效则返回 false/null

对于 res.result === "approved" 检查的情况,您当前的逻辑并未明确返回 false/null是错误的,因此类型错误。您可以通过在 if block 之后显式返回 null 来解决此问题。

authorize: async (credentials, _req) => {
try {
const res = await verifyOTP(credentials!.phone, credentials!.otp, credentials?.username);
if (res.result === "approved") {
return {
id: res.user.id,
email: res.user.email,
name: res.user.phone,
token: res.user.token
};
}
return null; // Add this line to satisfy the `authorize` typings
} catch (e: any) {
//const errorMessage = e.response.data.message;
//throw new Error(errorMessage);
return null;
}
}

作为旁注,您也不需要使用 Promise.resolve()/Promise.reject() 包装用户对象和 null ,所以我也省略了这些。

关于typescript - 如何在 nextauthjs 的 typescript 中正确编写授权函数,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/70990262/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com