diff --git a/global.d.ts b/global.d.ts index 1776b38..1c90dd2 100644 --- a/global.d.ts +++ b/global.d.ts @@ -1,5 +1,6 @@ declare global { interface Window { + Kakao: any; kakao: any; } } diff --git a/src/components/Landing/Landing.module.scss b/src/components/Landing/Landing.module.scss index 711e2a7..83d03d2 100644 --- a/src/components/Landing/Landing.module.scss +++ b/src/components/Landing/Landing.module.scss @@ -36,32 +36,6 @@ gap: 16px; } -.kakaoBtn { - width: 90%; - max-width: 350px; - height: 52px; - padding: 16px; - display: flex; - justify-content: center; - align-items: center; - flex-shrink: 0; - border-radius: 12px; - background: #ffe400; - color: #222; - @include BOLD; - line-height: 130%; - letter-spacing: -0.16px; - position: relative; - cursor: pointer; - - .kakaoIcon { - position: absolute; - left: 24px; - display: flex; - align-items: center; - } -} - .serviceBtn { max-width: 350px; text-align: center; diff --git a/src/components/Landing/Login/Login.module.scss b/src/components/Landing/Login/Login.module.scss new file mode 100644 index 0000000..900faf3 --- /dev/null +++ b/src/components/Landing/Login/Login.module.scss @@ -0,0 +1,27 @@ +@import '@/styles/globals.scss'; + +.kakaoBtn { + width: 90%; + max-width: 350px; + height: 52px; + padding: 16px; + display: flex; + justify-content: center; + align-items: center; + flex-shrink: 0; + border-radius: 12px; + background: #ffe400; + color: #222; + @include BOLD; + line-height: 130%; + letter-spacing: -0.16px; + position: relative; + cursor: pointer; + + .kakaoIcon { + position: absolute; + left: 24px; + display: flex; + align-items: center; + } +} diff --git a/src/components/Landing/Login/index.tsx b/src/components/Landing/Login/index.tsx new file mode 100644 index 0000000..811eb3b --- /dev/null +++ b/src/components/Landing/Login/index.tsx @@ -0,0 +1,75 @@ +import { useState } from 'react'; +import { useRouter } from 'next/router'; +import styles from './Login.module.scss'; +import IconComponent from '@/components/Asset/Icon'; +import BASE_URL from '@/constants/baseurl'; + +interface AuthObj { + access_token: string; + expires_in: number; + refresh_token: string; + refresh_token_expires_in: number; + scope: string; + token_type: string; +} + +interface ErrorResponse { + error: string; + error_description: string; +} + +export default function Login() { + const [loading, setLoading] = useState(false); + const APP_KEY = process.env.NEXT_PUBLIC_KAKAO_MAP_APP_KEY; + + const router = useRouter(); + + const handleLogin = async () => { + setLoading(true); + + if (!window.Kakao.isInitialized()) { + window.Kakao.init(APP_KEY); + } + + window.Kakao.Auth.login({ + success: async (authObj: AuthObj) => { + try { + const response = await BASE_URL.post('/auth/login', { + kakaoAccessToken: authObj.access_token, + }); + + localStorage.setItem('access_token', authObj.access_token); + router.push('/map'); + } catch (error) { + console.error('로그인 실패:', error); + } finally { + setLoading(false); + } + }, + fail: (error: ErrorResponse) => { + console.error('로그인 실패:', error); + setLoading(false); + }, + }); + }; + + return ( +
+
+ +
+ {loading ? '로그인 중...' : '카카오로 계속하기'} +
+ ); +} diff --git a/src/components/Landing/index.tsx b/src/components/Landing/index.tsx index 1705007..7777ffb 100644 --- a/src/components/Landing/index.tsx +++ b/src/components/Landing/index.tsx @@ -1,6 +1,7 @@ import Link from 'next/link'; import IconComponent from '../Asset/Icon'; import styles from './Landing.module.scss'; +import Login from './Login'; export default function Landing() { return ( @@ -18,17 +19,7 @@ export default function Landing() {
-
-
- -
- 카카오로 계속하기 -
+
서비스 둘러보기 diff --git a/src/constants/baseurl.tsx b/src/constants/baseurl.tsx new file mode 100644 index 0000000..c198503 --- /dev/null +++ b/src/constants/baseurl.tsx @@ -0,0 +1,26 @@ +import axios, { InternalAxiosRequestConfig } from 'axios'; + +const BASE_URL = axios.create({ + baseURL: 'http://ec2-13-124-234-41.ap-northeast-2.compute.amazonaws.com:3000', +}); + +BASE_URL.interceptors.request.use( + async (config: InternalAxiosRequestConfig) => { + const token = localStorage.getItem('access_token'); + if (token) { + config.headers['Authorization'] = `Bearer ${token}`; + } + + if (config.headers['exclude-access-token']) { + delete config.headers['exclude-access-token']; + return config; + } + + return config; + }, + error => { + return Promise.reject(error); + } +); + +export default BASE_URL; diff --git a/src/pages/_document.tsx b/src/pages/_document.tsx index 40be6a4..414ffc8 100644 --- a/src/pages/_document.tsx +++ b/src/pages/_document.tsx @@ -5,10 +5,13 @@ export default function Document() { return ( +