Commit 80239d34 authored by Jiwon Yoon's avatar Jiwon Yoon
Browse files

Merge branch 'master' into jiwon

parents 8e1da1f3 7e4f390c
...@@ -10,6 +10,7 @@ import MovieListPage from "./pages/MovieListPage"; ...@@ -10,6 +10,7 @@ import MovieListPage from "./pages/MovieListPage";
import MoviePage from "./pages/MoviePage"; import MoviePage from "./pages/MoviePage";
import TheaterPage from "./pages/TheaterPage"; import TheaterPage from "./pages/TheaterPage";
import MyPage from "./pages/MyPage"; import MyPage from "./pages/MyPage";
import GuestPage from "./pages/GuestPage";
import AdminPage from "./pages/AdminPage/AdminPage"; import AdminPage from "./pages/AdminPage/AdminPage";
import TicketingPage from "./pages/TicketingPage"; import TicketingPage from "./pages/TicketingPage";
import TicketingSeatPage from './pages/TicketingSeatPage' import TicketingSeatPage from './pages/TicketingSeatPage'
...@@ -37,6 +38,7 @@ function App() { ...@@ -37,6 +38,7 @@ function App() {
<Route path="/movielist" component={MovieListPage} /> <Route path="/movielist" component={MovieListPage} />
<Route path="/movie/:movieId" component={MoviePage} /> <Route path="/movie/:movieId" component={MoviePage} />
<Route path="/mypage" component={MyPage} /> <Route path="/mypage" component={MyPage} />
<Route path="/guest" component={GuestPage} />
<Route path="/ticket/seat" component={TicketingSeatPage} /> <Route path="/ticket/seat" component={TicketingSeatPage} />
<Route path="/ticket" component={TicketingPage} /> <Route path="/ticket" component={TicketingPage} />
<Route path="/payment" component={Payment} /> <Route path="/payment" component={Payment} />
......
...@@ -18,6 +18,11 @@ const logout = async () => { ...@@ -18,6 +18,11 @@ const logout = async () => {
return data return data
}; };
const guestLogin = async (guest) => {
const { data } = await axios.post(`${baseUrl}/api/auth/guest`, guest);
return data
}
const signup = async (user) => { const signup = async (user) => {
const url = `${baseUrl}/api/auth/signup`; const url = `${baseUrl}/api/auth/signup`;
const { data } = await axios.post(url, user); const { data } = await axios.post(url, user);
...@@ -63,12 +68,13 @@ const authApi = { ...@@ -63,12 +68,13 @@ const authApi = {
getUser, getUser,
login, login,
logout, logout,
guestLogin,
signup, signup,
confirmMbnum, confirmMbnum,
confirmNum, confirmNum,
profile, profile,
getMember, getMember,
comparePw, comparePw,
modifyUser, modifyUser
}; };
export default authApi export default authApi
\ No newline at end of file
...@@ -10,7 +10,10 @@ const getAllfromTM = async () => { ...@@ -10,7 +10,10 @@ const getAllfromTM = async () => {
const { data } = await axios.get(`${baseUrl}/api/movie/all`, payload) const { data } = await axios.get(`${baseUrl}/api/movie/all`, payload)
return data return data
} }
const getMovieIdfromTM = async (movieId) => {
const { data } = await axios.get(`${baseUrl}/api/movie/${movieId}`)
return data
}
const getMovieInfofromTM = async (id) => { const getMovieInfofromTM = async (id) => {
const movieId = id const movieId = id
const response = await axios.get(`${TMDBUrl}/${movieId}?api_key=${process.env.REACT_APP_TMDB_API_KEY}&language=ko-KR`) const response = await axios.get(`${TMDBUrl}/${movieId}?api_key=${process.env.REACT_APP_TMDB_API_KEY}&language=ko-KR`)
...@@ -71,6 +74,7 @@ const movieApi = { ...@@ -71,6 +74,7 @@ const movieApi = {
getCreditsfromTM, getCreditsfromTM,
getVideosfromTM, getVideosfromTM,
getListfromDB, getListfromDB,
getMovieIdfromTM,
submit, submit,
remove, remove,
search, search,
......
import axios from "axios";
import { baseUrl } from "../utils/baseUrl.js";
const findReservedSeats = async (timeTable) => {
const url = `${baseUrl}/api/reservation/findreservation`;
const { data } = await axios.post(url, timeTable);
return data
}
const findReservation = async () => {
const url = `${baseUrl}/api/reservation/findreservation`;
const { data } = await axios.get(url);
return data
}
const findOneReservation = async () => {
console.log("여기여기2");
const url = `${baseUrl}/api/reservation/findonereservation`;
const { data } = await axios.get(url);
return data
}
const save = async (save) => {
const url = `${baseUrl}/api/reservation/save`;
const { data } = await axios.post(url, save);
return data
}
const reservationApi = {
findReservation,
findReservedSeats,
findOneReservation,
save
}
export default reservationApi
\ No newline at end of file
...@@ -2,25 +2,26 @@ import { useState } from "react"; ...@@ -2,25 +2,26 @@ import { useState } from "react";
import styles from "./login.module.scss"; import styles from "./login.module.scss";
import { Redirect } from "react-router-dom"; import { Redirect } from "react-router-dom";
import catchErrors from "../../utils/catchErrors"; import catchErrors from "../../utils/catchErrors";
import {useAuth} from "../../context/auth_context.js"; import { useAuth } from "../../context/auth_context.js";
const Login = () => { const Login = () => {
const {login, loading} = useAuth(); const { login, guestLogin, loading } = useAuth();
//useState를 이용해서 각 state 생성 및 초기값 저장 //useState를 이용해서 각 state 생성 및 초기값 저장
const [state, setState] = useState(true); // 이 줄은 css에 해당하는 state const [state, setState] = useState(true); // 이 줄은 css에 해당하는 state
//state변수 지정 하지만 이 변수는 react에 의해 없어지지 않음, 그리고 그 다음 변수는 state변수를 갱신해주는 함수 //state변수 지정 하지만 이 변수는 react에 의해 없어지지 않음, 그리고 그 다음 변수는 state변수를 갱신해주는 함수
const [user, setUser] = useState({ const [user, setUser] = useState({
id: '', id: "",
password: '' password: ""
}); });
const [error, setError] = useState(""); const [error, setError] = useState("");
const [success, setSuccess] = useState(false); const [success, setSuccess] = useState(false);
const [guest, setGuset] = useState({ const [guest, setGuset] = useState({
guestName: '', guestName: "",
gusetBirthday: '', guestEmail: "",
gusetMbnum: '', guestBirthday: "",
guestPassword: '' guestMbnum: "",
guestPassword: ""
}) })
//input태그에 걸려있는 onchange에서 실행할 함수설정 //input태그에 걸려있는 onchange에서 실행할 함수설정
...@@ -41,13 +42,23 @@ const Login = () => { ...@@ -41,13 +42,23 @@ const Login = () => {
} }
const requestServer = async (data) => { const requestServer = async (data) => {
if(data === user){ try {
if (data === user) {
const success = await login(data); const success = await login(data);
if(success){ if (success) {
setSuccess(true); setSuccess("member");
alert('로그인이 완료되었습니다.') alert('로그인이 완료되었습니다.')
} }
}else{ } else {
const success = await guestLogin(data);
if (success) {
setSuccess("guest");
alert('로그인이 완료되었습니다.')
}
}
} catch (error) {
catchErrors(error, setError);
} }
} }
...@@ -60,15 +71,16 @@ const Login = () => { ...@@ -60,15 +71,16 @@ const Login = () => {
} }
else { else {
requestServer(guest); requestServer(guest);
alert('로그인이 완료되었습니다.')
} }
} catch (error) { } catch (error) {
catchErrors(error, setError); catchErrors(error, setError);
} }
} }
if (success) { if (success === "member") {
return <Redirect to="/" />; return <Redirect to="/" />;
} else if (success === "guest"){
return <Redirect to="/guest" />;
} }
return ( return (
...@@ -90,8 +102,8 @@ const Login = () => { ...@@ -90,8 +102,8 @@ const Login = () => {
{/* 로그인 */} {/* 로그인 */}
<div className="tab-pane fade show active" id="login" role="tabpanel" aria-labelledby="login-tab"> <div className="tab-pane fade show active" id="login" role="tabpanel" aria-labelledby="login-tab">
<form className="d-flex flex-column" name="login" onSubmit={handleOnSummit}> <form className="d-flex flex-column" name="login" onSubmit={handleOnSummit}>
<input className={styles.input} type="text" name="id" placeholder="ID" onChange={handleLoginOnChange} maxLength="10" required /> <input className={styles.input} type="text" name="id" placeholder="ID" onChange={handleLoginOnChange} maxLength="10"/>
<input className={styles.input} type="password" name="password" placeholder="Password" onChange={handleLoginOnChange} maxLength="11" required /> <input className={styles.input} type="password" name="password" placeholder="Password" onChange={handleLoginOnChange} maxLength="11"/>
<input className={`rounded-2 mt-2 ${styles.butterYellowAndBtn} ${styles.btnHover}`} type="submit" value="Login" disabled={loading} /> <input className={`rounded-2 mt-2 ${styles.butterYellowAndBtn} ${styles.btnHover}`} type="submit" value="Login" disabled={loading} />
<span><a href="./signup" className={styles.intoSignupPage}>회원이 아니십니까?</a></span> <span><a href="./signup" className={styles.intoSignupPage}>회원이 아니십니까?</a></span>
</form> </form>
...@@ -99,11 +111,11 @@ const Login = () => { ...@@ -99,11 +111,11 @@ const Login = () => {
{/* 비회원예매 학인 */} {/* 비회원예매 학인 */}
<div className="tab-pane fade" id="guest" role="tabpanel" aria-labelledby="guest-tab"> <div className="tab-pane fade" id="guest" role="tabpanel" aria-labelledby="guest-tab">
<form className="d-flex flex-column" onSubmit={handleOnSummit}> <form className="d-flex flex-column" onSubmit={handleOnSummit}>
<input className={styles.input} type="text" name="guestName" id="guestName" placeholder="이름" onChange={handleGuestOnChange} maxLength="5" required /> <input className={styles.input} type="text" name="guestName" id="guestName" placeholder="이름" onChange={handleGuestOnChange} maxLength="10"/>
<input className={styles.input} type="email" name="guestEmail" id="guestEmail" placeholder="이메일" onChange={handleGuestOnChange} maxLength="16" required /> <input className={styles.input} type="email" name="guestEmail" id="guestEmail" placeholder="이메일" onChange={handleGuestOnChange} maxLength="20"/>
<input className={styles.input} type="number" name="gusetBirthday" id="gusetBirthday" placeholder="생년월일" onChange={handleGuestOnChange} maxLength="6" required /> <input className={styles.input} type="number" name="guestBirthday" id="guestBirthday" placeholder="생년월일" onChange={handleGuestOnChange} min="0" max="999999" />
<input className={styles.input} type="number" name="gusetMbnum" id="gusetMbnum" placeholder="휴대폰 번호" onChange={handleGuestOnChange} maxLength="11" required /> <input className={styles.input} type="number" name="guestMbnum" id="guestMbnum" placeholder="휴대폰 번호" onChange={handleGuestOnChange} min="0" max="99999999999" />
<input className={styles.input} type="password" name="guestPassword" id="password" placeholder="비밀번호" onChange={handleGuestOnChange} maxLength="11" required /> <input className={styles.input} type="password" name="guestPassword" id="guestPassword" placeholder="비밀번호" onChange={handleGuestOnChange} maxLength="20"/>
<p className={`text-white ${styles.fontSizeTwo}`}> <p className={`text-white ${styles.fontSizeTwo}`}>
비회원 정보 입력 예매 내역 확인/취소 티켓 발권이 어려울 있으니 다시 한번 확인해 주시기 바랍니다. 비회원 정보 입력 예매 내역 확인/취소 티켓 발권이 어려울 있으니 다시 한번 확인해 주시기 바랍니다.
</p> </p>
......
...@@ -202,14 +202,14 @@ const MyInfo = () => { ...@@ -202,14 +202,14 @@ const MyInfo = () => {
return ( return (
<> <>
{/* 마이페이지 창 */} {/* 마이페이지 창 */}
<div className="d-flex flex-column"> <div className={`${styles.main}`}>
<span className={styles.title}>마이페이지</span> <span className={styles.title}>마이페이지</span>
<div className={`d-flex justify-content-around`}> <div className={`d-flex justify-content-around`}>
<div className={`${styles.box}`}> <div className={`${styles.box}`}>
<p className={`${styles.hoverTxt}`}>프로필 변경</p> <p className={`${styles.hoverTxt}`}>프로필 변경</p>
<img src={`/upload/${profile}`} className={`figure-img img-fluid rounded-circle ${styles.img} ${styles.profile}`} role="button" data-bs-toggle="modal" data-bs-target="#staticBackdrop" /> <img src={`/upload/${profile}`} className={`figure-img img-fluid rounded-circle ${styles.img} ${styles.profile}`} role="button" data-bs-toggle="modal" data-bs-target="#staticBackdrop" />
</div> </div>
<div className="d-flex flex-column py-2 justify-content-around"> <div className="d-flex flex-column py-2 mx-3 justify-content-around">
<span className={`${styles.userName}`}>{`${userNickName}`} 반갑습니다!</span> <span className={`${styles.userName}`}>{`${userNickName}`} 반갑습니다!</span>
<button className={`rounded my-2 fs-5 ${styles.butterYellowAndBtn} ${styles.btnHover}`} data-bs-toggle="modal" href="#verifyPassword" >회원정보 수정</button> <button className={`rounded my-2 fs-5 ${styles.butterYellowAndBtn} ${styles.btnHover}`} data-bs-toggle="modal" href="#verifyPassword" >회원정보 수정</button>
</div> </div>
......
.main{
display: flex;
flex-direction: column;
align-items: center;
justify-content: center;
width: 100%;
}
.title{ .title{
display: flex; display: flex;
justify-content: center; justify-content: center;
color: #FEDC00; color: #FEDC00;
font-size: 3rem; font-size: 2.5rem;
margin: 2rem 0; margin: 2rem 0;
} }
...@@ -19,7 +27,7 @@ ...@@ -19,7 +27,7 @@
} }
.userName{ .userName{
color: white; color: white;
font-size: 1.8rem; font-size: 1.5rem;
} }
.contents{ .contents{
...@@ -61,8 +69,8 @@ ...@@ -61,8 +69,8 @@
.hoverTxt{ .hoverTxt{
display: none; display: none;
position:absolute; position:absolute;
top:5rem; top:4rem;
left:2.5rem; left:1.6rem;
color : #FEDC00; color : #FEDC00;
font-size: 1.5rem; font-size: 1.5rem;
} }
...@@ -70,8 +78,8 @@ ...@@ -70,8 +78,8 @@
display: block; display: block;
} }
.profile{ .profile{
width: 12rem; width: 10rem;
height: 12rem; height: 10rem;
} }
.profile:hover{ .profile:hover{
opacity: 0.5; opacity: 0.5;
...@@ -127,7 +135,7 @@ ...@@ -127,7 +135,7 @@
color: black; color: black;
} }
@media (max-width: 403px) { @media (max-width: 576px) {
.title{ .title{
display: flex; display: flex;
justify-content: center; justify-content: center;
...@@ -137,7 +145,7 @@ ...@@ -137,7 +145,7 @@
} }
.box{ .box{
width:8rem; width:8rem;
margin: 0px 1.5rem 0 0.5rem; margin: 0px 1rem;
position: relative; position: relative;
} }
...@@ -153,9 +161,9 @@ ...@@ -153,9 +161,9 @@
.hoverTxt{ .hoverTxt{
display: none; display: none;
position:absolute; position:absolute;
top:5rem; top:3.2rem;
left:2.5rem; left:1.7rem;
color : #FEDC00; color : #FEDC00;
font-size: 1.5rem; font-size: 1rem;
} }
} }
\ No newline at end of file
import { useEffect } from "react";
import { Link } from "react-router-dom"; import { Link } from "react-router-dom";
import { useAuth } from "../../context/auth_context.js" import { useAuth } from "../../context/auth_context.js"
const SubNav = () => { const SubNav = () => {
const { user, setUser, logout } = useAuth(); const { user, logout } = useAuth();
return ( return (
<> {(user.role !== "user") ?
<nav className="nav justify-content-end py-1">
{(user.role === "member")
? <Link className="nav-link text-white" to="/mypage">마이페이지</Link>
: <Link className="nav-link text-white" to="/admin">관리자페이지</Link>}
<Link className="nav-link text-white" to="/" onClick={logout}>로그아웃 </Link>
</nav> :
<nav className="nav justify-content-end py-1"> <nav className="nav justify-content-end py-1">
{(user.id === 0) ? <>
<Link className="nav-link text-white" to="/login">로그인</Link> <Link className="nav-link text-white" to="/login">로그인</Link>
<Link className="nav-link text-white" to="/signup" >회원가입</Link> <Link className="nav-link text-white" to="/signup" >회원가입</Link> </>
</nav> : <>{(user.role === "admin") ?
<Link className="nav-link text-white" to="/admin">관리자페이지</Link>
: ((user.role === "member") ?
<Link className="nav-link text-white" to="/mypage">마이페이지</Link>
: <Link className="nav-link text-white" to="/guest">예매확인</Link>)}
<Link className="nav-link text-white" to="/" onClick={logout}>로그아웃</Link></>
} }
</> </nav>
) )
} }
export default SubNav export default SubNav
\ No newline at end of file \ No newline at end of file
import { useState, useEffect } from "react";
import reservationApi from "../../apis/reservation.api";
import styles from "./reservation-details.module.scss"; import styles from "./reservation-details.module.scss";
const ReservationDetails = () => { const ReservationDetails = () => {
const [movies, setMovies] = useState([]);
const findReservaion = async () => {
const movieList = await reservationApi.findOneReservation();
setMovies(movieList);
}
useEffect(() => {
findReservaion();
}, [])
return ( return (
<div className={`d-flex flex-column align-items-center ${styles.width}`}> <div className={`d-flex flex-column align-items-center ${styles.width}`}>
<div className={`${styles.header}`}>나의 예매 내역</div> <div className={`${styles.header}`}>나의 예매 내역</div>
{movies.length > 0
? movies.map(movie => (
<div className={`${styles.body}`}> <div className={`${styles.body}`}>
<div className={`d-flex justify-content-around align-items-center py-3`}> <div className={`d-flex justify-content-around align-items-center py-3`}>
<div className={`${styles.span} d-flex justify-content-center`}> <div className={`${styles.span} d-flex justify-content-center`}>
<span className={`${styles.layout}`}>영화 포스터</span> <img src={`https://image.tmdb.org/t/p/original${movie.poster_path}`} className={`card-img-top rounded ${styles.poster}`} alt="Movie Poster" />
</div> </div>
<div className={`${styles.span} d-flex flex-column`}> <div className={`${styles.span} d-flex flex-column`}>
<span className={`${styles.layout}`}>영화제목</span> <span className={`${styles.layout}`}>{movie.title}</span>
<span className={`${styles.layout}`}>예매확인번호</span> <span className={`${styles.layout}`}>예매확인번호</span>
<span className={`${styles.layout}`}>예매날짜</span> <span className={`${styles.layout}`}></span>
<span className={`${styles.layout}`}>상영관</span> <span className={`${styles.layout}`}></span>
<span className={`${styles.layout}`}>좌석정보</span> <span className={`${styles.layout}`}>{movie.row} {movie.col}</span>
<span className={`${styles.layout}`}>결제금액</span> <span className={`${styles.layout}`}>결제금액</span>
<span className={`${styles.layout}`}>결제수단</span> <span className={`${styles.layout}`}>{movie.payment}</span>
</div> </div>
</div> </div>
</div> </div>
<div className={`${styles.header}`}>나의 리뷰</div> ))
: <div className={`${styles.layout}`}>예매 내역이 존재하지 않습니다.</div>}
</div> </div>
) )
} }
......
...@@ -4,27 +4,33 @@ ...@@ -4,27 +4,33 @@
justify-content: center; justify-content: center;
} }
.poster{
max-height: 20rem;
object-fit: contain;
}
.header{ .header{
display: flex; display: flex;
justify-content: center; justify-content: center;
background-color: #FEDC00; background-color: #FEDC00;
width: 80%; width: 70%;
text-align: center; text-align: center;
font-size: 2.5rem; font-size: 2.3rem;
margin: 5rem; margin: 3rem;
} }
.body{ .body{
width: 80%; width: 70%;
border-top: 1px solid #FEDC00; padding: 1rem 0;
border-bottom: 1px solid #FEDC00; border-bottom: 1px solid #FEDC00;
} }
.span .layout{ .layout{
color:white; color:white;
font-size: 1.5rem; font-size: 1.5rem;
} }
@media (max-width: 403px) { @media (max-width: 576px) {
.header{ .header{
display: flex; display: flex;
...@@ -33,7 +39,11 @@ ...@@ -33,7 +39,11 @@
width: 80%; width: 80%;
text-align: center; text-align: center;
font-size: 1.5rem; font-size: 1.5rem;
margin: 2rem; margin: 1rem;
} }
.layout{
color:white;
font-size: 1rem;
}
} }
\ No newline at end of file
import { createContext, useCallback, useContext, useEffect, useState } from "react"; import { createContext, useCallback, useContext, useEffect, useState } from "react";
import authApi from "../apis/auth.api"; import authApi from "../apis/auth.api";
import catchErrors from "../utils/catchErrors"; import catchErrors from "../utils/catchErrors";
import config from "../utils/clientConfig";
const AuthContext = createContext({ const AuthContext = createContext({
error: "", error: "",
...@@ -10,6 +9,7 @@ const AuthContext = createContext({ ...@@ -10,6 +9,7 @@ const AuthContext = createContext({
setUser: () => { }, setUser: () => { },
login: () => Promise.resolve(false), login: () => Promise.resolve(false),
logout: () => { }, logout: () => { },
guestLogin: () => Promise.resolve(false),
catchErrorAuth: (error, displayError) => { }, catchErrorAuth: (error, displayError) => { },
}); });
...@@ -34,7 +34,7 @@ const AuthProvider = ({ children }) => { ...@@ -34,7 +34,7 @@ const AuthProvider = ({ children }) => {
setLoading(true); setLoading(true);
const user = await authApi.login(id, password); const user = await authApi.login(id, password);
setUser(user); setUser(user);
return true; return true
} catch (error) { } catch (error) {
catchErrors(error, setError); catchErrors(error, setError);
return false; return false;
...@@ -57,6 +57,20 @@ const AuthProvider = ({ children }) => { ...@@ -57,6 +57,20 @@ const AuthProvider = ({ children }) => {
} }
}, []); }, []);
const guestLogin = useCallback(async (guest) => {
try {
setError("");
setLoading(true);
const user = await authApi.guestLogin(guest);
setUser(user);
return true
} catch (error) {
catchErrors(error, setError);
} finally {
setLoading(false);
}
}, []);
const catchErrorAuth = useCallback(async (error, displayError) => { const catchErrorAuth = useCallback(async (error, displayError) => {
let errorMsg; let errorMsg;
if (error.response) { if (error.response) {
...@@ -85,7 +99,7 @@ const AuthProvider = ({ children }) => { ...@@ -85,7 +99,7 @@ const AuthProvider = ({ children }) => {
return ( return (
<AuthContext.Provider <AuthContext.Provider
value={{ error, loading, user, setUser, login, logout, catchErrorAuth }} value={{ error, loading, user, setUser, login, logout, guestLogin, catchErrorAuth }}
> >
{children} {children}
</AuthContext.Provider> </AuthContext.Provider>
......
import ReservationDetails from "../components/ReservationDetails/ReservationDetails";
const GuestPage = () => {
return (
<div className="d-flex flex-column justify-content-center align-items-center py-4">
<ReservationDetails/>
</div>
)
}
export default GuestPage
\ No newline at end of file
import MyInfo from "../components/MyInfo/MyInfo" import MyInfo from "../components/MyInfo/MyInfo";
import ReservationDetails from "../components/ReservationDetails"; import ReservationDetails from "../components/ReservationDetails/ReservationDetails";
const MyPage = () => { const MyPage = () => {
return ( return (
......
...@@ -3,6 +3,7 @@ import { useAuth } from '../context/auth_context' ...@@ -3,6 +3,7 @@ import { useAuth } from '../context/auth_context'
import { useEffect, useState } from 'react' import { useEffect, useState } from 'react'
import catchErrors from '../utils/catchErrors' import catchErrors from '../utils/catchErrors'
import reservationApi from '../apis/reservation.api'
const PaymentCompletePage = () => { const PaymentCompletePage = () => {
...@@ -22,11 +23,12 @@ const PaymentCompletePage = () => { ...@@ -22,11 +23,12 @@ const PaymentCompletePage = () => {
async function getGuestInfo() { async function getGuestInfo() {
try { try {
if (user.id > 0) { if (user.id > 0) {
const response = await axios.get(`/api/auth/guestinfo/${user.id}`) const response = await axios.get(`/api/auth/guestinfo/${user.id}`);
const response2 = await axios.post(`/api/reservation/findonereservation`, { const guest = {
userType: "guest", userType: "guest",
user: user.id user: user.id
}) };
const response2 = await reservationApi.findOneReservation(guest);
console.log({ console.log({
reservationData: [...response2.data], reservationData: [...response2.data],
userData: { ...response.data }, userData: { ...response.data },
...@@ -55,10 +57,11 @@ const PaymentCompletePage = () => { ...@@ -55,10 +57,11 @@ const PaymentCompletePage = () => {
const response = await axios.post(`/api/auth/getuserinfo`, { const response = await axios.post(`/api/auth/getuserinfo`, {
id: user.id id: user.id
}) })
const response2 = await axios.post(`/api/reservation/findonereservation`, { const member = {
userType: "member", userType: "member",
user: user.id user: user.id
}) }
const response2 = await reservationApi.findOneReservation(member);
console.log(response2.data) console.log(response2.data)
if (response.data || response2.data) { if (response.data || response2.data) {
const responseEmail = await axios.post('/api/email/send', { const responseEmail = await axios.post('/api/email/send', {
......
import axios from 'axios' import axios from 'axios'
import { useEffect, useState } from 'react' import { useEffect, useState } from 'react'
import { useHistory } from 'react-router-dom' import { useHistory } from 'react-router-dom'
import reservationApi from '../../apis/reservation.api'
import { useAuth } from '../../context/auth_context' import { useAuth } from '../../context/auth_context'
import catchErrors from '../../utils/catchErrors' import catchErrors from '../../utils/catchErrors'
import styles from './PaymentPage.module.scss' import styles from './PaymentPage.module.scss'
...@@ -45,11 +46,11 @@ const Payment = ({ location }) => { ...@@ -45,11 +46,11 @@ const Payment = ({ location }) => {
async function handleClickGuest() { async function handleClickGuest() {
try { try {
const response = await axios.post('/api/auth/guest/save', { const response = await reservationApi.save({
...guestInfo ...guestInfo
}) });
setGuestID(response.data.id) setGuestID(response.data.id);
alert("비회원 정보가 저장되었습니다.") alert("비회원 정보가 저장되었습니다.");
} catch (error) { } catch (error) {
catchErrors(error, setError) catchErrors(error, setError)
} }
...@@ -68,7 +69,7 @@ const Payment = ({ location }) => { ...@@ -68,7 +69,7 @@ const Payment = ({ location }) => {
async function reservationComplete() { async function reservationComplete() {
try { try {
if (user.role === "member") { if (user.role === "member") {
const response = await axios.post(`/api/reservation/save`, { const response = await reservationApi.save({
userType: "member", userType: "member",
// payment: "카카오페이", // payment: "카카오페이",
user: userInfo.id, user: userInfo.id,
...@@ -93,7 +94,7 @@ const Payment = ({ location }) => { ...@@ -93,7 +94,7 @@ const Payment = ({ location }) => {
} }
} else { } else {
if (guestID) { if (guestID) {
const response = await axios.post(`/api/reservation/save`, { const response = await reservationApi.save({
userType: "guest", userType: "guest",
user: guestID, user: guestID,
...ticketInfo, ...ticketInfo,
......
...@@ -7,7 +7,7 @@ import styles from '../components/SeatTable/seatTable.module.scss' ...@@ -7,7 +7,7 @@ import styles from '../components/SeatTable/seatTable.module.scss'
import axios from 'axios' import axios from 'axios'
import { useAuth } from '../context/auth_context.js' import { useAuth } from '../context/auth_context.js'
import catchErrors from '../utils/catchErrors' import catchErrors from '../utils/catchErrors'
import { right } from '@popperjs/core' import reservationApi from '../apis/reservation.api.js'
const TicketingSeatPage = ({ location }) => { const TicketingSeatPage = ({ location }) => {
const history = useHistory() const history = useHistory()
...@@ -43,13 +43,13 @@ const TicketingSeatPage = ({ location }) => { ...@@ -43,13 +43,13 @@ const TicketingSeatPage = ({ location }) => {
theaterName: ticketInfo.selectedTheater theaterName: ticketInfo.selectedTheater
}) })
setTheaterInfo(response.data) setTheaterInfo(response.data)
const response2 = await axios.post('/api/reservation/findreservation', { const response2 = await reservationApi.findReservedSeats({
timetable: 1 timetable: 1
}) });
const reserve = response2.data.map((el) => const reserve = response2.data.map((el) =>
el.row + '-' + el.col el.row + '-' + el.col
) );
setReservedSeats(reserve) setReservedSeats(reserve);
} catch (error) { } catch (error) {
catchErrors(error, setError) catchErrors(error, setError)
} }
......
...@@ -65,6 +65,35 @@ const getAllMovie = async (req, res, next) => { ...@@ -65,6 +65,35 @@ const getAllMovie = async (req, res, next) => {
} }
} }
const getMovieById = async (req, res) => {
try {
const reservation = req.reservation
const movieId = reservation.map(movie => movie.movieId);
const elements = await Promise.all(
movieId.map(async (movieId) => {
const movie = await axios.get(`https://api.themoviedb.org/3/movie/${movieId}?api_key=${process.env.TMDB_APP_KEY}&language=ko-KR`)
const movieData = {
movieId : movie.data.id,
poster_path : movie.data.poster_path,
title : movie.data.title
}
return movieData
})
)
reservation.map(reservation => {
const movieId = elements.find(el => reservation.movieId === el.movieId )
reservation.dataValues = {
...reservation.dataValues,
poster_path: movieId.poster_path,
title: movieId.title
}
});
res.json(reservation);
} catch (error) {
return res.status(500).send(error.message || "영화 가져오기 중 에러 발생");
}
}
const getMovieList = async (req, res) => { const getMovieList = async (req, res) => {
const { category } = req.params const { category } = req.params
// console.log(category) // console.log(category)
...@@ -189,6 +218,7 @@ const findaboutAll = async (req, res, next) => { ...@@ -189,6 +218,7 @@ const findaboutAll = async (req, res, next) => {
export default { export default {
getListfromDB, getListfromDB,
getAllMovie, getAllMovie,
getMovieById,
getMovieList, getMovieList,
create, create,
remove, remove,
......
import axios from 'axios' import jwt from "jsonwebtoken";
import { Movie, Reservation, Theater } from '../db/index.js' import { Movie, Reservation, Theater, TimeTable } from '../db/index.js'
import sequelize from 'sequelize' import config from '../config/app.config.js'
const { Op } = sequelize
const findReservedSeats = async (req, res) => { const findReservedSeats = async (req, res) => {
const { timetable } = req.body
try { try {
const { timetable } = req.body
const reservedSeats = await Reservation.findAll({ const reservedSeats = await Reservation.findAll({
where: { where: {
timetable: timetable timetable: timetable
...@@ -17,11 +16,12 @@ const findReservedSeats = async (req, res) => { ...@@ -17,11 +16,12 @@ const findReservedSeats = async (req, res) => {
} }
} }
const findReservation = async (req, res) => { const findReservation = async (req, res) => {
const { user } = req.body
try { try {
const token = req.cookies.butterStudio;
const { id } = jwt.verify(token, config.jwtSecret);
const reservation = await Reservation.findAll({ const reservation = await Reservation.findAll({
where: { where: {
user: user user: id
} }
}) })
res.json(reservation) res.json(reservation)
...@@ -29,17 +29,21 @@ const findReservation = async (req, res) => { ...@@ -29,17 +29,21 @@ const findReservation = async (req, res) => {
res.status(500).send(error.message || "예매 내역들을 찾는 중 오류발생") res.status(500).send(error.message || "예매 내역들을 찾는 중 오류발생")
} }
} }
const findOneReservation = async (req, res) => { const findOneReservation = async (req, res, next) => {
const { userType, user } = req.body
try { try {
const token = req.cookies.butterStudio;
const { id, role } = jwt.verify(token, config.jwtSecret);
const reservation = await Reservation.findAll({ const reservation = await Reservation.findAll({
where: { where: {
userType: userType, userType: role,
user: user user: id
}, },
}) include: [Theater, TimeTable]
// console.log(reservation) });
res.json(reservation) console.log(reservation);
req.reservation = reservation
next()
// res.json(reservation);
} catch (error) { } catch (error) {
res.status(500).send(error.message || "예매 내역을 찾는 중 오류 발생") res.status(500).send(error.message || "예매 내역을 찾는 중 오류 발생")
} }
...@@ -54,10 +58,10 @@ const saveReservation = async (req, res) => { ...@@ -54,10 +58,10 @@ const saveReservation = async (req, res) => {
user: user, user: user,
userType: userType, userType: userType,
movieId: movieId, movieId: movieId,
theater: selectedTheater, theaterId: selectedTheater,
row: rows[index], row: rows[index],
col: cols[index], col: cols[index],
timetable: timetable, timetableId: timetable,
payment: payment, payment: payment,
totalFee: totalFee totalFee: totalFee
}) })
......
...@@ -10,8 +10,8 @@ const getUser = async (req, res) => { ...@@ -10,8 +10,8 @@ const getUser = async (req, res) => {
try { try {
if (req.cookies.butterStudio) { if (req.cookies.butterStudio) {
const token = req.cookies.butterStudio; const token = req.cookies.butterStudio;
const decoded = jwt.verify(token, config.jwtSecret); const { id, role } = jwt.verify(token, config.jwtSecret);
res.json(decoded); res.json( { id, role } );
} else { } else {
res.json({ id: 0, role: "user" }); res.json({ id: 0, role: "user" });
} }
...@@ -70,7 +70,45 @@ const logout = async (req, res) => { ...@@ -70,7 +70,45 @@ const logout = async (req, res) => {
id: 0, id: 0,
role: "user", role: "user",
}) })
res.send('successfully cookie cleared.') } catch (error) {
console.error(error);
return res.status(500).send("로그인 에러");
}
}
//비회원 예매확인 로그인
const guestLogin = async (req, res) => {
try {
const {guestName, guestEmail, guestBirthday, guestMbnum, guestPassword} = req.body;
const guest = await Guest.findOne({ where : {
name: guestName,
email: guestEmail,
birth: guestBirthday,
phoneNumber: guestMbnum,
password: guestPassword,
}});
if (!guest) {
return res.status(422).send(`사용자가 존재하지 않습니다`);
}else{
const guestRole = await guest.getRole();
const signData = {
id: guest.id,
role: guestRole.name
};
//토큰 생성
const token = jwt.sign(signData, config.jwtSecret, {
expiresIn: config.jwtExpires,
});
// 토큰을 쿠키에 저장
res.cookie(config.cookieName, token, {
maxAge: config.cookieMaxAge,
path: "/",
httpOnly: config.env === "production",
secure: config.env === "production",
});
// 사용자 반환
res.json(signData);
}
} catch (error) { } catch (error) {
console.error(error); console.error(error);
return res.status(500).send("로그인 에러"); return res.status(500).send("로그인 에러");
...@@ -277,9 +315,9 @@ const signup = async (req, res) => { ...@@ -277,9 +315,9 @@ const signup = async (req, res) => {
const getMember = async (req, res) => { const getMember = async (req, res) => {
try { try {
const token = req.cookies.butterStudio; const token = req.cookies.butterStudio;
const decoded = jwt.verify(token, config.jwtSecret); const { id, role } = jwt.verify(token, config.jwtSecret);
if (decoded.role === "member") { if ( role === "member") {
const user = await User.findOne({ where: { id: decoded.id } }); const user = await User.findOne({ where: { id: id } });
res.json({ nickname: user.nickname, img: user.img }); res.json({ nickname: user.nickname, img: user.img });
} else { } else {
res.status(500).send("잘못된 접근입니다."); res.status(500).send("잘못된 접근입니다.");
...@@ -294,17 +332,17 @@ const uploadProfile = async (req, res) => { ...@@ -294,17 +332,17 @@ const uploadProfile = async (req, res) => {
try { try {
const image = req.file.filename; const image = req.file.filename;
const token = req.cookies.butterStudio; const token = req.cookies.butterStudio;
const decoded = jwt.verify(token, config.jwtSecret); const { id } = jwt.verify(token, config.jwtSecret);
if (decoded) { if (id) {
const img = await User.findOne({ where: { id: decoded.id }, attributes: ["img"] }); const img = await User.findOne({ where: { id: id }, attributes: ["img"] });
fs.unlink("upload" + `\\${img.img}`, function (data) { console.log(data); }); fs.unlink("upload" + `\\${img.img}`, function (data) { console.log(data); });
const user = await User.update({ const user = await User.update({
img: image img: image
}, { where: { id: decoded.id } }); }, { where: { id: id } });
if (user) { if (user) {
const success = await User.findOne({ where: { id: decoded.id }, attributes: ["img"] }); const success = await User.findOne({ where: { id: id }, attributes: ["img"] });
res.json(success) res.json(success)
} else { } else {
throw new Error("프로필 등록 실패") throw new Error("프로필 등록 실패")
...@@ -320,9 +358,9 @@ const comparePw = async (req, res) => { ...@@ -320,9 +358,9 @@ const comparePw = async (req, res) => {
try { try {
//쿠키 안 토큰에서 id추출 //쿠키 안 토큰에서 id추출
const token = req.cookies.butterStudio; const token = req.cookies.butterStudio;
const decoded = jwt.verify(token, config.jwtSecret); const { id } = jwt.verify(token, config.jwtSecret);
//해당 id의 행 추출 //해당 id의 행 추출
const user = await User.scope("withPassword").findOne({ where: { id: decoded.id } }); const user = await User.scope("withPassword").findOne({ where: { id: id } });
//입력한 비번과 해당 행 비번을 비교 //입력한 비번과 해당 행 비번을 비교
const passwordMatch = await user.comparePassword(req.params.pw); const passwordMatch = await user.comparePassword(req.params.pw);
//클라이언트로 동일여부를 전송 //클라이언트로 동일여부를 전송
...@@ -337,9 +375,9 @@ const comparePw = async (req, res) => { ...@@ -337,9 +375,9 @@ const comparePw = async (req, res) => {
} }
} }
// 회원정보 수정할 때 쓰는 함수 // 회원정보 수정할 때 쓰는 함수
const overlap = async (decoded, dataType, data) => { const overlap = async ( id , dataType, data) => {
try { try {
let overlap = await User.findOne({ where: { id: decoded.id } }); let overlap = await User.findOne({ where: { id: id } });
// 변경할 데이터가 자기자신이면 true // 변경할 데이터가 자기자신이면 true
if (overlap[dataType] === data) { if (overlap[dataType] === data) {
return true return true
...@@ -360,7 +398,7 @@ const overlap = async (decoded, dataType, data) => { ...@@ -360,7 +398,7 @@ const overlap = async (decoded, dataType, data) => {
const modifyUser = async (req, res) => { const modifyUser = async (req, res) => {
try { try {
const token = req.cookies.butterStudio; const token = req.cookies.butterStudio;
const decoded = jwt.verify(token, config.jwtSecret); const { id } = jwt.verify(token, config.jwtSecret);
const { userName, userEmail, userNickName, userMbnum, userPassword } = req.body; const { userName, userEmail, userNickName, userMbnum, userPassword } = req.body;
let errorMsg = { let errorMsg = {
...@@ -379,8 +417,8 @@ const modifyUser = async (req, res) => { ...@@ -379,8 +417,8 @@ const modifyUser = async (req, res) => {
validation(errorMsg, userPassword, 8, 11, "errorPassword"); validation(errorMsg, userPassword, 8, 11, "errorPassword");
let valid = !(Object.values(errorMsg).some((element) => (element))); let valid = !(Object.values(errorMsg).some((element) => (element)));
const overlapEmail = await overlap(decoded, "email", userEmail); const overlapEmail = await overlap( id , "email", userEmail);
const overlapMbnum = await overlap(decoded, "phoneNumber", userMbnum); const overlapMbnum = await overlap( id , "phoneNumber", userMbnum);
if (!valid) { if (!valid) {
res.json(errorMsg); res.json(errorMsg);
} else { } else {
...@@ -391,7 +429,7 @@ const modifyUser = async (req, res) => { ...@@ -391,7 +429,7 @@ const modifyUser = async (req, res) => {
nickname: userNickName, nickname: userNickName,
phoneNumber: userMbnum, phoneNumber: userMbnum,
password: userPassword, password: userPassword,
}, { where: { id: decoded.id }, individualHooks: true }); }, { where: { id: id }, individualHooks: true });
res.json("성공"); res.json("성공");
} else if (!overlapEmail && overlapMbnum) { } else if (!overlapEmail && overlapMbnum) {
res.status(500).send("이미 있는 이메일입니다."); res.status(500).send("이미 있는 이메일입니다.");
...@@ -468,6 +506,7 @@ export default { ...@@ -468,6 +506,7 @@ export default {
getUser, getUser,
login, login,
logout, logout,
guestLogin,
confirmMbnum, confirmMbnum,
confirmNum, confirmNum,
signup, signup,
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment