mirror of
https://github.com/ChatGPTNextWeb/ChatGPT-Next-Web.git
synced 2025-10-03 00:26:40 +08:00
commit
f6c705cbf7
@ -51,7 +51,22 @@ async function handle(
|
|||||||
},
|
},
|
||||||
});
|
});
|
||||||
const count = result.length;
|
const count = result.length;
|
||||||
return NextResponse.json({ count: count, results: result });
|
return NextResponse.json({
|
||||||
|
count: count,
|
||||||
|
results: result.map((item) => {
|
||||||
|
return {
|
||||||
|
id: item.id,
|
||||||
|
name: item.name,
|
||||||
|
username: item.username,
|
||||||
|
gh_username: item.gh_username,
|
||||||
|
image: item.image,
|
||||||
|
email: item.email,
|
||||||
|
emailVerified: item.emailVerified,
|
||||||
|
createdAt: item.createdAt,
|
||||||
|
updatedAt: item.updatedAt,
|
||||||
|
};
|
||||||
|
}),
|
||||||
|
});
|
||||||
} catch {}
|
} catch {}
|
||||||
return NextResponse.json({ error: "未知错误" }, { status: 500 });
|
return NextResponse.json({ error: "未知错误" }, { status: 500 });
|
||||||
}
|
}
|
||||||
|
@ -1,6 +1,5 @@
|
|||||||
import { NextRequest, NextResponse } from "next/server";
|
import { NextRequest, NextResponse } from "next/server";
|
||||||
import prisma from "@/lib/prisma";
|
import prisma from "@/lib/prisma";
|
||||||
import { insertUser } from "@/lib/auth";
|
|
||||||
import { getTokenLength } from "@/lib/utils";
|
import { getTokenLength } from "@/lib/utils";
|
||||||
|
|
||||||
async function handle(
|
async function handle(
|
||||||
|
@ -1,9 +0,0 @@
|
|||||||
|
|
||||||
input {
|
|
||||||
text-align: left !important
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
.ant-input {
|
|
||||||
text-align: left !important
|
|
||||||
}
|
|
@ -1,6 +1,5 @@
|
|||||||
"use client";
|
"use client";
|
||||||
|
|
||||||
import "./users-table.modules.scss";
|
|
||||||
import React, { Dispatch, SetStateAction, useEffect, useState } from "react";
|
import React, { Dispatch, SetStateAction, useEffect, useState } from "react";
|
||||||
import { User } from "@prisma/client";
|
import { User } from "@prisma/client";
|
||||||
import {
|
import {
|
||||||
|
@ -3,16 +3,83 @@
|
|||||||
import { signIn } from "next-auth/react";
|
import { signIn } from "next-auth/react";
|
||||||
import React, { useState, useEffect, useRef, use } from "react";
|
import React, { useState, useEffect, useRef, use } from "react";
|
||||||
import { isName } from "@/lib/auth_list";
|
import { isName } from "@/lib/auth_list";
|
||||||
|
import { Form, Input, InputRef } from "antd";
|
||||||
|
import { UserOutlined, MailOutlined } from "@ant-design/icons";
|
||||||
|
import type { FormProps } from "antd";
|
||||||
|
import { SignInOptions } from "next-auth/react";
|
||||||
|
|
||||||
export default function UserLoginButton() {
|
export default function UserLoginButton() {
|
||||||
const [loading, setLoading] = useState(false);
|
const [loading, setLoading] = useState(false);
|
||||||
|
const [loginForm] = Form.useForm();
|
||||||
const nameInput = useRef<HTMLInputElement>(null);
|
const nameInput = useRef<InputRef>(null);
|
||||||
|
const passwordInput = useRef<InputRef>(null);
|
||||||
const emailInput = useRef<HTMLInputElement>(null);
|
const emailInput = useRef<HTMLInputElement>(null);
|
||||||
const [username, setUsername] = useState("");
|
const [username, setUsername] = useState("");
|
||||||
const [error, setError] = useState(false);
|
const [password, setPassword] = useState("");
|
||||||
|
|
||||||
const handleComposition = (e: React.CompositionEvent<HTMLInputElement>) => {
|
const [error, setError] = useState(false);
|
||||||
|
type FieldType = {
|
||||||
|
username?: string;
|
||||||
|
password?: string;
|
||||||
|
email?: string;
|
||||||
|
};
|
||||||
|
const onFinish: FormProps<FieldType>["onFinish"] = (values) => {
|
||||||
|
setLoading(true);
|
||||||
|
let signInOptions: SignInOptions = {
|
||||||
|
redirect: false,
|
||||||
|
};
|
||||||
|
let loginProvider = "";
|
||||||
|
|
||||||
|
if (values.email) {
|
||||||
|
loginProvider = "email";
|
||||||
|
signInOptions = { ...signInOptions, email: values.email };
|
||||||
|
} else {
|
||||||
|
loginProvider = "credentials";
|
||||||
|
signInOptions = {
|
||||||
|
...signInOptions,
|
||||||
|
username: values.username,
|
||||||
|
password: values.password ?? "",
|
||||||
|
};
|
||||||
|
}
|
||||||
|
signIn(loginProvider, signInOptions).then((result) => {
|
||||||
|
setLoading(false);
|
||||||
|
if (!result?.error) {
|
||||||
|
window.location.href =
|
||||||
|
result?.url && result.url.includes("verify") ? result.url : "/";
|
||||||
|
} else {
|
||||||
|
const errorParts = result.error.split(",");
|
||||||
|
if (errorParts.length > 1) {
|
||||||
|
loginForm.setFields([
|
||||||
|
{
|
||||||
|
name: errorParts[0],
|
||||||
|
errors: [errorParts[1]],
|
||||||
|
},
|
||||||
|
]);
|
||||||
|
} else {
|
||||||
|
loginForm.setFields([
|
||||||
|
{
|
||||||
|
name: "password",
|
||||||
|
errors: [result.error],
|
||||||
|
},
|
||||||
|
]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
console.log("response,", result);
|
||||||
|
});
|
||||||
|
|
||||||
|
setLoading(false);
|
||||||
|
console.log("Success:", values);
|
||||||
|
};
|
||||||
|
|
||||||
|
const onFinishFailed: FormProps<FieldType>["onFinishFailed"] = (
|
||||||
|
errorInfo,
|
||||||
|
) => {
|
||||||
|
console.log("Failed:", errorInfo);
|
||||||
|
};
|
||||||
|
|
||||||
|
const handleNameComposition = (
|
||||||
|
e: React.CompositionEvent<HTMLInputElement>,
|
||||||
|
) => {
|
||||||
if (e.type === "compositionend") {
|
if (e.type === "compositionend") {
|
||||||
setUsername(e.currentTarget.value);
|
setUsername(e.currentTarget.value);
|
||||||
}
|
}
|
||||||
@ -23,6 +90,12 @@ export default function UserLoginButton() {
|
|||||||
}
|
}
|
||||||
setUsername(e.target.value);
|
setUsername(e.target.value);
|
||||||
};
|
};
|
||||||
|
const onPasswordChange = (e: React.ChangeEvent<HTMLInputElement>) => {
|
||||||
|
if ((e.nativeEvent as InputEvent).isComposing) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
setPassword(e.target.value);
|
||||||
|
};
|
||||||
const onSubmitHandler = async (e: React.FormEvent<HTMLFormElement>) => {
|
const onSubmitHandler = async (e: React.FormEvent<HTMLFormElement>) => {
|
||||||
// handle yow submition
|
// handle yow submition
|
||||||
setLoading(true);
|
setLoading(true);
|
||||||
@ -40,6 +113,7 @@ export default function UserLoginButton() {
|
|||||||
} else {
|
} else {
|
||||||
result = await signIn("credentials", {
|
result = await signIn("credentials", {
|
||||||
username: username,
|
username: username,
|
||||||
|
password: password,
|
||||||
redirect: false,
|
redirect: false,
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
@ -56,10 +130,11 @@ export default function UserLoginButton() {
|
|||||||
if (nameInput.current) {
|
if (nameInput.current) {
|
||||||
if (!isName(username)) {
|
if (!isName(username)) {
|
||||||
setError(true);
|
setError(true);
|
||||||
nameInput.current.setCustomValidity("用户名校验失败");
|
// nameInput
|
||||||
|
// nameInput.current.setCustomValidity("用户名校验失败");
|
||||||
} else {
|
} else {
|
||||||
setError(false);
|
setError(false);
|
||||||
nameInput.current.setCustomValidity("");
|
// nameInput.current.setCustomValidity("");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
// console.log("username:", username);
|
// console.log("username:", username);
|
||||||
@ -67,79 +142,176 @@ export default function UserLoginButton() {
|
|||||||
|
|
||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
{/*
|
<div className="mt-6 sm:mx-auto sm:w-full sm:max-w-sm">
|
||||||
This example requires updating your template:
|
<Form
|
||||||
|
|
||||||
```
|
|
||||||
<html class="h-full bg-white">
|
|
||||||
<body class="h-full">
|
|
||||||
```
|
|
||||||
*/}
|
|
||||||
|
|
||||||
<div className="mt-10 sm:mx-auto sm:w-full sm:max-w-sm">
|
|
||||||
<form
|
|
||||||
className="space-y-6"
|
className="space-y-6"
|
||||||
action="#"
|
// action="#"
|
||||||
method="POST"
|
// method="POST"
|
||||||
autoComplete="off"
|
autoComplete="off"
|
||||||
onSubmit={onSubmitHandler}
|
onFinish={onFinish}
|
||||||
|
onFinishFailed={onFinishFailed}
|
||||||
|
size="large"
|
||||||
|
form={loginForm}
|
||||||
|
id="login-form"
|
||||||
|
// onSubmit={onSubmitHandler}
|
||||||
>
|
>
|
||||||
<div>
|
<div>
|
||||||
<div className="mt-2">
|
<Form.Item
|
||||||
<input
|
|
||||||
id="username"
|
|
||||||
name="username"
|
name="username"
|
||||||
type="username"
|
rules={[
|
||||||
ref={nameInput}
|
{
|
||||||
// value={username}
|
validator: async (_, value) => {
|
||||||
onCompositionStart={(e) => e.preventDefault()}
|
if (value && !isName(value)) {
|
||||||
onCompositionEnd={handleComposition}
|
return Promise.reject(
|
||||||
onChange={onNameChange}
|
new Error("Invalid username format!"),
|
||||||
// required
|
);
|
||||||
placeholder="输入姓名、拼音或邮箱"
|
|
||||||
className={`${
|
|
||||||
loading
|
|
||||||
? "cursor-not-allowed bg-stone-50 dark:bg-stone-800"
|
|
||||||
: "bg-white hover:bg-stone-50 active:bg-stone-100 dark:bg-black dark:hover:border-white dark:hover:bg-black"
|
|
||||||
} group my-2 flex h-10 w-full items-center justify-center space-x-2 rounded-md border border-stone-200 transition-colors duration-75 focus:outline-none dark:border-stone-700
|
|
||||||
${
|
|
||||||
error
|
|
||||||
? "focus:invalid:border-red-500 focus:invalid:ring-red-500"
|
|
||||||
: ""
|
|
||||||
}
|
}
|
||||||
`}
|
const email_value = loginForm.getFieldValue("email");
|
||||||
|
if (!value && !email_value) {
|
||||||
|
return Promise.reject(
|
||||||
|
new Error("Please input your username!"),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
if (value && email_value) {
|
||||||
|
return Promise.reject(new Error("Field must be unique!"));
|
||||||
|
}
|
||||||
|
const password_value = loginForm.getFieldValue("password");
|
||||||
|
if (!value && password_value) {
|
||||||
|
return Promise.reject(
|
||||||
|
new Error("Please input your username!"),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
},
|
||||||
|
},
|
||||||
|
]}
|
||||||
|
>
|
||||||
|
<Input
|
||||||
|
// id="basic_username"
|
||||||
|
// name="username"
|
||||||
|
// type="username"
|
||||||
|
// ref={nameInput}
|
||||||
|
// // value={username}
|
||||||
|
// onCompositionStart={(e) => e.preventDefault()}
|
||||||
|
// onCompositionEnd={handleNameComposition}
|
||||||
|
// onChange={onNameChange}
|
||||||
|
// required
|
||||||
|
autoComplete="off"
|
||||||
|
prefix={<UserOutlined style={{ color: "rgba(0,0,0,.25)" }} />}
|
||||||
|
placeholder="输入姓名、拼音或邮箱"
|
||||||
|
className={
|
||||||
|
"text-sm font-medium text-stone-600 dark:text-stone-400"
|
||||||
|
}
|
||||||
|
// className={`${
|
||||||
|
// loading
|
||||||
|
// ? "cursor-not-allowed bg-stone-50 dark:bg-stone-800"
|
||||||
|
// : "bg-white hover:bg-stone-50 active:bg-stone-100 dark:bg-black dark:hover:border-white dark:hover:bg-black"
|
||||||
|
// } group my-2 flex h-10 w-full items-center justify-center space-x-2 rounded-md border border-stone-200 transition-colors duration-75 focus:outline-none dark:border-stone-700
|
||||||
|
// ${
|
||||||
|
// error
|
||||||
|
// ? "focus:invalid:border-red-500 focus:invalid:ring-red-500"
|
||||||
|
// : ""
|
||||||
|
// }
|
||||||
|
// `}
|
||||||
/>
|
/>
|
||||||
<input
|
</Form.Item>
|
||||||
id="email"
|
|
||||||
|
<Form.Item<FieldType>
|
||||||
|
// label="Password"
|
||||||
|
name="password"
|
||||||
|
rules={[
|
||||||
|
{
|
||||||
|
validator: async (_, value) => {
|
||||||
|
if (value) {
|
||||||
|
if (value.length < 6) {
|
||||||
|
return Promise.reject(
|
||||||
|
new Error("Password must be at least 6 characters!"),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
|
},
|
||||||
|
]}
|
||||||
|
>
|
||||||
|
<Input.Password
|
||||||
|
// id="basic_password"
|
||||||
|
// name="password"
|
||||||
|
// type="password"
|
||||||
|
// status={error ? "error" : ""}
|
||||||
|
// ref={passwordInput}
|
||||||
|
// value={password}
|
||||||
|
// // onCompositionStart={(e) => e.preventDefault()}
|
||||||
|
// // onCompositionEnd={handleComposition}
|
||||||
|
// onChange={onPasswordChange}
|
||||||
|
autoComplete="off"
|
||||||
|
// // required
|
||||||
|
placeholder="密码验证,测试阶段"
|
||||||
|
className={
|
||||||
|
"text-sm font-medium text-stone-600 dark:text-stone-400"
|
||||||
|
}
|
||||||
|
// className={`${
|
||||||
|
// loading
|
||||||
|
// ? "cursor-not-allowed bg-stone-50 dark:bg-stone-800"
|
||||||
|
// : "bg-white hover:bg-stone-50 active:bg-stone-100 dark:bg-black dark:hover:border-white dark:hover:bg-black"
|
||||||
|
// } group my-2 flex h-10 w-full items-center justify-center space-x-2 rounded-md border border-stone-200 transition-colors duration-75 focus:outline-none dark:border-stone-700
|
||||||
|
// ${
|
||||||
|
// error
|
||||||
|
// ? "focus:invalid:border-red-500 focus:invalid:ring-red-500"
|
||||||
|
// : ""
|
||||||
|
// }
|
||||||
|
// `}
|
||||||
|
/>
|
||||||
|
</Form.Item>
|
||||||
|
<Form.Item
|
||||||
name="email"
|
name="email"
|
||||||
type="email"
|
rules={[
|
||||||
ref={emailInput}
|
{
|
||||||
|
type: "email",
|
||||||
|
message: "The input is not valid E-mail!",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
validator: async (_, value) => {
|
||||||
|
const username_value = loginForm.getFieldValue("username");
|
||||||
|
if (value && username_value) {
|
||||||
|
return Promise.reject(new Error("Field must be unique!"));
|
||||||
|
}
|
||||||
|
},
|
||||||
|
},
|
||||||
|
]}
|
||||||
|
>
|
||||||
|
<Input
|
||||||
|
// id="email"
|
||||||
|
// name="email"
|
||||||
|
// type="email"
|
||||||
|
// ref={emailInput}
|
||||||
// value={username}
|
// value={username}
|
||||||
onCompositionStart={(e) => e.preventDefault()}
|
// onCompositionStart={(e) => e.preventDefault()}
|
||||||
// onCompositionEnd={handleComposition}
|
// onCompositionEnd={handleComposition}
|
||||||
// onChange={onNameChange}
|
// onChange={onNameChange}
|
||||||
// required
|
// required
|
||||||
|
prefix={<MailOutlined style={{ color: "rgba(0,0,0,.25)" }} />}
|
||||||
placeholder="邮箱验证,测试阶段"
|
placeholder="邮箱验证,测试阶段"
|
||||||
className={`${
|
className={
|
||||||
loading
|
"text-sm font-medium text-stone-600 dark:text-stone-400"
|
||||||
? "cursor-not-allowed bg-stone-50 dark:bg-stone-800"
|
|
||||||
: "bg-white hover:bg-stone-50 active:bg-stone-100 dark:bg-black dark:hover:border-white dark:hover:bg-black"
|
|
||||||
} group my-2 flex h-10 w-full items-center justify-center space-x-2 rounded-md border border-stone-200 transition-colors duration-75 focus:outline-none dark:border-stone-700
|
|
||||||
${
|
|
||||||
error
|
|
||||||
? "focus:invalid:border-red-500 focus:invalid:ring-red-500"
|
|
||||||
: ""
|
|
||||||
}
|
}
|
||||||
`}
|
// className={`${
|
||||||
|
// loading
|
||||||
|
// ? "cursor-not-allowed bg-stone-50 dark:bg-stone-800"
|
||||||
|
// : "bg-white hover:bg-stone-50 active:bg-stone-100 dark:bg-black dark:hover:border-white dark:hover:bg-black"
|
||||||
|
// } group my-2 flex h-10 w-full items-center justify-center space-x-2 rounded-md border border-stone-200 transition-colors duration-75 focus:outline-none dark:border-stone-700
|
||||||
|
// ${
|
||||||
|
// error
|
||||||
|
// ? "focus:invalid:border-red-500 focus:invalid:ring-red-500"
|
||||||
|
// : ""
|
||||||
|
// }
|
||||||
|
// `}
|
||||||
/>
|
/>
|
||||||
{/*{error && <p className="mt-2 text-pink-600 text-sm">{error}</p>}*/}
|
</Form.Item>
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div>
|
<Form.Item>
|
||||||
<button
|
<button
|
||||||
disabled={loading}
|
disabled={loading}
|
||||||
// onClick={(e) => handleSubmit(e)}
|
// onClick={() => loginForm.submit()}
|
||||||
type="submit"
|
type="submit"
|
||||||
className={`${
|
className={`${
|
||||||
loading
|
loading
|
||||||
@ -149,8 +321,8 @@ export default function UserLoginButton() {
|
|||||||
>
|
>
|
||||||
Sign in
|
Sign in
|
||||||
</button>
|
</button>
|
||||||
</div>
|
</Form.Item>
|
||||||
</form>
|
</Form>
|
||||||
</div>
|
</div>
|
||||||
{/*</div>*/}
|
{/*</div>*/}
|
||||||
</>
|
</>
|
||||||
|
@ -14,7 +14,7 @@
|
|||||||
border: 0;
|
border: 0;
|
||||||
border-top: 1px solid var(--color-separator);
|
border-top: 1px solid var(--color-separator);
|
||||||
display: block;
|
display: block;
|
||||||
margin: 2rem auto 1rem;
|
margin: 1rem auto 1rem;
|
||||||
overflow: visible
|
overflow: visible
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -47,7 +47,7 @@
|
|||||||
}
|
}
|
||||||
|
|
||||||
.signin form input[type],.signin>div input[type] {
|
.signin form input[type],.signin>div input[type] {
|
||||||
margin-bottom: .5rem
|
//margin-bottom: .5rem
|
||||||
}
|
}
|
||||||
|
|
||||||
.signin form button,.signin>div button {
|
.signin form button,.signin>div button {
|
||||||
@ -73,7 +73,7 @@ html {
|
|||||||
.login-form {
|
.login-form {
|
||||||
background-color: #fff;
|
background-color: #fff;
|
||||||
width: 350px;
|
width: 350px;
|
||||||
height: 500px;
|
height: 550px;
|
||||||
border-radius: 15px;
|
border-radius: 15px;
|
||||||
|
|
||||||
/* 定位到中心 */
|
/* 定位到中心 */
|
||||||
@ -87,3 +87,11 @@ html {
|
|||||||
backdrop-filter: blur(10px); /* 应用模糊效果 */
|
backdrop-filter: blur(10px); /* 应用模糊效果 */
|
||||||
background-color: rgba(255, 255, 255, 0.5); /* 半透明的白色背景 */
|
background-color: rgba(255, 255, 255, 0.5); /* 半透明的白色背景 */
|
||||||
}
|
}
|
||||||
|
|
||||||
|
input {
|
||||||
|
text-align: left !important
|
||||||
|
}
|
||||||
|
|
||||||
|
#login-form input:-webkit-autofill {
|
||||||
|
transition: background-color 5000s ease-in-out 0s;
|
||||||
|
}
|
||||||
|
116
lib/auth.ts
116
lib/auth.ts
@ -7,7 +7,7 @@ import prisma from "@/lib/prisma";
|
|||||||
import { User } from "@prisma/client";
|
import { User } from "@prisma/client";
|
||||||
import {ADMIN_LIST, isEmail, isName} from "@/lib/auth_list";
|
import {ADMIN_LIST, isEmail, isName} from "@/lib/auth_list";
|
||||||
import {createTransport} from "nodemailer";
|
import {createTransport} from "nodemailer";
|
||||||
|
import { comparePassword, hashPassword } from "@/lib/utils";
|
||||||
const SECURE_COOKIES:boolean = !!process.env.SECURE_COOKIES;
|
const SECURE_COOKIES:boolean = !!process.env.SECURE_COOKIES;
|
||||||
|
|
||||||
|
|
||||||
@ -73,13 +73,14 @@ export const authOptions: NextAuthOptions = {
|
|||||||
// You can pass any HTML attribute to the <input> tag through the object.
|
// You can pass any HTML attribute to the <input> tag through the object.
|
||||||
credentials: {
|
credentials: {
|
||||||
username: { label: "Username", type: "text", placeholder: "输入姓名或邮箱" },
|
username: { label: "Username", type: "text", placeholder: "输入姓名或邮箱" },
|
||||||
// password: { label: "Password", type: "password" }
|
password: { label: "Password", type: "password", placeholder: "密码验证,测试阶段" }
|
||||||
},
|
},
|
||||||
// @ts-ignore
|
// @ts-ignore
|
||||||
async authorize(credential, req) {
|
async authorize(credential, req) {
|
||||||
const username = cleanUpString(`${credential?.username}`);
|
const username = cleanUpString(`${credential?.username}`);
|
||||||
|
const password = cleanPassword(`${credential?.password}`);
|
||||||
// 验证用户名
|
// 验证用户名
|
||||||
// console.log(credential, username, '==============3')
|
// console.log(credential, 'p', password, '==============3')
|
||||||
// 判断姓名格式是否符合要求,不符合则拒绝
|
// 判断姓名格式是否符合要求,不符合则拒绝
|
||||||
if (username && isName(username)) {
|
if (username && isName(username)) {
|
||||||
// Any object returned will be saved in `user` property of the JWT
|
// Any object returned will be saved in `user` property of the JWT
|
||||||
@ -89,11 +90,21 @@ export const authOptions: NextAuthOptions = {
|
|||||||
} else {
|
} else {
|
||||||
user['name'] = username;
|
user['name'] = username;
|
||||||
}
|
}
|
||||||
return await insertUser(user) ?? user
|
// 目前用户不存在,则会创建新用户。
|
||||||
|
let existingUser = await existUser(user); // await insertUser(user)
|
||||||
|
if (!existingUser) {
|
||||||
|
// 如果不存在,则报错
|
||||||
|
// throw new Error("用户查询失败")
|
||||||
|
// 如果不存在,则创建
|
||||||
|
existingUser = await insertUser(user);
|
||||||
|
}
|
||||||
|
// 有密码就校验密码,没有就直接返回用户
|
||||||
|
password && validatePassword(password, existingUser.password);
|
||||||
|
return existingUser;
|
||||||
} else {
|
} else {
|
||||||
// If you return null then an error will be displayed advising the user to check their details.
|
// If you return null then an error will be displayed advising the user to check their details.
|
||||||
// return null
|
// return null
|
||||||
throw new Error("用户名校验失败")
|
throw new Error("username,用户名校验失败")
|
||||||
// You can also Reject this callback with an Error thus the user will be sent to the error page with the error message as a query parameter
|
// You can also Reject this callback with an Error thus the user will be sent to the error page with the error message as a query parameter
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -183,62 +194,17 @@ export async function VerifiedAdminUser() {
|
|||||||
return !!(name && ADMIN_LIST.includes(name));
|
return !!(name && ADMIN_LIST.includes(name));
|
||||||
}
|
}
|
||||||
|
|
||||||
// export function withSiteAuth(action: any) {
|
export function validatePassword(password: string, hashPassword: string | null | undefined ): boolean | void {
|
||||||
// return async (
|
if (!hashPassword) {
|
||||||
// formData: FormData | null,
|
throw new Error("password,未设置密码");
|
||||||
// siteId: string,
|
}
|
||||||
// key: string | null,
|
|
||||||
// ) => {
|
if (!comparePassword(password, hashPassword)) {
|
||||||
// const session = await getSession();
|
throw new Error("password,用户名或密码不正确")
|
||||||
// if (!session) {
|
} else {
|
||||||
// return {
|
return true;
|
||||||
// error: "Not authenticated",
|
}
|
||||||
// };
|
}
|
||||||
// }
|
|
||||||
// const site = await prisma.site.findUnique({
|
|
||||||
// where: {
|
|
||||||
// id: siteId,
|
|
||||||
// },
|
|
||||||
// });
|
|
||||||
// if (!site || site.userId !== session.user.id) {
|
|
||||||
// return {
|
|
||||||
// error: "Not authorized",
|
|
||||||
// };
|
|
||||||
// }
|
|
||||||
//
|
|
||||||
// return action(formData, site, key);
|
|
||||||
// };
|
|
||||||
// }
|
|
||||||
//
|
|
||||||
// export function withPostAuth(action: any) {
|
|
||||||
// return async (
|
|
||||||
// formData: FormData | null,
|
|
||||||
// postId: string,
|
|
||||||
// key: string | null,
|
|
||||||
// ) => {
|
|
||||||
// const session = await getSession();
|
|
||||||
// if (!session?.user.id) {
|
|
||||||
// return {
|
|
||||||
// error: "Not authenticated",
|
|
||||||
// };
|
|
||||||
// }
|
|
||||||
// const post = await prisma.post.findUnique({
|
|
||||||
// where: {
|
|
||||||
// id: postId,
|
|
||||||
// },
|
|
||||||
// include: {
|
|
||||||
// site: true,
|
|
||||||
// },
|
|
||||||
// });
|
|
||||||
// if (!post || post.userId !== session.user.id) {
|
|
||||||
// return {
|
|
||||||
// error: "Post not found",
|
|
||||||
// };
|
|
||||||
// }
|
|
||||||
//
|
|
||||||
// return action(formData, post, key);
|
|
||||||
// };
|
|
||||||
// }
|
|
||||||
|
|
||||||
async function existUser(user: {[key: string]: string} | User ) {
|
async function existUser(user: {[key: string]: string} | User ) {
|
||||||
const conditions = [];
|
const conditions = [];
|
||||||
@ -257,19 +223,20 @@ async function existUser(user: {[key: string]: string} | User ) {
|
|||||||
|
|
||||||
export async function insertUser(user: {[key: string]: string}) {
|
export async function insertUser(user: {[key: string]: string}) {
|
||||||
try {
|
try {
|
||||||
const existingUser = await existUser(user);
|
|
||||||
// console.log('[LOG]', existingUser, user, '=======')
|
|
||||||
if (!existingUser) {
|
|
||||||
return await prisma.user.create({
|
return await prisma.user.create({
|
||||||
data: user
|
data: user
|
||||||
})
|
})
|
||||||
} else {
|
// const existingUser = await existUser(user);
|
||||||
// console.log('user==========', existingUser)
|
// // console.log('[LOG]', existingUser, user, '=======')
|
||||||
return existingUser;
|
// if (!existingUser) {
|
||||||
}
|
//
|
||||||
|
// } else {
|
||||||
|
// // console.log('user==========', existingUser)
|
||||||
|
// return existingUser;
|
||||||
|
// }
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
console.log('[Prisma Error]', e);
|
throw new Error("username,用户创建失败");
|
||||||
return false;
|
// return false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -287,6 +254,15 @@ function cleanUpString(input: string): string {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function cleanPassword(input: string): string {
|
||||||
|
try {
|
||||||
|
// 去除前后空格
|
||||||
|
return input.trim()
|
||||||
|
}
|
||||||
|
catch {
|
||||||
|
return '';
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user