'use client'; import { useEffect, useState } from "react"; import { useRouter } from "next/navigation"; import ModalCloseSvg from "../svgs/closexsvg"; import apiService from "../lib/apiService"; type Props = { open: boolean; onClose: () => void; onSubmit?: (payload: { email: string; code?: string; newPassword: string }) => void; showVerification?: boolean; devVerificationState?: 'initial' | 'sent' | 'verified' | 'failed'; initialEmail?: string; }; export default function ChangePasswordModal({ open, onClose, onSubmit, showVerification = false, devVerificationState, initialEmail }: Props) { const router = useRouter(); const [email, setEmail] = useState(initialEmail || ""); const [code, setCode] = useState(""); const [newPassword, setNewPassword] = useState(""); const [confirmPassword, setConfirmPassword] = useState(""); const [error, setError] = useState(null); // 인증번호 오류 등 const [requireCode, setRequireCode] = useState(showVerification); const [isCodeSent, setIsCodeSent] = useState(showVerification); const canConfirm = code.trim().length > 0; const [isVerified, setIsVerified] = useState(false); const [isSending, setIsSending] = useState(false); const [isVerifying, setIsVerifying] = useState(false); const [showSuccessModal, setShowSuccessModal] = useState(false); const hasError = !!error; // initialEmail이 변경되면 email state 업데이트 useEffect(() => { if (initialEmail) { setEmail(initialEmail); } }, [initialEmail]); // 외부에서 전달된 개발모드 상태(devVerificationState)에 따라 UI 동기화 useEffect(() => { if (!devVerificationState) return; switch (devVerificationState) { case 'initial': setRequireCode(false); setIsCodeSent(false); setCode(""); setError(null); setIsVerified(false); break; case 'sent': setRequireCode(true); setIsCodeSent(true); setCode(""); setError(null); setIsVerified(false); break; case 'verified': setRequireCode(true); setIsCodeSent(true); setCode("123456"); setError(null); setIsVerified(true); break; case 'failed': setRequireCode(true); setIsCodeSent(true); setCode(""); setError("올바르지 않은 인증번호입니다. 인증번호를 확인해주세요."); setIsVerified(false); break; default: break; } }, [devVerificationState]); const handleLoginClick = () => { // 토큰 삭제 (로그아웃) if (typeof window !== 'undefined') { localStorage.removeItem('token'); document.cookie = 'token=; path=/; expires=Thu, 01 Jan 1970 00:00:00 GMT'; } // 로그인 페이지로 이동 router.push('/login'); onClose(); }; const handleSubmit = async () => { setError(null); if (requireCode) { if (!code) { setError("인증번호를 입력해 주세요."); return; } } if (!newPassword || !confirmPassword) { setError("새 비밀번호를 입력해 주세요."); return; } if (newPassword !== confirmPassword) { setError("새 비밀번호가 일치하지 않습니다."); return; } if (!email.trim()) { setError("이메일을 입력해 주세요."); return; } if (requireCode && !code.trim()) { setError("인증번호를 입력해 주세요."); return; } try { await apiService.resetPassword(email, code, newPassword, confirmPassword); onSubmit?.({ email, code: requireCode ? code : undefined, newPassword }); setShowSuccessModal(true); } catch (err) { setError(err instanceof Error ? err.message : "비밀번호 변경에 실패했습니다."); } }; const handleCancel = () => { // 모든 상태 초기화 setEmail(initialEmail || ""); setCode(""); setNewPassword(""); setConfirmPassword(""); setError(null); setRequireCode(showVerification); setIsCodeSent(showVerification); setIsVerified(false); setIsSending(false); setIsVerifying(false); onClose(); }; // 완료 팝업은 open prop과 관계없이 표시 if (showSuccessModal) { return (
{/* header */}
{/* body */}

비밀번호 변경이 완료됐습니다.

새로운 비밀번호로 다시 로그인 해주세요.

{/* footer */}
); } if (!open) return null; return (
{/* header */}

비밀번호 변경

{/* body */}
setEmail(e.target.value)} className={[ "h-10 flex-1 rounded-[8px] border border-input-border px-3 text-[16px] leading-[1.5] text-neutral-700 placeholder:text-text-placeholder-alt outline-none", hasError ? "bg-white" : isCodeSent ? "bg-neutral-50" : "bg-white", ].join(" ")} placeholder="이메일" />
{requireCode ? (
인증번호
setCode(e.target.value)} className="h-10 flex-1 rounded-[8px] border border-input-border bg-white px-3 text-[16px] leading-normal text-neutral-700 placeholder:text-text-placeholder-alt outline-none" placeholder="인증번호를 입력해 주세요." />
{isCodeSent && !hasError && !isVerified ? (

인증 확인을 위해 작성한 이메일로 인증번호를 발송했습니다.

이메일을 확인해 주세요.

) : null} {error ? (

{error}

) : null}
) : null}
setNewPassword(e.target.value)} disabled={!isVerified} className={[ "h-10 rounded-[8px] border border-input-border px-3 text-[16px] leading-[1.5] text-neutral-700 placeholder:text-text-placeholder-alt outline-none", isVerified ? "bg-white" : "bg-neutral-50", ].join(" ")} placeholder="새 비밀번호" />
setConfirmPassword(e.target.value)} disabled={!isVerified} className={[ "h-10 rounded-[8px] border border-input-border px-3 text-[16px] leading-[1.5] text-neutral-700 placeholder:text-text-placeholder-alt outline-none", isVerified ? "bg-white" : "bg-neutral-50", ].join(" ")} placeholder="새 비밀번호 확인" />
{/* footer */}
); }