From 291dc0538d8d90e88cd140559843118fa22d9c58 Mon Sep 17 00:00:00 2001 From: soomin9106 Date: Sat, 10 Aug 2024 15:16:47 +0900 Subject: [PATCH] feature: auth failure middleware redirection --- src/app/auth/validation/complete/page.tsx | 2 +- src/auth/components/EmailForm/index.tsx | 6 ++-- src/auth/hooks/useAuth.tsx | 2 ++ src/auth/hooks/useLoginFailToast.tsx | 24 ++++++++++++++ src/middleware.ts | 11 +++---- src/shared/constants/token.ts | 4 +++ src/shared/middlewares/auth.ts | 38 +++++++++++++++++++++-- 7 files changed, 75 insertions(+), 12 deletions(-) create mode 100644 src/auth/hooks/useLoginFailToast.tsx diff --git a/src/app/auth/validation/complete/page.tsx b/src/app/auth/validation/complete/page.tsx index 11a55287..5c00fbb4 100644 --- a/src/app/auth/validation/complete/page.tsx +++ b/src/app/auth/validation/complete/page.tsx @@ -15,7 +15,7 @@ export default function ValidationCompletePage() { const router = useRouter(); const auth_token = searchParams.get("auth_token"); - useAuth(auth_token? auth_token : ""); + // useAuth(auth_token? auth_token : ""); return (
diff --git a/src/auth/components/EmailForm/index.tsx b/src/auth/components/EmailForm/index.tsx index 2078e845..53384949 100644 --- a/src/auth/components/EmailForm/index.tsx +++ b/src/auth/components/EmailForm/index.tsx @@ -1,5 +1,4 @@ "use client"; - import { Button } from "@shared/components/ui/button"; import { Form, @@ -16,13 +15,16 @@ import { SUBSCRIBE_ANNOUCE, } from "@subscription/constants/subscribe"; -import { LOGIN_OR_SIGNUP } from "@auth/constants/auth"; +import { LOGIN_OR_SIGNUP, SIGNUP_FAILED } from "@auth/constants/auth"; import { useEmailForm } from "@auth/hooks/useEmailForm"; +import { useLoginFailToast } from "@auth/hooks/useLoginFailToast"; export default function EmailForm() { const { form, onSubmit, goToPendingPage } = useEmailForm(); const { handleSubmit, control, formState } = form; + useLoginFailToast(); + return (
diff --git a/src/auth/hooks/useAuth.tsx b/src/auth/hooks/useAuth.tsx index 296c1abd..1eab257f 100644 --- a/src/auth/hooks/useAuth.tsx +++ b/src/auth/hooks/useAuth.tsx @@ -23,6 +23,8 @@ export const useAuth = (auth_token: string) => { { auth_token }, { onSuccess: (response: ApiResponse) => { + console.log('res ', response); + if (response?.data?.data) { const { accessToken, refreshToken } = response.data.data; diff --git a/src/auth/hooks/useLoginFailToast.tsx b/src/auth/hooks/useLoginFailToast.tsx new file mode 100644 index 00000000..f3e23a54 --- /dev/null +++ b/src/auth/hooks/useLoginFailToast.tsx @@ -0,0 +1,24 @@ +import { useEffect } from "react"; + +import { deleteCookie,getCookie } from "cookies-next"; + +import { useToast } from "@shared/components/ui/use-toast"; +import { ISLOGIN } from "@shared/constants/token"; + +import { SIGNUP_FAILED } from "@auth/constants/auth"; + +export function useLoginFailToast() { + const { toast } = useToast(); + const isLoginFailed = getCookie(ISLOGIN); + + useEffect(() => { + if (isLoginFailed === "false") { + toast({ + title: SIGNUP_FAILED, + }); + + deleteCookie(ISLOGIN); + + } + }, [isLoginFailed, toast]); +} diff --git a/src/middleware.ts b/src/middleware.ts index 3f202e44..3980eb49 100644 --- a/src/middleware.ts +++ b/src/middleware.ts @@ -3,6 +3,7 @@ import { NextResponse } from "next/server"; import { COOKIES } from "@shared/constants/token"; import { articleMiddleware } from "@shared/middlewares/article"; +import { AuthMiddleware } from "@shared/middlewares/auth"; import { problemMiddleware } from "@shared/middlewares/problem"; import { unsubscriptionMiddleware } from "@shared/middlewares/subscription"; import { workbookMiddleware } from "@shared/middlewares/workbook"; @@ -15,10 +16,6 @@ const withOutAuth = async (req: NextRequest) => { const nextUrl = req.nextUrl.clone(); const { pathname, searchParams } = nextUrl; - // if (pathname === "/") { - // return MainMiddleware(); - // } - if (pathname === "/workbook") { return workbookMiddleware({ nextUrl }); } @@ -35,9 +32,9 @@ const withOutAuth = async (req: NextRequest) => { return problemMiddleware({ req, nextUrl }); } - // if (pathname.includes("/auth/validation/complete")) { - // return AuthMiddleware(); - // } + if (pathname.includes("/auth/validation/complete")) { + return AuthMiddleware({ req, nextUrl }); + } }; // NOTE : 인증기반 접근할 수 있는 페이지에 대한 middleware diff --git a/src/shared/constants/token.ts b/src/shared/constants/token.ts index add79bca..0a2bd160 100644 --- a/src/shared/constants/token.ts +++ b/src/shared/constants/token.ts @@ -2,3 +2,7 @@ export const COOKIES = { ACCESS_TOKEN: "accessToken", REFRESH_TOKEN: "refreshToken", }; + +export const ISLOGIN = 'isLogin' + +export const AUTH_TOKEN = 'auth_token' diff --git a/src/shared/middlewares/auth.ts b/src/shared/middlewares/auth.ts index 646c5610..691c8dfc 100644 --- a/src/shared/middlewares/auth.ts +++ b/src/shared/middlewares/auth.ts @@ -1,3 +1,37 @@ -export const AuthMiddleware = () => { - return true; +import { NextURL } from "next/dist/server/web/next-url"; +import { NextRequest, NextResponse } from "next/server"; + +import { ApiResponse, fewFetch } from "@api/fewFetch"; + +import { API_ROUTE } from "@auth/remotes/api"; +import { tokenResponse } from "@auth/types/auth"; + +type authMiddlewareProps = { + req: NextRequest; + nextUrl: NextURL; +}; + +export const AuthMiddleware = async ({ req, nextUrl }: authMiddlewareProps) => { + try { + const { searchParams } = nextUrl; + const auth_token = searchParams.get('auth_token') + if (auth_token) { + const response: ApiResponse = await fewFetch().post(API_ROUTE.TOKEN(auth_token)) + + if (response.data?.message === "알 수 없는 오류가 발생했어요." || !response.data?.data?.isLogin) { + nextUrl.pathname = `/auth` + nextUrl.searchParams.delete('auth_token') + + const response = NextResponse.redirect(nextUrl); + response.cookies.set('isLogin', 'false'); + return response; + } else { + if (response.data?.data?.isLogin) { + return NextResponse.redirect(nextUrl); + } + } + } + } catch { + return undefined + } };