chatbot-template/auth.ts
2024-03-14 20:00:52 +03:00

62 lines
1.6 KiB
TypeScript

import NextAuth from 'next-auth'
import Credentials from 'next-auth/providers/credentials'
import { authConfig } from './auth.config'
import { z } from 'zod'
import { sql } from '@vercel/postgres'
import { getStringFromBuffer } from './lib/utils'
interface User {
id: string
name: string
email: string
password: string
salt: string
}
async function getUser(email: string): Promise<User | undefined> {
try {
const user = await sql<User>`SELECT * FROM users WHERE email=${email}`
return user.rows[0]
} catch (error) {
throw new Error('Failed to fetch user.')
}
}
export const { auth, signIn, signOut } = NextAuth({
...authConfig,
providers: [
Credentials({
async authorize(credentials) {
const parsedCredentials = z
.object({
email: z.string().email(),
password: z.string().min(6)
})
.safeParse(credentials)
if (parsedCredentials.success) {
const { email, password } = parsedCredentials.data
const user = await getUser(email)
if (!user) return null
const encoder = new TextEncoder()
const saltedPassword = encoder.encode(password + user.salt)
const hashedPasswordBuffer = await crypto.subtle.digest(
'SHA-256',
saltedPassword
)
const hashedPassword = getStringFromBuffer(hashedPasswordBuffer)
if (hashedPassword === user.password) {
return user
} else {
return null
}
}
return null
}
})
]
})