Fix-auth-hashing-update-worklog
This commit is contained in:
@@ -1,4 +1,5 @@
|
||||
import { Metadata } from "next"
|
||||
import { hash } from "bcryptjs"
|
||||
import { createId } from "@paralleldrive/cuid2"
|
||||
import { eq } from "drizzle-orm"
|
||||
|
||||
@@ -10,6 +11,12 @@ export const metadata: Metadata = {
|
||||
description: "Create an account",
|
||||
}
|
||||
|
||||
const normalizeBcryptHash = (value: string) => {
|
||||
if (value.startsWith("$2")) return value
|
||||
if (value.startsWith("$")) return `$2b${value}`
|
||||
return `$2b$${value}`
|
||||
}
|
||||
|
||||
export default function RegisterPage() {
|
||||
async function registerAction(formData: FormData): Promise<ActionState> {
|
||||
"use server"
|
||||
@@ -37,11 +44,12 @@ export default function RegisterPage() {
|
||||
})
|
||||
if (existing) return { success: false, message: "该邮箱已注册" }
|
||||
|
||||
const hashedPassword = normalizeBcryptHash(await hash(password, 10))
|
||||
await db.insert(users).values({
|
||||
id: createId(),
|
||||
name: name.length ? name : null,
|
||||
email,
|
||||
password,
|
||||
password: hashedPassword,
|
||||
role: "student",
|
||||
})
|
||||
|
||||
|
||||
31
src/auth.ts
31
src/auth.ts
@@ -1,6 +1,19 @@
|
||||
import { compare, hash } from "bcryptjs"
|
||||
import NextAuth from "next-auth"
|
||||
import Credentials from "next-auth/providers/credentials"
|
||||
|
||||
const normalizeRole = (value: unknown) => {
|
||||
const role = String(value ?? "").trim().toLowerCase()
|
||||
if (role === "admin" || role === "student" || role === "teacher" || role === "parent") return role
|
||||
return "student"
|
||||
}
|
||||
|
||||
const normalizeBcryptHash = (value: string) => {
|
||||
if (value.startsWith("$2")) return value
|
||||
if (value.startsWith("$")) return `$2b${value}`
|
||||
return `$2b$${value}`
|
||||
}
|
||||
|
||||
export const { handlers, auth, signIn, signOut } = NextAuth({
|
||||
trustHost: true,
|
||||
secret: process.env.NEXTAUTH_SECRET,
|
||||
@@ -29,17 +42,17 @@ export const { handlers, auth, signIn, signOut } = NextAuth({
|
||||
if (!user) return null
|
||||
|
||||
const storedPassword = user.password ?? null
|
||||
if (storedPassword) {
|
||||
if (storedPassword !== password) return null
|
||||
} else if (process.env.NODE_ENV === "production") {
|
||||
return null
|
||||
}
|
||||
if (!storedPassword) return null
|
||||
const normalizedPassword = normalizeBcryptHash(storedPassword)
|
||||
if (!normalizedPassword.startsWith("$2")) return null
|
||||
const ok = await compare(password, normalizedPassword)
|
||||
if (!ok) return null
|
||||
|
||||
return {
|
||||
id: user.id,
|
||||
name: user.name ?? undefined,
|
||||
email: user.email,
|
||||
role: (user.role ?? "student") as string,
|
||||
role: normalizeRole(user.role),
|
||||
}
|
||||
},
|
||||
}),
|
||||
@@ -48,7 +61,7 @@ export const { handlers, auth, signIn, signOut } = NextAuth({
|
||||
jwt: async ({ token, user }) => {
|
||||
if (user) {
|
||||
token.id = (user as { id: string }).id
|
||||
token.role = (user as { role?: string }).role ?? "student"
|
||||
token.role = normalizeRole((user as { role?: string }).role)
|
||||
token.name = (user as { name?: string }).name
|
||||
}
|
||||
|
||||
@@ -66,7 +79,7 @@ export const { handlers, auth, signIn, signOut } = NextAuth({
|
||||
})
|
||||
|
||||
if (fresh) {
|
||||
token.role = fresh.role ?? token.role ?? "student"
|
||||
token.role = normalizeRole(fresh.role ?? token.role)
|
||||
token.name = fresh.name ?? token.name
|
||||
}
|
||||
}
|
||||
@@ -76,7 +89,7 @@ export const { handlers, auth, signIn, signOut } = NextAuth({
|
||||
session: async ({ session, token }) => {
|
||||
if (session.user) {
|
||||
session.user.id = String(token.id ?? "")
|
||||
session.user.role = String(token.role ?? "student")
|
||||
session.user.role = normalizeRole(token.role)
|
||||
if (typeof token.name === "string") {
|
||||
session.user.name = token.name
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user