From e9897d416b3e7327bbd4d4aef887eee37751ae82 Mon Sep 17 00:00:00 2001 From: dujinkim Date: Fri, 27 Jun 2025 01:16:20 +0000 Subject: (대표님) 20250627 오전 10시 작업사항 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- hooks/use-next-auth-reauth.ts | 76 +++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 76 insertions(+) create mode 100644 hooks/use-next-auth-reauth.ts (limited to 'hooks/use-next-auth-reauth.ts') diff --git a/hooks/use-next-auth-reauth.ts b/hooks/use-next-auth-reauth.ts new file mode 100644 index 00000000..6c17ddae --- /dev/null +++ b/hooks/use-next-auth-reauth.ts @@ -0,0 +1,76 @@ +// hooks/use-next-auth-reauth.ts +"use client" + +import * as React from "react" +import { useSession } from "next-auth/react" + +interface UseNextAuthReAuthOptions { + // 재인증 유효 시간 (밀리초, 기본값: 5분) + validDuration?: number + // 재인증이 필요한지 여부 + requireReAuth?: boolean +} + +export function useNextAuthReAuth(options: UseNextAuthReAuthOptions = {}) { + const { validDuration = 5 * 60 * 1000, requireReAuth = true } = options + const { data: session, status, update } = useSession() + + const [showReAuthModal, setShowReAuthModal] = React.useState(false) + const [isLoading, setIsLoading] = React.useState(true) + + // 재인증이 필요한지 확인 + const isAuthenticated = React.useMemo(() => { + if (!session || !requireReAuth) { + return status === "authenticated" + } + + // JWT 토큰에서 재인증 시간 확인 + const reAuthTime = session.user?.reAuthTime + if (!reAuthTime) return false + + const now = Date.now() + return (now - reAuthTime) < validDuration + }, [session, requireReAuth, validDuration, status]) + + React.useEffect(() => { + if (status === "loading") return + + if (status === "unauthenticated") { + setIsLoading(false) + return + } + + if (requireReAuth && !isAuthenticated) { + setShowReAuthModal(true) + } + + setIsLoading(false) + }, [status, requireReAuth, isAuthenticated]) + + const handleReAuthSuccess = React.useCallback(async () => { + // 세션 업데이트 (재인증 시간 포함) + await update({ + reAuthTime: Date.now() + }) + setShowReAuthModal(false) + }, [update]) + + const forceReAuth = React.useCallback(async () => { + // 재인증 강제 실행 + await update({ + reAuthTime: null + }) + setShowReAuthModal(true) + }, [update]) + + return { + isAuthenticated, + showReAuthModal, + isLoading, + userEmail: session?.user?.email || "", + handleReAuthSuccess, + forceReAuth, + sessionStatus: status, + session, + } +} \ No newline at end of file -- cgit v1.2.3