diff --git a/apps/client/package.json b/apps/client/package.json index cc953d5..7bd81c6 100644 --- a/apps/client/package.json +++ b/apps/client/package.json @@ -3,6 +3,7 @@ "version": "0.0.0", "private": true, "imports": { + "#images": "./src/assets/images/index.ts", "#icons/*.tsx": "./src/assets/icons/*.tsx", "#components/*.tsx": "./src/components/*.tsx", "#pages/*.tsx": "./src/pages/*.tsx", diff --git a/apps/client/src/App.css b/apps/client/src/App.css index dc35bf4..8bc457f 100644 --- a/apps/client/src/App.css +++ b/apps/client/src/App.css @@ -5,4 +5,9 @@ --yellow-color: #FEE500; --light-gray-color: #E9E9E9; --dark-gray-color: #AAAAAA; + --strawberry-color: #F3A7A7; + --banana-color: #F1F3A7; + --mint-color: #BBF0A8; + --blueberry-color: #C4A7F3; + --chocolate-color: #7B4B23; } \ No newline at end of file diff --git a/apps/client/src/App.tsx b/apps/client/src/App.tsx index 8d1e17b..477e964 100644 --- a/apps/client/src/App.tsx +++ b/apps/client/src/App.tsx @@ -5,6 +5,8 @@ import SignUp from '#pages/Signup.tsx'; import GoogleLogin from '#pages/GoogleLogin.tsx'; import KakaoLogin from '#pages/KakaoLogin.tsx'; import Cake from '#pages/Cake.tsx'; +import CreateCake from '#pages/CreateCake.tsx'; +import CreateLetter from '#pages/CreateLetter.tsx'; import './App.css'; const App = () => { @@ -14,7 +16,9 @@ const App = () => { } /> } /> } /> - } /> + } /> + } /> + } /> ); }; diff --git a/apps/client/src/assets/images/BananaCream.tsx b/apps/client/src/assets/images/BananaCream.tsx new file mode 100644 index 0000000..f9c9bcc --- /dev/null +++ b/apps/client/src/assets/images/BananaCream.tsx @@ -0,0 +1,866 @@ +import React from 'react'; +import type { SVGProps } from 'react'; + +const BananaCream = (props: SVGProps) => { + return ( + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + ); +}; + +export default BananaCream; diff --git a/apps/client/src/assets/images/BananaSheet.tsx b/apps/client/src/assets/images/BananaSheet.tsx new file mode 100644 index 0000000..b7bee36 --- /dev/null +++ b/apps/client/src/assets/images/BananaSheet.tsx @@ -0,0 +1,116 @@ +import React from 'react'; +import type { SVGProps } from 'react'; + +const BananaSheet = (props: SVGProps) => { + return ( + + + + + + + + + + + + + + + + + + + + + + + ); +}; + +export default BananaSheet; diff --git a/apps/client/src/assets/images/BlueberryCream.tsx b/apps/client/src/assets/images/BlueberryCream.tsx new file mode 100644 index 0000000..c027933 --- /dev/null +++ b/apps/client/src/assets/images/BlueberryCream.tsx @@ -0,0 +1,846 @@ +import React from 'react'; +import type { SVGProps } from 'react'; + +const BlueberryCream = (props: SVGProps) => { + return ( + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + ); +}; + +export default BlueberryCream; diff --git a/apps/client/src/assets/images/BlueberrySheet.tsx b/apps/client/src/assets/images/BlueberrySheet.tsx new file mode 100644 index 0000000..4649c14 --- /dev/null +++ b/apps/client/src/assets/images/BlueberrySheet.tsx @@ -0,0 +1,46 @@ +import React from 'react'; +import type { SVGProps } from 'react'; + +const BlueberrySheet = (props: SVGProps) => { + return ( + + + + + + + + + ); +}; + +export default BlueberrySheet; diff --git a/apps/client/src/assets/images/ChocoCream.tsx b/apps/client/src/assets/images/ChocoCream.tsx new file mode 100644 index 0000000..a11bb13 --- /dev/null +++ b/apps/client/src/assets/images/ChocoCream.tsx @@ -0,0 +1,736 @@ +import React from 'react'; +import type { SVGProps } from 'react'; + +const ChocoCream = (props: SVGProps) => { + return ( + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + ); +}; + +export default ChocoCream; diff --git a/apps/client/src/assets/images/ChocoSheet.tsx b/apps/client/src/assets/images/ChocoSheet.tsx new file mode 100644 index 0000000..ad527c5 --- /dev/null +++ b/apps/client/src/assets/images/ChocoSheet.tsx @@ -0,0 +1,66 @@ +import React from 'react'; +import type { SVGProps } from 'react'; + +const ChocoSheet = (props: SVGProps) => { + return ( + + + + + + + + + + + + + ); +}; + +export default ChocoSheet; diff --git a/apps/client/src/assets/images/MintCream.tsx b/apps/client/src/assets/images/MintCream.tsx new file mode 100644 index 0000000..6a3d9aa --- /dev/null +++ b/apps/client/src/assets/images/MintCream.tsx @@ -0,0 +1,956 @@ +import React from 'react'; +import type { SVGProps } from 'react'; + +const MintCream = (props: SVGProps) => { + return ( + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + ); +}; + +export default MintCream; diff --git a/apps/client/src/assets/images/MintSheet.tsx b/apps/client/src/assets/images/MintSheet.tsx new file mode 100644 index 0000000..327f2ce --- /dev/null +++ b/apps/client/src/assets/images/MintSheet.tsx @@ -0,0 +1,76 @@ +import React from 'react'; +import type { SVGProps } from 'react'; + +const MintSheet = (props: SVGProps) => { + return ( + + + + + + + + + + + + + + + ); +}; + +export default MintSheet; diff --git a/apps/client/src/assets/images/StrawberryCream.tsx b/apps/client/src/assets/images/StrawberryCream.tsx new file mode 100644 index 0000000..d16e078 --- /dev/null +++ b/apps/client/src/assets/images/StrawberryCream.tsx @@ -0,0 +1,806 @@ +import React from 'react'; +import type { SVGProps } from 'react'; + +const StrawberryCream = (props: SVGProps) => { + return ( + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + ); +}; + +export default StrawberryCream; diff --git a/apps/client/src/assets/images/StrawberrySheet.tsx b/apps/client/src/assets/images/StrawberrySheet.tsx new file mode 100644 index 0000000..9aad6d6 --- /dev/null +++ b/apps/client/src/assets/images/StrawberrySheet.tsx @@ -0,0 +1,66 @@ +import React from 'react'; +import type { SVGProps } from 'react'; + +const StrawberrySheet = (props: SVGProps) => { + return ( + + + + + + + + + + + + + ); +}; + +export default StrawberrySheet; diff --git a/apps/client/src/assets/images/WhiteCream.tsx b/apps/client/src/assets/images/WhiteCream.tsx new file mode 100644 index 0000000..259bc35 --- /dev/null +++ b/apps/client/src/assets/images/WhiteCream.tsx @@ -0,0 +1,536 @@ +import React from 'react'; +import type { SVGProps } from 'react'; + +const WhiteCream = (props: SVGProps) => { + return ( + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + ); +}; + +export default WhiteCream; diff --git a/apps/client/src/assets/images/WhiteSheet.tsx b/apps/client/src/assets/images/WhiteSheet.tsx new file mode 100644 index 0000000..4cef0c1 --- /dev/null +++ b/apps/client/src/assets/images/WhiteSheet.tsx @@ -0,0 +1,46 @@ +import React from 'react'; +import type { SVGProps } from 'react'; + +const WhiteSheet = (props: SVGProps) => { + return ( + + + + + + + + + ); +}; + +export default WhiteSheet; diff --git a/apps/client/src/assets/images/index.ts b/apps/client/src/assets/images/index.ts new file mode 100644 index 0000000..121293e --- /dev/null +++ b/apps/client/src/assets/images/index.ts @@ -0,0 +1,27 @@ +import BlueberrySheet from './BlueberrySheet'; +import BlueberryCream from './BlueberryCream'; +import StrawberrySheet from './StrawberrySheet'; +import StrawberryCream from './StrawberryCream'; +import ChocoSheet from './ChocoSheet'; +import ChocoCream from './ChocoCream'; +import MintSheet from './MintSheet'; +import MintCream from './MintCream'; +import BananaSheet from './BananaSheet'; +import BananaCream from './BananaCream'; +import WhiteSheet from './WhiteSheet'; +import WhiteCream from './WhiteCream'; + +export { + BlueberrySheet, + BlueberryCream, + StrawberryCream, + StrawberrySheet, + ChocoSheet, + ChocoCream, + MintSheet, + MintCream, + BananaSheet, + BananaCream, + WhiteSheet, + WhiteCream, +}; diff --git a/apps/client/src/components/Button.tsx b/apps/client/src/components/Button.tsx index b2a9eaf..19f1196 100644 --- a/apps/client/src/components/Button.tsx +++ b/apps/client/src/components/Button.tsx @@ -12,16 +12,18 @@ const StyledButton = styled.button<{ }>` width: 15rem; height: 3rem; + margin-top: 1rem; display: flex; align-items: center; justify-content: center; background-color: ${(props) => `var(${props.$bgColor})`}; - color: ${(props) => props.$textColor}; + color: ${(props) => `var(${props.$textColor})`}; border: ${(props) => props.$type === 'google' ? '1px solid var(--dark-gray-color)' : 'none'}; border-radius: 0.5rem; cursor: pointer; font-size: 1rem; + font-weight: 700; svg { margin-right: 1rem; diff --git a/apps/client/src/components/ColorSelector.tsx b/apps/client/src/components/ColorSelector.tsx new file mode 100644 index 0000000..d351967 --- /dev/null +++ b/apps/client/src/components/ColorSelector.tsx @@ -0,0 +1,104 @@ +import React, { SetStateAction, useState } from 'react'; +import styled from 'styled-components'; + +import { CakeColorType } from '@isttp/types/all'; + +const Title = styled.h2` + display: flex; + gap: 20px; + font-size: 24px; +`; + +const Button = styled.button<{ $active: boolean }>` + background: none; + border: none; + font-size: 24px; + color: ${(props) => + props.$active ? 'var(--orange-color)' : 'var(--dark-gray-color)'}; + cursor: pointer; + outline: none; + + &:hover { + color: #ff7043; + } +`; + +const ColorContainer = styled.div` + display: flex; + justify-content: center; + flex-wrap: wrap; + background-color: #e8e8e8; + padding: 20px; + border-radius: 10px; + margin-top: 20px; +`; + +const ColorOption = styled.div<{ $color: string; selected: boolean }>` + width: 60px; + height: 60px; + margin: 10px; + border-radius: 50%; + background-color: var(--${(props) => props.$color}-color); + border: ${(props) => + props.selected ? '5px solid #FF7043' : '5px solid transparent'}; + cursor: pointer; + transition: border 0.3s; + + &:hover { + border: 5px solid #ff7043; + } +`; + +type ColorSelectorProps = { + selectedSheet: string | null; + setSelectedSheet: React.Dispatch>; + selectedCream: string | null; + setSelectedCream: React.Dispatch>; +}; + +const ColorSelector: React.FC = ({ + selectedSheet, + setSelectedSheet, + selectedCream, + setSelectedCream, +}) => { + const [mode, setMode] = useState<'sheet' | 'cream'>('sheet'); + + const colors: CakeColorType[] = [ + 'white', + 'chocolate', + 'strawberry', + 'banana', + 'mint', + 'blueberry', + ]; + + const selectedColor = mode === 'sheet' ? selectedSheet : selectedCream; + const setSelectedColor = + mode === 'sheet' ? setSelectedSheet : setSelectedCream; + + return ( + <> + + <Button $active={mode === 'sheet'} onClick={() => setMode('sheet')}> + 시트 + </Button> + <Button $active={mode === 'cream'} onClick={() => setMode('cream')}> + 크림 + </Button> + + + {colors.map((color, index) => ( + setSelectedColor(color)} + /> + ))} + + + ); +}; + +export default ColorSelector; diff --git a/apps/client/src/components/RenderCake.tsx b/apps/client/src/components/RenderCake.tsx new file mode 100644 index 0000000..9f4fcb5 --- /dev/null +++ b/apps/client/src/components/RenderCake.tsx @@ -0,0 +1,60 @@ +import React from 'react'; +import styled from 'styled-components'; +import { CakeColorType } from '@isttp/types/all'; + +import * as Svg from '#images'; + +const SvgContainer = styled.div` + margin-top: 20px; + width: 300px; + height: 300px; + position: relative; +`; + +const SvgElement = styled.svg` + width: 100%; + height: 100%; + position: absolute; + top: 0; + left: 0; +`; + +type RenderedCakeProps = { + sheetColor: CakeColorType; + creamColor: CakeColorType; +}; + +const SheetSVG = { + white: Svg.WhiteSheet, + chocolate: Svg.ChocoSheet, + strawberry: Svg.StrawberrySheet, + banana: Svg.BananaSheet, + mint: Svg.MintSheet, + blueberry: Svg.BlueberrySheet, +}; + +const CreamSVG = { + white: Svg.WhiteCream, + chocolate: Svg.ChocoCream, + strawberry: Svg.StrawberryCream, + banana: Svg.BananaCream, + mint: Svg.MintCream, + blueberry: Svg.BlueberryCream, +}; + +const RenderCake: React.FC = ({ + sheetColor, + creamColor, +}) => { + const SheetComponent = SheetSVG[sheetColor]; + const CreamComponent = CreamSVG[creamColor]; + + return ( + + + + + ); +}; + +export default RenderCake; diff --git a/apps/client/src/components/Toggle.tsx b/apps/client/src/components/Toggle.tsx index 19b7e97..85fdd96 100644 --- a/apps/client/src/components/Toggle.tsx +++ b/apps/client/src/components/Toggle.tsx @@ -1,7 +1,9 @@ import React from 'react'; +import { useNavigate } from 'react-router-dom'; import styled, { css } from 'styled-components'; interface ToggleBtnProps { + ownerId: string; toggle: boolean; onClick: () => void; } @@ -10,14 +12,20 @@ interface Proptype { $istoggle: boolean; } -const Toggle: React.FC = ({ toggle, onClick }) => ( - - - - - - -); +const Toggle: React.FC = ({ ownerId, toggle, onClick }) => { + const navigate = useNavigate(); + + return ( + + + + + + + ); +}; export default Toggle; diff --git a/apps/client/src/components/cake/CakeInfo.tsx b/apps/client/src/components/cake/CakeInfo.tsx index f2d3d7c..d85a36d 100644 --- a/apps/client/src/components/cake/CakeInfo.tsx +++ b/apps/client/src/components/cake/CakeInfo.tsx @@ -1,24 +1,36 @@ import React, { useEffect, useState } from 'react'; -import axiosInstance from '#apis/axios.ts'; -import { CakeTypeResponse, PageTypeResponse } from '@isttp/types/all'; -import Pagenation from './Pagenation'; import { useParams } from 'react-router-dom'; +import axiosInstance from '#apis/axios.ts'; +import { + CakeTypeResponse, + PageTypeResponse, + CakeColorType, +} from '@isttp/types/all'; +import Pagenation from '#components/cake/Pagenation.tsx'; +import RenderCake from '#components/RenderCake.tsx'; -interface yearProp { +interface CakeInfoProps { year: string; + sheetColor: CakeColorType; + creamColor: CakeColorType; } -const CakeInfo: React.FC = ({ year }) => { +const CakeInfo: React.FC = ({ + year, + sheetColor, + creamColor, +}) => { const [cakeData, setCakeData] = useState([]); const [pageData, setPageData] = useState({ currentPage: 1, totalPage: 1, }); - const { cakeUserId } = useParams(); + + const { ownerId } = useParams(); async function getLetters(page: number) { const res = await axiosInstance.get( - `/cake/${cakeUserId}/${year}?keyword=false&page=${page}`, + `/cake/letters/${ownerId}/${year}?keyword=false&page=${page}`, ); setCakeData(res.data.data); setPageData({ @@ -27,9 +39,10 @@ const CakeInfo: React.FC = ({ year }) => { res.data.totalPage === 0 ? res.data.totalPage + 1 : res.data.totalPage, }); } + useEffect(() => { getLetters(1); - }, []); + }, [ownerId]); function changePage(page: number) { getLetters(page); @@ -37,7 +50,7 @@ const CakeInfo: React.FC = ({ year }) => { return ( <> -
케이크
+
{cakeData.map((cake, index) => (
diff --git a/apps/client/src/components/cake/MyCake.tsx b/apps/client/src/components/cake/MyCake.tsx index 110cde6..61af4ea 100644 --- a/apps/client/src/components/cake/MyCake.tsx +++ b/apps/client/src/components/cake/MyCake.tsx @@ -1,28 +1,83 @@ -import React, { useState } from 'react'; +import React, { useState, useEffect } from 'react'; +import { useNavigate } from 'react-router-dom'; +import axiosInstance from '#apis/axios.ts'; import Toggle from '#components/Toggle.tsx'; import GridInfo from '#components/GridInfo.tsx'; import CakeInfo from '#components/cake/CakeInfo.tsx'; import Wrapper from '#components/Wrapper.tsx'; -import { CakeUserTypeResponse } from '@isttp/types/all'; +import Button from '#components/Button.tsx'; +import { CakeUserTypeResponse, CakeColorType } from '@isttp/types/all'; -interface MyCakeProps { +type MyCakeProps = { + ownerId: string; data: CakeUserTypeResponse; +}; + +type CakeColorState = { + sheetColor: CakeColorType; + creamColor: CakeColorType; +}; + +function handleShareUrl() { + alert('기능 준비중'); } -const MyCake: React.FC = ({ data }) => { +const MyCake: React.FC = ({ ownerId, data }) => { + const navigate = useNavigate(); const [toggle, setToggle] = useState(false); + const [cakeColor, setCakeColor] = useState({ + sheetColor: 'chocolate', + creamColor: 'white', + }); const clickedToggle = () => { setToggle((prev) => !prev); }; + async function getColors(userId: string) { + try { + const res = await axiosInstance.get(`/cake/color/${userId}`); + + if (!res.data.sheetColor || !res.data.creamColor) { + navigate(`/cake/create/${userId}`); + } + + setCakeColor({ + sheetColor: res.data.sheetColor, + creamColor: res.data.creamColor, + }); + } catch (error) { + console.log(error); + // 에러 코드에 따라 모달 + } + } + + useEffect(() => { + getColors(ownerId); + }, [ownerId]); + return (

{data.nickname} 님의 케이크

장식초를 눌러 편지를 확인해보세요

- - {toggle ? : } + + {toggle ? ( + + ) : ( + <> + + +
+ ); +}; + +export default ChooseLetter; diff --git a/apps/client/src/components/letter/WriteLetter.tsx b/apps/client/src/components/letter/WriteLetter.tsx new file mode 100644 index 0000000..1ca2d23 --- /dev/null +++ b/apps/client/src/components/letter/WriteLetter.tsx @@ -0,0 +1,17 @@ +import React from 'react'; +import Wrapper from '#components/Wrapper.tsx'; + +type WriteLetterProps = { + handlePrev: () => void; +}; + +const WriteLetter = ({ handlePrev }: WriteLetterProps) => { + return ( + +

Write Letter

+ +
+ ); +}; + +export default WriteLetter; diff --git a/apps/client/src/pages/Cake.tsx b/apps/client/src/pages/Cake.tsx index de393fe..edeb5dc 100644 --- a/apps/client/src/pages/Cake.tsx +++ b/apps/client/src/pages/Cake.tsx @@ -7,23 +7,21 @@ import { CakeUserTypeResponse } from '@isttp/types/all'; import { useParams } from 'react-router-dom'; const Cake = () => { - const { cakeUserId } = useParams(); + const { ownerId } = useParams(); const [isMyCake, setIsMyCake] = useState(false); const [cakeUserData, setCakeUserData] = useState(); - async function chooseVersion() { - const res = await axiosInstance.get( - `cake/version?cakeUserId=${cakeUserId}`, - ); + async function chooseVersion(ownerId: string) { + const res = await axiosInstance.get(`cake/version?cakeUserId=${ownerId}`); setCakeUserData(res.data.data); - if (res.data.userId.userId === cakeUserId) { + if (res.data.userId === ownerId) { setIsMyCake(true); } } useEffect(() => { - chooseVersion(); - }, []); + chooseVersion(ownerId); + }, [ownerId]); if (!cakeUserData) { return
에러처리 해주기
; @@ -32,9 +30,9 @@ const Cake = () => { return ( {isMyCake ? ( - + ) : ( - + )} ); diff --git a/apps/client/src/pages/CreateCake.tsx b/apps/client/src/pages/CreateCake.tsx new file mode 100644 index 0000000..3ef758e --- /dev/null +++ b/apps/client/src/pages/CreateCake.tsx @@ -0,0 +1,113 @@ +import React, { useState, useEffect } from 'react'; +import { useNavigate, useParams } from 'react-router-dom'; +import { AxiosError } from 'axios'; +import axiosInstance from '#apis/axios.ts'; +import Button from '#components/Button.tsx'; +import Wrapper from '#components/Wrapper.tsx'; +import RenderCake from '#components/RenderCake.tsx'; +import ColorSelector from '#components/ColorSelector.tsx'; + +import { CakeColorType } from '@isttp/types/all'; + +async function getColors(userId: string) { + try { + const res = await axiosInstance.get(`/cake/color/${userId}`); + const { sheetColor, creamColor } = res.data; + + if (!sheetColor || !creamColor) { + return null; + } + + return { sheetColor, creamColor }; + } catch (error) { + console.log(error); + // 로그인이 필요합니다 모달 어떤 에러인지에 따라 모달 달리 하기 + } +} + +const CreateCake = () => { + const navigate = useNavigate(); + const { ownerId } = useParams(); + const [sheetColor, setSheetColor] = useState('white'); + const [creamColor, setCreamColor] = useState('chocolate'); + + async function handleCreateCake() { + try { + axiosInstance + .post('/cake/color', { + sheetColor: sheetColor, + creamColor: creamColor, + }) + .then((res) => { + if (res.status === 200) { + alert('케이크 만들기에 성공했습니다.'); + navigate(`/cake/${ownerId}`); + } else { + throw new Error('케이크 만들기에 실패했습니다.'); + } + }); + } catch (error) { + if (error instanceof AxiosError) { + if (error.response?.status === 401) { + alert('로그인이 필요합니다.'); + navigate('/'); + return; + } + } + } + } + + useEffect(() => { + const fetchIsOwner = async () => { + axiosInstance + .get('/user/me') + .then((res) => { + if (res.data.userId !== ownerId) { + alert('잘못된 접근입니다.'); + navigate(`/cake/${ownerId}`); + return; + } + }) + .catch((error) => { + console.error(error); + if (error instanceof AxiosError) { + if (error.response?.status === 401) { + alert('로그인이 필요합니다.'); + navigate('/'); + return; + } + } + }); + }; + + const fetchColors = async () => { + getColors(ownerId).then((res) => { + if (!res) { + return; + } + + setSheetColor(res.sheetColor); + setCreamColor(res.creamColor); + }); + }; + + fetchIsOwner(); + fetchColors(); + }, [ownerId]); + + return ( + +

케이크 만들기

+ + +