CoffeeJoo_Panel_kafeDar/app/(auth)/register/page.js

258 lines
8.0 KiB
JavaScript
Raw Blame History

This file contains invisible Unicode characters

This file contains invisible Unicode characters that are indistinguishable to humans but may be processed differently by a computer. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

"use client";
import { useState } from "react";
import { useDispatch } from "react-redux";
import { useRouter } from "next/navigation";
import { setToken } from "@/redux/slices/authSlice";
import { setProfile } from "@/redux/slices/profileSlice";
import { showToast } from "@/redux/slices/toastSlice";
import authService from "@/services/auth";
import Link from "next/link";
export default function RegisterPage() {
const dispatch = useDispatch();
const router = useRouter();
const [formData, setFormData] = useState({
name: "",
email: "",
password: "",
confirmPassword: "",
});
const [errors, setErrors] = useState({});
const [isLoading, setIsLoading] = useState(false);
const validateForm = () => {
const newErrors = {};
if (!formData.name.trim()) {
newErrors.name = "نام الزامی است";
} else if (formData.name.trim().length < 3) {
newErrors.name = "نام باید حداقل 3 کاراکتر باشد";
}
if (!formData.email.trim()) {
newErrors.email = "ایمیل الزامی است";
} else if (!/^[^\s@]+@[^\s@]+\.[^\s@]+$/.test(formData.email)) {
newErrors.email = "ایمیل معتبر نیست";
}
if (!formData.password.trim()) {
newErrors.password = "رمز عبور الزامی است";
} else if (formData.password.length < 6) {
newErrors.password = "رمز عبور باید حداقل 6 کاراکتر باشد";
}
if (!formData.confirmPassword.trim()) {
newErrors.confirmPassword = "تأیید رمز عبور الزامی است";
} else if (formData.password !== formData.confirmPassword) {
newErrors.confirmPassword = "رمز عبور و تأیید آن یکسان نیستند";
}
setErrors(newErrors);
return Object.keys(newErrors).length === 0;
};
const handleChange = (e) => {
const { name, value } = e.target;
setFormData((prev) => ({
...prev,
[name]: value,
}));
// پاک کردن error هنگام تایپ
if (errors[name]) {
setErrors((prev) => ({
...prev,
[name]: "",
}));
}
};
const handleSubmit = async (e) => {
e.preventDefault();
if (!validateForm()) {
return;
}
setIsLoading(true);
try {
const response = await fetch("/api/auth/register", {
method: "POST",
headers: {
"Content-Type": "application/json",
},
body: JSON.stringify({
name: formData.name,
email: formData.email,
password: formData.password,
}),
});
if (!response.ok) {
const error = await response.json();
throw new Error(error.message || "خطا در ثبت‌نام");
}
const data = await response.json();
dispatch(
setProfile(
data.user || { name: formData.name, email: formData.email }
)
);
dispatch(
showToast({
message: "ثبت‌نام شما موفق بود! خوش آمدید",
type: "success",
})
);
router.push("/");
} catch (error) {
dispatch(
showToast({
message: error.message || "خطایی در حین ثبت‌نام رخ داد",
type: "error",
})
);
setErrors((prev) => ({
...prev,
submit: error.message,
}));
} finally {
setIsLoading(false);
}
};
return (
<div className="min-h-screen flex items-center justify-center bg-linear-to-br from-green-50 to-teal-100 px-4">
<div className="w-full max-w-md bg-white rounded-lg shadow-lg p-8">
<h1 className="text-3xl font-bold text-center text-gray-800 mb-2">
ثبتنام
</h1>
<p className="text-center text-gray-600 mb-6">
حساب کاربری جدید ایجاد کنید
</p>
{errors.submit && (
<div className="mb-4 p-3 bg-red-50 border border-red-200 rounded-lg text-red-700 text-sm">
{errors.submit}
</div>
)}
<form onSubmit={handleSubmit} className="space-y-5">
{/* Name Field */}
<div>
<label className="block text-sm font-medium text-gray-700 mb-1">
نام
</label>
<input
type="text"
name="name"
value={formData.name}
onChange={handleChange}
placeholder="نام خود را وارد کنید"
className={`w-full px-4 py-2 border rounded-lg focus:outline-none focus:ring-2 focus:ring-teal-500 transition ${
errors.name ? "border-red-500" : "border-gray-300"
}`}
disabled={isLoading}
/>
{errors.name && (
<p className="mt-1 text-red-600 text-xs">{errors.name}</p>
)}
</div>
{/* Email Field */}
<div>
<label className="block text-sm font-medium text-gray-700 mb-1">
ایمیل
</label>
<input
type="email"
name="email"
value={formData.email}
onChange={handleChange}
placeholder="ایمیل خود را وارد کنید"
className={`w-full px-4 py-2 border rounded-lg focus:outline-none focus:ring-2 focus:ring-teal-500 transition ${
errors.email ? "border-red-500" : "border-gray-300"
}`}
disabled={isLoading}
/>
{errors.email && (
<p className="mt-1 text-red-600 text-xs">{errors.email}</p>
)}
</div>
{/* Password Field */}
<div>
<label className="block text-sm font-medium text-gray-700 mb-1">
رمز عبور
</label>
<input
type="password"
name="password"
value={formData.password}
onChange={handleChange}
placeholder="رمز عبور خود را وارد کنید"
className={`w-full px-4 py-2 border rounded-lg focus:outline-none focus:ring-2 focus:ring-teal-500 transition ${
errors.password ? "border-red-500" : "border-gray-300"
}`}
disabled={isLoading}
/>
{errors.password && (
<p className="mt-1 text-red-600 text-xs">{errors.password}</p>
)}
</div>
{/* Confirm Password Field */}
<div>
<label className="block text-sm font-medium text-gray-700 mb-1">
تأیید رمز عبور
</label>
<input
type="password"
name="confirmPassword"
value={formData.confirmPassword}
onChange={handleChange}
placeholder="رمز عبور را دوباره وارد کنید"
className={`w-full px-4 py-2 border rounded-lg focus:outline-none focus:ring-2 focus:ring-teal-500 transition ${
errors.confirmPassword ? "border-red-500" : "border-gray-300"
}`}
disabled={isLoading}
/>
{errors.confirmPassword && (
<p className="mt-1 text-red-600 text-xs">
{errors.confirmPassword}
</p>
)}
</div>
{/* Submit Button */}
<button
type="submit"
disabled={isLoading}
className="w-full bg-teal-600 text-white font-semibold py-2 rounded-lg hover:bg-teal-700 transition disabled:bg-gray-400 disabled:cursor-not-allowed"
>
{isLoading ? "درحال ثبت‌نام..." : "ثبت‌نام"}
</button>
</form>
{/* Login Link */}
<div className="mt-6 text-center text-gray-600">
قبلاً حساب دارید؟{" "}
<Link
href="/login"
className="text-teal-600 font-semibold hover:underline"
>
وارد شوید
</Link>
</div>
</div>
</div>
);
}