'use client'; import './style.scss'; import Link from 'next/link'; import { useRouter } from 'next/navigation'; import { useState, useEffect, useRef } from 'react'; import { VerificationType } from '@/constants/common'; import { VerifyEmailRequest, ResendEmailRequest } from '@/types/request/auth'; import { fetchApi } from '@/lib/utils/client'; import Loading from '@/app/component/Loading'; export default function Approval() { const router = useRouter(); const [loading, setLoading] = useState(false); const [error, setError] = useState(''); const [verifyCode, setVerifyCode] = useState(''); const verifyCodeRef = useRef(null); const type: string|null = sessionStorage.getItem('type'); const email: string = (sessionStorage.getItem('email') || ''); const expiration: string|null = sessionStorage.getItem('expiration'); const callbackURL: string = (sessionStorage.getItem('callbackURL') || '/'); // 인증번호 유지 시간 조회 const getResendApprovalSecond = (): number => { let remainResendApprovalSecond: string | null = sessionStorage.getItem('remainResendApprovalSecond'); if (!remainResendApprovalSecond) { remainResendApprovalSecond = '120'; // 2분 후 만료 sessionStorage.setItem('remainResendApprovalSecond', remainResendApprovalSecond); } return Number(remainResendApprovalSecond); }; const [resendApprovalSecond, setResendApprovalSecond] = useState( getResendApprovalSecond() ); // 다시 보내기 여부 const [canResend, setCanResend] = useState(false); useEffect(() => { if (error) { alert(error); setError(''); } }, [error]); // 페이지 벗어날 때 세션 정리 useEffect(() => { if (!email || email == '') { alert('잘못된 접근입니다.'); location.replace('/'); return; } // 인증 시간 만료 확인 if (type == null || type == "") { alert('다시 시도해주세요.'); router.push('/'); return; } if (!expiration || Date.now() > Number(expiration)) { alert('인증 시간이 만료되었습니다. 다시 시도해주세요.'); router.push(callbackURL); return; } const handleUnload = (e: BeforeUnloadEvent) => { const isReload = (e.type === 'beforeunload' || (performance.getEntriesByType('navigation')[0] as PerformanceNavigationTiming)?.type === 'reload' || performance.navigation.type === 1); if (isReload) { e.preventDefault(); return; } sessionStorage.clear(); } window.addEventListener('beforeunload', handleUnload); return () => window.removeEventListener('beforeunload', handleUnload); }, [expiration, router]); // 다시 보내기 타이머 설정 useEffect(() => { if (resendApprovalSecond <= 0) { setCanResend(true); sessionStorage.setItem('expiration', '0'); sessionStorage.removeItem('remainResendApprovalSecond'); return; } const timer = setInterval(() => { setResendApprovalSecond((prev) => { if (prev <= 1) { clearInterval(timer); setCanResend(true); return 0; } return prev - 1; }); }, 1000); sessionStorage.setItem('remainResendApprovalSecond', resendApprovalSecond.toString()); return () => clearInterval(timer); }, [resendApprovalSecond]); // 인증번호 검증 const handleSubmit = async (e: React.FormEvent) => { e.preventDefault(); setLoading(true); try { if (!verifyCode) { verifyCodeRef.current?.focus(); throw new Error('인증번호를 입력하세요.'); } await new Promise(resolve => setTimeout(resolve, 500)); const res = await fetchApi('/api/auth/verify-email', { method: 'POST', body: { Email: email, Code: verifyCode, Type: Number(type) } as VerifyEmailRequest }); sessionStorage.setItem('email', email); switch (type) { // 회원가입 완료 case VerificationType.Registration.toString(): router.push('/welcome'); break; // 비밀번호 변경 페이지 이동 case VerificationType.ForgotPassword.toString(): router.push('/reset-password'); break; } } catch (err) { if (err instanceof Error) { setError(err.message); } } finally { setLoading(false); } }; // 인증번호 다시 보내기 const handleResend = async () => { try { await fetchApi('/api/auth/resend-email', { method: 'POST', body: { Email: email, Type: Number(type) } as ResendEmailRequest }); setCanResend(false); setResendApprovalSecond(getResendApprovalSecond()); setVerifyCode(""); } catch (err) { if (err instanceof Error) { setError(err.message); } } }; return ( <> {loading && }
인증번호 확인

보안을 위해 인증번호를 발송했습니다.
수신된 인증번호를 입력해주세요.


setVerifyCode(e.target.value)} autoComplete="off" />

도움이 필요하신가요?
인증번호를 받을 수 없거나 오류가 발생한 경우 운영자에게 문의하세요.
); }