diff --git a/src/apis/postGoogleOauth.ts b/src/apis/postGoogleOauth.ts new file mode 100644 index 00000000..66e9e737 --- /dev/null +++ b/src/apis/postGoogleOauth.ts @@ -0,0 +1,11 @@ +import httpClient from '.'; + +const postGoogleOauth = async (code: string) => { + const response = await httpClient.post('/auth/signIn/GOOGLE', { + redirectUri: process.env.NEXT_PUBLIC_GOOGLE_REDIRECT_URI, + token: code, + }); + return response.data; +}; + +export default postGoogleOauth; diff --git a/src/apis/postNaverOauth.ts b/src/apis/postNaverOauth.ts new file mode 100644 index 00000000..56434bb0 --- /dev/null +++ b/src/apis/postNaverOauth.ts @@ -0,0 +1,12 @@ +import httpClient from '.'; + +const postNaverOauth = async (code: string, state: string) => { + const response = await httpClient.post('/auth/signIn/NAVER', { + state, + redirectUri: process.env.NEXT_PUBLIC_NAVER_REDIRECT_URI, + token: code, + }); + return response.data; +}; + +export default postNaverOauth; diff --git a/src/hooks/useGoogleLogin.ts b/src/hooks/useGoogleLogin.ts new file mode 100644 index 00000000..46045f44 --- /dev/null +++ b/src/hooks/useGoogleLogin.ts @@ -0,0 +1,41 @@ +import postGoogleOauth from '@/apis/postGoogleOauth'; +import { toast } from '@/components/ui/use-toast'; +import { useMutation } from '@tanstack/react-query'; +import { isAxiosError } from 'axios'; +import { useRouter } from 'next/router'; + +const useGoogleLogin = () => { + const router = useRouter(); + + return useMutation({ + mutationFn: async (code: string) => { + const result = await postGoogleOauth(code); + localStorage.setItem('accessToken', result.accessToken); + localStorage.setItem('refreshToken', result.refreshToken); + return result; + }, + onSuccess: () => { + router.push('/epigrams'); + }, + onError: (error) => { + if (isAxiosError(error)) { + const status = error.response?.status; + + if (!status) return; + + if (status === 400) { + toast({ description: '잘못된 요청입니다. 요청을 확인해 주세요.', className: 'bg-state-error text-white font-semibold' }); + router.push('/auth/SignIn'); + return; + } + + if (status >= 500) { + toast({ description: '서버에 문제가 발생했습니다. 잠시 후 다시 시도해 주세요.', className: 'bg-state-error text-white font-semibold' }); + } + } + toast({ description: '알 수 없는 에러가 발생했습니다.', className: 'bg-state-error text-white font-semibold' }); + }, + }); +}; + +export default useGoogleLogin; diff --git a/src/hooks/useKakaoLogin.ts b/src/hooks/useKakaoLogin.ts index 14d8d81b..ea627868 100644 --- a/src/hooks/useKakaoLogin.ts +++ b/src/hooks/useKakaoLogin.ts @@ -15,7 +15,7 @@ const useKakaoLogin = () => { return result; }, onSuccess: () => { - router.push('/'); + router.push('/epigrams'); }, onError: (error) => { if (isAxiosError(error)) { diff --git a/src/hooks/useNaverLogin.ts b/src/hooks/useNaverLogin.ts new file mode 100644 index 00000000..9ff23b36 --- /dev/null +++ b/src/hooks/useNaverLogin.ts @@ -0,0 +1,42 @@ +import postNaverOauth from '@/apis/postNaverOauth'; +import { toast } from '@/components/ui/use-toast'; +import { useMutation } from '@tanstack/react-query'; +import { isAxiosError } from 'axios'; +import { useRouter } from 'next/router'; + +const useNaverLogin = () => { + const router = useRouter(); + + return useMutation({ + mutationFn: async ({ code, state }: { code: string; state: string }) => { + const result = await postNaverOauth(code, state); + localStorage.setItem('accessToken', result.accessToken); + localStorage.setItem('refreshToken', result.refreshToken); + return result; + }, + onSuccess: () => { + router.push('/epigrams'); + }, + onError: (error) => { + if (isAxiosError(error)) { + const status = error.response?.status; + + if (!status) return; + + if (status === 400) { + toast({ description: '잘못된 요청입니다. 요청을 확인해 주세요.', className: 'bg-state-error text-white font-semibold' }); + router.push('/auth/SignIn'); + return; + } + + if (status >= 500) { + toast({ description: '서버에 문제가 발생했습니다. 잠시 후 다시 시도해 주세요.', className: 'bg-state-error text-white font-semibold' }); + } + } + + toast({ description: '알 수 없는 에러가 발생했습니다.', className: 'bg-state-error text-white font-semibold' }); + }, + }); +}; + +export default useNaverLogin; diff --git a/src/hooks/useSignInMutation.ts b/src/hooks/useSignInMutation.ts index 2f4ebb5e..0ed58dc1 100644 --- a/src/hooks/useSignInMutation.ts +++ b/src/hooks/useSignInMutation.ts @@ -2,6 +2,7 @@ import { postSignin } from '@/apis/auth'; import { toast } from '@/components/ui/use-toast'; import { useMutation } from '@tanstack/react-query'; import { useRouter } from 'next/router'; +import { isAxiosError } from 'axios'; const useSigninMutation = () => { const router = useRouter(); @@ -11,10 +12,36 @@ const useSigninMutation = () => { onSuccess: (data) => { localStorage.setItem('accessToken', data.accessToken); localStorage.setItem('refreshToken', data.refreshToken); - router.push('/'); + router.push('/epigrams'); }, - onError: () => { - toast({ description: '이메일 혹은 비밀번호를 확인해주세요.', className: 'border-state-error text-state-error font-semibold' }); + onError: (error) => { + if (!isAxiosError(error)) { + return; + } + + const { status } = error.response || {}; + + if (status === 500) { + toast({ + description: '서버 오류가 발생했습니다. 잠시 후 다시 시도해주세요.', + className: 'border-state-error text-state-error font-semibold', + }); + return; + } + + // NOTE: status값은 항상 있으며 undefined와 숫자를 비교연산 할 수 없어 Number로 설정 + if (Number(status) >= 500) { + toast({ + description: '서버에서 예상치 못한 문제가 발생했습니다. 잠시 후 다시 시도해주세요.', + className: 'border-state-error text-state-error font-semibold', + }); + return; + } + + toast({ + description: '이메일 혹은 비밀번호를 확인해주세요.', + className: 'border-state-error text-state-error font-semibold', + }); }, }); }; diff --git a/src/pages/auth/SignIn.tsx b/src/pages/auth/SignIn.tsx index c1bfd025..8e165591 100644 --- a/src/pages/auth/SignIn.tsx +++ b/src/pages/auth/SignIn.tsx @@ -77,19 +77,24 @@ export default function SignIn() {