Commit 409bc0c7 authored by Kim, Subin's avatar Kim, Subin
Browse files

Merge remote-tracking branch 'origin/cherry' into kimpen

parents e1bf1bfd dbfe342d
import React, { useState, useEffect } from 'react'; import React, { useState, useEffect } from 'react';
import { Link, Redirect } from 'react-router-dom'; import { Link, Redirect } from 'react-router-dom';
import styled from 'styled-components'; import styled from 'styled-components';
import { Navbar, Nav, NavLink } from 'react-bootstrap';
import axios from 'axios';
const Nav = styled.nav` const MENU = styled(Navbar)`
background-color: #7B031D; background-color: #7B031D;
height: 6vh;
a { a {
color: #ffffff; color : white;
}
& .logoutBtn:hover {
text-decoration: underline;
} }
` `
function Menu() { function Menu() {
const [state, setState] = useState() const [state, setState] = useState()
const [user, setUser] = useState({ role: "" })
const name = localStorage.getItem('name'); const name = localStorage.getItem('name');
if (state) return <Redirect to="/" />;
function logout() { function logout() {
localStorage.clear(); localStorage.clear();
alert("로그아웃 되었습니다."); alert("로그아웃 되었습니다.");
setState(true); setState(true);
} }
useEffect(() => {
acheck();
}, [])
function acheck() {
axios.get(`/users/${localStorage.getItem('_id')}`)
.then(res => {
if (res.data.role == "admin") {
setUser(res.data)
}
}).catch(err => {
alert(err.error)
});
}
if (state) return <Redirect to="/" />
return ( return (
<Nav className="navbar sticky-top navbar-expand-md"> <MENU expand="md" variant="dark">
<a class="navbar-brand" href="#">대관 서비스</a> <Navbar.Brand href="#">대관 서비스</Navbar.Brand>
<button className="navbar-toggler" type="button" data-toggle="collapse" data-target="#collapsibleNavbar" aria-controls="collapsibleNavbar"> <Navbar.Toggle aria-controls="basic-navbar-nav" />
<span className="navbar-toggler-icon"></span> <Navbar.Collapse id="basic-navbar-nav">
</button> <Nav className="mr-auto">
<div className="collapse navbar-collapse justify-content-between" id="collapsibleNavbar"> <NavLink as={Link} to="/notice">공지사항</NavLink>
<ul className="navbar-nav"> <NavLink as={Link} to="/home">대관 현황</NavLink>
<li className="nav-item">
<Link to="/notice" className="nav-link">공지사항</Link> <NavLink as={Link} to={{
</li> pathname: `/apply/${localStorage.getItem('_id')}`,
<li className="nav-item"> state: { id: localStorage.getItem('_id') },
<Link to="/home" className="nav-link">대관 현황</Link> }} className="nav-link">대관 신청</NavLink>
</li>
<li className="nav-item"> <NavLink as={Link} to={{
<Link to={{ pathname: `/check/${localStorage.getItem('_id')}`,
pathname: `/apply/${localStorage.getItem('_id')}`, state: { id: localStorage.getItem('_id') },
state: { id: localStorage.getItem('_id') }, }} className="nav-link">
}} className="nav-link">대관 신청</Link> 대관 확인/취소</NavLink>
</li>
<li className="nav-item"> {user.role === "admin" ? (
<Link to={{ <NavLink as={Link} to={{
pathname: `/check/${localStorage.getItem('_id')}`,
state: { id: localStorage.getItem('_id') },
}} className="nav-link">
대관 확인/취소</Link>
</li>
<li className="nav-item">
<Link to={{
pathname: `/acheck/${localStorage.getItem('_id')}`, pathname: `/acheck/${localStorage.getItem('_id')}`,
state: { id: localStorage.getItem('_id') }, state: { id: localStorage.getItem('_id') },
}} className="nav-link"> }} className="nav-link">
대관 확인/취소(관리자)</Link> 대관 확인/취소(관리자)</NavLink>) : null}
</li> </Nav>
</ul> <Nav >
<div className="h-100 mr-3"> <NavLink>
<div className="text-white text-right font-weight-light"><small>{name} 안녕하세요</small></div> <small className="d-flex flex-row justify-content-end">
<div className="text-white text-right font-weight-light"><small> <div className="text-white text-right font-weight-light pr-2">{name}</div>
<Link to={{ <NavLink className="p-0" as={Link} to={{
pathname: `/change/${localStorage.getItem('_id')}`, pathname: `/change/${localStorage.getItem('_id')}`,
state: { id: localStorage.getItem('_id') }, state: { id: localStorage.getItem('_id') },
}}>비밀번호 변경</Link> / <span className="logoutBtn" onClick={logout} >로그아웃</span></small></div> }}> 비밀번호 변경 </NavLink> / <NavLink className="p-0" onClick={logout} > 로그아웃</NavLink></small>
</div> </NavLink>
</div> </Nav>
</Nav> </Navbar.Collapse>
</MENU >
) )
} }
......
...@@ -8,12 +8,12 @@ function ACheck(props) { ...@@ -8,12 +8,12 @@ function ACheck(props) {
const [state, setState] = useState() const [state, setState] = useState()
const [reserve, setReserve] = useState([]); const [reserve, setReserve] = useState([]);
useEffect(() => { useEffect(() => {
getReserve(); getReserve();
}, []) }, [])
function getReserve() { function getReserve() {
axios.get(`/users/admin/${props.match.params.id}`, { axios.get(`/users/admin/${props.match.params.id}`, {
headers: { authorization: localStorage.getItem('token') }, headers: { authorization: localStorage.getItem('token') },
}) })
.then(res => { .then(res => {
if (res.status === 404) { if (res.status === 404) {
...@@ -30,10 +30,19 @@ function ACheck(props) { ...@@ -30,10 +30,19 @@ function ACheck(props) {
if (state) return <Redirect to="/home" />; if (state) return <Redirect to="/home" />;
function remove(index) { function remove(index) {
axios.delete(`/reserves/${reserve[index]._id}`) // axios.delete(`/reserves/${reserve[index]._id}`)
// .then(res => {
// if (res.status === 404) return alert(res.data.error)
// alert("삭제되었습니다!");
// getReserve();
// })
// .catch(err => {
// alert(err.error)
// });
axios.put(`/reserves/${reserve[index]._id}`)
.then(res => { .then(res => {
if (res.status === 404) return alert(res.data.error) if (res.status === 404) return alert(res.data.error)
alert("삭제되었습니다!"); alert("승인을 거절했습니다!");
getReserve(); getReserve();
}) })
.catch(err => { .catch(err => {
...@@ -42,7 +51,9 @@ function ACheck(props) { ...@@ -42,7 +51,9 @@ function ACheck(props) {
}; };
function admit(index) { function admit(index) {
axios.put(`/reserves/${reserve[index]._id}`) axios.put(`/reserves/${reserve[index]._id}`, {
approve: true,
})
.then(res => { .then(res => {
if (res.status === 404) return alert(res.data.error) if (res.status === 404) return alert(res.data.error)
alert("승인되었습니다!"); alert("승인되었습니다!");
...@@ -69,25 +80,26 @@ function ACheck(props) { ...@@ -69,25 +80,26 @@ function ACheck(props) {
</tr> </tr>
</thead> </thead>
<tbody> <tbody>
{reserve.map((reserve, index) => { {reserve != "" ? (
return ( reserve.map((reserve, index) => {
<tr key={index}> return (
<td>{reserve.user.name}</td> <tr key={index}>
<td>{reserve.date}</td> <td>{reserve.user.name}</td>
<td>{reserve.time}</td> <td>{reserve.date}</td>
<td>{reserve.room}</td> <td>{reserve.starttime}~{(Number(reserve.starttime) + reserve.usetime)}</td>
<td>{reserve.num}</td> <td>{reserve.room}</td>
<td> <td>{reserve.num}</td>
<button onClick={() => admit(index)} className="btn btn-primary"> <td>
승인 <button onClick={() => admit(index)} className="btn btn-primary">
승인
</button> </button>
<button onClick={() => remove(index)} className="btn btn-danger"> <button onClick={() => remove(index)} className="btn btn-danger">
거절 거절
</button> </button>
</td> </td>
</tr> </tr>
) )
})} })) : <div>최근 대관 신청 내역이 없습니다.</div>}
</tbody> </tbody>
</table> </table>
...@@ -96,4 +108,4 @@ function ACheck(props) { ...@@ -96,4 +108,4 @@ function ACheck(props) {
) )
} }
export default ACheck export default ACheck
\ No newline at end of file
...@@ -22,27 +22,26 @@ function Apply(props) { ...@@ -22,27 +22,26 @@ function Apply(props) {
} }
function time(starttime) { function time(starttime) {
console.log(starttime) if (starttime == 21) {
if (starttime == 21) { return (<Field as="select" name="usetime">
return (<Field as="select" name="usetime"> <option value="">이용시간을 선택하세요</option>
<option value="">이용시간을 선택하세요</option> <option value="1">1시간</option>
<option value="1">1시간</option> </Field>)
</Field>) }
} if (starttime == 20) {
if (starttime == 20) {
return (<Field as="select" name="usetime">
<option value="">이용시간을 선택하세요</option>
<option value="1">1시간</option>
<option value="2">2시간</option>
</Field>)
}
return (<Field as="select" name="usetime"> return (<Field as="select" name="usetime">
<option value="">이용시간을 선택하세요</option> <option value="">이용시간을 선택하세요</option>
<option value="1">1시간</option> <option value="1">1시간</option>
<option value="2">2시간</option> <option value="2">2시간</option>
<option value="3">3시간</option>
</Field>) </Field>)
}
return (<Field as="select" name="usetime">
<option value="">이용시간을 선택하세요</option>
<option value="1">1시간</option>
<option value="2">2시간</option>
<option value="3">3시간</option>
</Field>)
} }
function getUser() { function getUser() {
...@@ -93,17 +92,21 @@ function Apply(props) { ...@@ -93,17 +92,21 @@ function Apply(props) {
url: '/reserves', url: '/reserves',
data: values data: values
}).then(res => { }).then(res => {
if (res.status === 404) return alert(res.data.error) if (res.status === 404) {
alert(res.data.error)
return window.location.reload();
}
alert("신청이 완료되었습니다!"); alert("신청이 완료되었습니다!");
setState(true); setState(true);
console.log("res.data", res.data)
}) })
.catch(err => { .catch(err => {
alert(err.error) alert(err.error)
}); });
// setTimeout(() => { setTimeout(() => {
// setSubmitting(false); setSubmitting(false);
// }, 400); // finish the cycle in handler }, 400); // finish the cycle in handler
}} }}
> >
{({ {({
...@@ -208,7 +211,6 @@ function Apply(props) { ...@@ -208,7 +211,6 @@ function Apply(props) {
> >
X X
</button> </button>
</div> </div>
</div> </div>
))} ))}
...@@ -234,4 +236,4 @@ function Apply(props) { ...@@ -234,4 +236,4 @@ function Apply(props) {
) )
} }
export default Apply export default Apply
\ No newline at end of file
...@@ -2,86 +2,106 @@ import React, { useState } from 'react'; ...@@ -2,86 +2,106 @@ import React, { useState } from 'react';
import { Formik } from 'formik'; import { Formik } from 'formik';
import * as Yup from 'yup'; import * as Yup from 'yup';
import axios from 'axios'; import axios from 'axios';
import 'bootstrap/dist/css/bootstrap.css'; import Menu from '../Components/Menu';
import { Link, Redirect } from 'react-router-dom'; import { Link, Redirect } from 'react-router-dom';
import { Container, Button, Col } from 'react-bootstrap';
import styled from 'styled-components';
const Check = styled.div`
& #reCheck::after {
content: '새로운 비밀번호를 다시 입력하세요';
}
& #reCheck:not(.right) {
content: '비밀번호가 일치하지 않습니다.';
color: red;
}
`
function Change(props) { function Change(props) {
const [state, setState] = useState(); const [state, setState] = useState();
const [checkPw, setCheckPw] = useState(true);
if (state) { if (state) {
return <Redirect to="/" />; return <Redirect to="/" />;
} }
console.log(props) // console.log(props)
return ( return (
<div className="d-flex flex-column justify-content-between vh-100"> <div className="">
<Formik <Menu />
initialValues={{ password: '' }} <Container fluid className="p-0 vh-90">
validationSchema={Yup.object({ <Check className="row justify-content-center m-0">
password: Yup.string() <Col md={4} className="pt-5">
.required('비밀번호를 입력해주세요.') <Formik
.min(8, '8자 이상 입력해주세요.'), initialValues={{ password: '' }}
password2: Yup.string() validationSchema={Yup.object({
.required('비밀번호를 다시 입력해주세요.') password: Yup.string()
.min(8, '8자 이상 입력해주세요.') .required('비밀번호를 입력해주세요.')
.oneOf([Yup.ref("password"), null], '비밀번호가 일치하지 않습니다.'), .min(8, '8자 이상 입력해주세요.'),
})} password2: Yup.string()
onSubmit={(values, { setSubmitting }) => { .required('비밀번호를 다시 입력해주세요.')
axios.put(`/users/change/${props.location.state.id}`, { ...values }, .min(8, '8자 이상 입력해주세요.')
) .oneOf([Yup.ref("password"), null], '비밀번호가 일치하지 않습니다.'),
.then(res => { })}
console.log(res.data); onSubmit={(values, { setSubmitting }) => {
if (res.status === 404) return alert(res.data.error) axios.put(`/users/change/${props.location.state.id}`, { ...values },
alert("회원정보가 수정되었습니다!") )
setState(true); .then(res => {
}) console.log(res.data);
.catch(err => { if (res.status === 404) return alert(res.data.error)
alert(err.error) alert("회원정보가 수정되었습니다!")
}); setState(true);
})
.catch(err => {
alert(err.error)
});
setTimeout(() => {
setSubmitting(false);
}, 400); // finish the cycle in handler
}}
>
{({
errors,
touched,
handleSubmit,
getFieldProps, // contain values, handleChange, handleBlur
isSubmitting,
}) => (
<form onSubmit={handleSubmit} className="d-flex flex-column">
<div className="form-group">
<div className={touched.password && errors.password ? "text-danger" : ""}> 비밀번호를 입력하세요(8자리 이상)</div>
<input
className={(touched.password && errors.password ? 'form-control is-invalid' : "form-control")}
type="password"
name="password"
{...getFieldProps('password')}
placeholder="새로운 비밀번호"
/>
</div>
<div className="form-group">
{touched.password2 && errors.password2 ? setCheckPw(false) : null}
<div id="reCheck" className={checkPw ? "right" : "err"}></div>
<input
className={(touched.password2 && errors.password2 ? 'form-control is-invalid' : "form-control")}
type="password"
name="password2"
{...getFieldProps('password2')}
placeholder="새 비밀번호를 다시 입력해주세요."
/>
</div>
<Button type="submit" variant="secondary" disabled={isSubmitting}>저장하기</Button>
</form>
)}
</Formik>
</Col>
</Check>
setTimeout(() => { </Container>
setSubmitting(false);
}, 400); // finish the cycle in handler
}}
>
{({
errors,
touched,
handleSubmit,
getFieldProps, // contain values, handleChange, handleBlur
isSubmitting,
}) => (
<div className="row justify-content-center align-items-center">
<form onSubmit={handleSubmit} className="col-sm-3">
<div className="form-group mb-4">
<input
className={(touched.password && errors.password ? 'form-control is-invalid' : "form-control")}
type="password"
name="password"
{...getFieldProps('password')}
placeholder="새 비밀번호를 입력해주세요."
/>
{touched.password && errors.password ? (
<div className="invalid-feedback text-left">{errors.password}</ div>
) : null}
</div>
<div className="form-group mb-4">
<input
className={(touched.password2 && errors.password2 ? 'form-control is-invalid' : "form-control")}
type="password"
name="password2"
{...getFieldProps('password2')}
placeholder="새 비밀번호를 다시 입력해주세요."
/>
{touched.password2 && errors.password2 ? (
<div className="invalid-feedback text-left">{errors.password2}</div>
) : null}
</div>
<button type="submit" className="btn btn-light" disabled={isSubmitting}>저장</button>
</form>
</div>
)}
</Formik>
</div > </div >
); );
} }
......
...@@ -59,7 +59,7 @@ function Check(props) { ...@@ -59,7 +59,7 @@ function Check(props) {
<td>{reserve.starttime}~{(Number(reserve.starttime) + reserve.usetime)}</td> <td>{reserve.starttime}~{(Number(reserve.starttime) + reserve.usetime)}</td>
<td>{reserve.room}</td> <td>{reserve.room}</td>
<td>{reserve.num}</td> <td>{reserve.num}</td>
<td>{reserve.approve ? "승인" : "미승인"}</td> <td>{reserve.check ? (reserve.approve ? "사용가능" : "사용불가") : "승인대기중"}</td>
<td> <td>
<button onClick={() => remove(index)} className="btn btn-danger"> <button onClick={() => remove(index)} className="btn btn-danger">
취소 취소
......
...@@ -2,11 +2,20 @@ import React, { useState } from 'react'; ...@@ -2,11 +2,20 @@ import React, { useState } from 'react';
import { Field, Formik } from 'formik'; import { Field, Formik } from 'formik';
import * as Yup from 'yup'; import * as Yup from 'yup';
import axios from 'axios'; import axios from 'axios';
import 'bootstrap/dist/css/bootstrap.css';
import { Link, Redirect } from 'react-router-dom'; import { Link, Redirect } from 'react-router-dom';
import styled from 'styled-components';
import { Navbar, Container, Row, Col, Button } from 'react-bootstrap';
const Menu = styled(Navbar)`
background-color: #7B031D;
a {
color : white;
}
`
function Find() { function Find() {
const [state, setState] = useState(); const [state, setState] = useState(false);
if (state) { if (state) {
return <Redirect to={{ return <Redirect to={{
...@@ -14,88 +23,90 @@ function Find() { ...@@ -14,88 +23,90 @@ function Find() {
state: { id: localStorage.getItem('_id') }, state: { id: localStorage.getItem('_id') },
}} />; }} />;
} }
return ( return (
<div className="d-flex flex-column justify-content-between vh-100"> <div className="vh-100">
<Formik <Menu expand="md" variant="dark">
initialValues={{ id: '', question: '', answer: '' }} <Navbar.Brand>비밀번호 찾기</Navbar.Brand>
validationSchema={Yup.object({ </Menu>
id: Yup.string() <Container fluid>
.required('학번을 입력해주세요.'), <Row className="justify-content-center">
answer: Yup.string() <Col md={3} xs={11} className="p-0">
.required('답변을 입력해주세요.'), <Formik
})} initialValues={{ id: '', question: '', answer: '' }}
onSubmit={(values, { setSubmitting }) => { validationSchema={Yup.object({
axios({ id: Yup.string()
method: 'post', .required('학번을 입력해주세요.'),
url: '/login/find', answer: Yup.string()
data: values, .required('답변을 입력해주세요.'),
}).then(res => { })}
if (res.status === 404) return alert(res.data.error) onSubmit={(values, { setSubmitting }) => {
localStorage.setItem('_id', res.data.users._id) axios({
setState(true); method: 'post',
}) url: '/login/find',
.catch(err => { data: values,
alert(err.error) }).then(res => {
}); if (res.status === 404) return alert(res.data.error)
localStorage.setItem('_id', res.data.users._id)
setState(true);
})
.catch(err => {
alert(err.error)
});
console.log(values);
setTimeout(() => {
setSubmitting(false);
}, 400); // finish the cycle in handler
}}
>
{({
errors,
touched,
handleSubmit,
getFieldProps, // contain values, handleChange, handleBlur
isSubmitting,
}) => (
<form onSubmit={handleSubmit} className="d-flex flex-column pt-5">
<div className="form-group pb-2">
<div className={touched.id && errors.id ? "text-danger" : ""}>학번을 입력하세요</div>
<input
className={(touched.id && errors.id ? 'form-control is-invalid' : "form-control")}
type="number"
name="id"
{...getFieldProps('id')}
placeholder="Input Student Id"
/>
</div>
<div className="form-group pb-2">
<label className="pr-2">본인 확인 질문</label>
<Field as="select" name="question">
<option value="">질문을 선택하세요</option>
<option value="life">자신의 인생 좌우명은?</option>
<option value="school">자신이 다녔던 초등학교의 이름은?</option>
<option value="place">기억에 남는 추억의 장소는?</option>
</Field>
</div>
<div className="form-group pb-2">
<div className={touched.answer && errors.answer ? "text-danger" : ""}>답변을 입력해주세요.</div>
<input
className={(touched.answer && errors.answer ? 'form-control is-invalid' : "form-control")}
type="text"
name="answer"
{...getFieldProps('answer')}
placeholder="Input answer" />
</div>
console.log(values); <Button className="mb-2" variant="secondary" type="submit" disabled={isSubmitting}>비밀번호 찾기</Button>
setTimeout(() => { <Button variant="outline-secondary" as={Link} to="/login">로그인하러 가기</Button>
setSubmitting(false); </form>
}, 400); // finish the cycle in handler )}
}} </Formik>
> </Col>
{({ </Row>
errors, </Container >
touched, </div >
handleSubmit,
getFieldProps, // contain values, handleChange, handleBlur
isSubmitting,
}) => (
<div className="row justify-content-center align-items-center">
<form onSubmit={handleSubmit} className="col-sm-3">
<div className="form-group mb-4">
<input
className={(touched.id && errors.id ? 'form-control is-invalid' : "form-control")}
type="number"
name="id"
{...getFieldProps('id')}
placeholder="Input Student Id"
/>
{touched.id && errors.id ? (
<div className="invalid-feedback text-left">{errors.id}</div>
) : null}
</div>
<div className="form-group mb-4">
<label>본인 확인 질문</label>
<Field as="select" name="question">
<option value="">질문을 선택하세요</option>
<option value="life">자신의 인생 좌우명은?</option>
<option value="school">자신이 다녔던 초등학교의 이름은?</option>
<option value="place">기억에 남는 추억의 장소는?</option>
</Field>
</div>
<div className="form-group mb-4">
<input
className={(touched.answer && errors.answer ? 'form-control is-invalid' : "form-control")}
type="text"
name="answer"
{...getFieldProps('answer')}
placeholder="Input answer" />
{touched.answer && errors.answer ? (
<div className="invalid-feedback text-left">{errors.answer}</div>
) : null}
</div>
<button type="submit" className="btn btn-dark" disabled={isSubmitting}>
submit
</button>
<button><Link to="/login">로그인</Link></button>
<button><Link to="/"></Link></button>
</form>
</div>
)}
</Formik>
</div>
); );
} }
......
...@@ -4,10 +4,10 @@ import { Link, Redirect } from 'react-router-dom'; ...@@ -4,10 +4,10 @@ import { Link, Redirect } from 'react-router-dom';
import { Formik } from 'formik'; import { Formik } from 'formik';
import * as Yup from 'yup'; import * as Yup from 'yup';
import axios from 'axios'; import axios from 'axios';
import 'bootstrap/dist/css/bootstrap.css';
import Logo from '../icon.png'; import Logo from '../icon.png';
import { Container, Row, Button } from 'react-bootstrap';
const Asd = styled.div` const Col_1 = styled.div`
background-color: #7B031D; background-color: #7B031D;
&.web { &.web {
...@@ -35,13 +35,14 @@ const Asd = styled.div` ...@@ -35,13 +35,14 @@ const Asd = styled.div`
} }
` `
const Asdf = styled.div` const Col_2 = styled.div`
background-color: rgb(239, 218, 200); background-color: rgb(239, 218, 200);
a { a {
color : #7B031D; color : #7B031D;
} }
&.mob-formik { & .mob-formik {
height : 80vh; height : 80vh;
width: 100%; width: 100%;
display: flex; display: flex;
...@@ -49,42 +50,40 @@ const Asdf = styled.div` ...@@ -49,42 +50,40 @@ const Asdf = styled.div`
align-items: center; align-items: center;
} }
&.web-formik { & .web-form {
height: 100%; height: 100%;
display: flex; display: flex;
align-items: center; align-items: center;
justify-content: center; justify-content: center;
} }
& .mobb { & .mob-container {
height: 35vh;
display: flex; display: flex;
flex-direction: column; flex-direction: column;
justify-content: space-around;
} }
& .webb { & .webb {
flex-direction: column; flex-direction: column;
} }
& .qwer { & .web-container {
display: flex; display: flex;
justify-content: space-between;
height: 12vh; height: 12vh;
width: 30vw; width: 30vw;
margin-bottom: 25px;
} }
& .web-input-form { & .web-input-form {
width: 80%; width: 80%;
justify-content: space-between;
align-content: space-around;
flex-direction: column;
display: flex; display: flex;
flex-direction: column;
justify-content: space-around;
} }
& .mob-input-form { & .mob-input-form {
display: flex;
flex-direction: column;
justify-content: space-around;
} }
` `
...@@ -104,88 +103,92 @@ function Login() { ...@@ -104,88 +103,92 @@ function Login() {
return <Redirect to="/home" />; return <Redirect to="/home" />;
} }
return ( return (
<div className="row vw-100 vh-100 m-0"> <Container fluid className="p-0">
<Asd className={"col-md-4 col-12" + (mobile ? " mobile" : " web")}> <Row className="vw-100 vh-100 m-0 " >
<div className={mobile ? "mob-head" : ""}> <Col_1 className={"col-md-4 col-12" + (mobile ? " mobile" : " web")}>
<img className={mobile ? "mob-img" : "img-fluid"} src={Logo} /> <div className={mobile ? "mob-head" : ""}>
<div className={"d-flex " + (mobile ? "align-items-center" : "justify-content-center")}> <img className={mobile ? "mob-img" : "img-fluid"} src={Logo} />
<h1 className="font-weight-bold text-white text-center">고려대학교<br/>대관 서비스</h1> <div className={"d-flex " + (mobile ? "align-items-center" : "justify-content-center")}>
<h1 className="font-weight-bold text-white text-center">고려대학교<br />대관 서비스</h1>
</div>
</div> </div>
</div> </Col_1>
</Asd> <Col_2 className="col-md-8 col-12" >
<Asdf className={"col-md-8 col-12" + (mobile ? " mob-formik p-0" : " web-formik")}> <Formik
<Formik initialValues={{ id: '', password: '' }}
initialValues={{ id: '', password: '' }} validationSchema={Yup.object({
validationSchema={Yup.object({ id: Yup.string()
id: Yup.string() .required('학번을 입력해주세요.'),
.required('학번을 입력해주세요.'), password: Yup.string()
password: Yup.string() .required('비밀번호를 입력해주세요.')
.required('비밀번호를 입력해주세요.') .min(8, '8자 이상 입력해주세요.'),
.min(8, '8자 이상 입력해주세요.'), })}
})} onSubmit={(values, { setSubmitting }) => {
onSubmit={(values, { setSubmitting }) => { axios({
axios({ method: 'post',
method: 'post', url: '/login',
url: '/login', data: values,
data: values, }).then(res => {
}).then(res => { if (res.status === 404) return alert(res.data.error)
if (res.status === 404) return alert(res.data.error)
localStorage.setItem('token', res.data.token);
localStorage.setItem('token', res.data.token); localStorage.setItem('_id', res.data.users._id);
localStorage.setItem('_id', res.data.users._id); localStorage.setItem('name', res.data.users.name);
localStorage.setItem('name', res.data.users.name); setState(true);
setState(true); })
}) .catch(err => {
.catch(err => { alert(err.error)
alert(err.error) });
});
setTimeout(() => {
setTimeout(() => { setSubmitting(false);
setSubmitting(false); }, 400); // finish the cycle in handler
}, 400); // finish the cycle in handler }}
}} >
> {({
{({ errors,
errors, touched,
touched, handleSubmit,
handleSubmit, getFieldProps, // contain values, handleChange, handleBlur
getFieldProps, // contain values, handleChange, handleBlur isSubmitting,
isSubmitting, }) => (
}) => ( <div className={mobile ? " mob-formik p-0" : " web-form"}>
<form onSubmit={handleSubmit} className={mobile ? "w-75 h-50vh" : "d-flex webb"}> <form onSubmit={handleSubmit} className={mobile ? "w-75" : "d-flex webb"}>
<div className={mobile ? "mobb" : "qwer"}> <div className={mobile ? "mob-container" : "web-container"}>
<div className={(mobile ? "mob-" : "web-") + "input-form"}> <div className={mobile ? "mob-input-form" : "web-input-form mr-2"}>
<div className={"form-group m-0" + (mobile ? " mb-2" : "")}> <div className={"form-group m-0" + (mobile ? " mb-2" : " ")}>
<input <input
className={(touched.id && errors.id ? 'form-control is-invalid' : "form-control")} className={(touched.id && errors.id ? 'form-control is-invalid' : "form-control")}
type="number" type="number"
name="id" name="id"
{...getFieldProps('id')} {...getFieldProps('id')}
placeholder="Input Student Id" placeholder="Input Student Id"
/> />
</div>
<div className={"form-group m-0"+ (mobile ? " mb-2" : " ")}>
<input
className={(touched.password && errors.password ? 'form-control is-invalid' : "form-control")}
type="password"
name="password"
{...getFieldProps('password')}
placeholder="Input Password"
/>
</div>
</div>
<Button type="submit" variant="dark" className={mobile ? " w-100" : " w-20"} disabled={isSubmitting}> Login </Button>
</div> </div>
<div className="form-group m-0">
<input
className={(touched.password && errors.password ? 'form-control is-invalid' : "form-control")}
type="password"
name="password"
{...getFieldProps('password')}
placeholder="Input Password"
/>
</div>
</div>
<button type="submit" className={"btn btn-dark" + (mobile ? " w-100" : " w-20")} disabled={isSubmitting}> Login </button>
</div>
<div><Link to="/find">비밀번호를 잊으셨나요?</Link></div> <div><Link to="/find">비밀번호를 잊으셨나요?</Link></div>
<div><Link to="/signup">회원이 아니신가요?</Link></div> <div><Link to="/signup">회원이 아니신가요?</Link></div>
</form> </form>
)} </div>
)}
</Formik>
</Col_2>
</Row>
</Container>
</Formik>
</Asdf>
</div >
) )
} }
......
import React, { useState, useEffect, useRef } from 'react'; import React, { useState, useEffect, useRef } from 'react';
import Menu from '../Components/Menu'; import Menu from '../Components/Menu';
import axios from 'axios'; import axios from 'axios';
import styled from 'styled-components'; import { Link } from 'react-router-dom';
import { Container, Row, Col, Card, Navbar, Accordion, Button } from 'react-bootstrap';
function Notice() { function Notice() {
const [notices, setNotices] = useState([]); const [notices, setNotices] = useState([]);
...@@ -27,9 +28,8 @@ function Notice() { ...@@ -27,9 +28,8 @@ function Notice() {
axios.get(`/notices`) axios.get(`/notices`)
.then(res => { .then(res => {
if (res.status !== 201) { if (res.status !== 201) {
alert(res.data.error); // alert(res.data.error);
} }
console.log(res.data);
setNotices(res.data); setNotices(res.data);
}) })
.catch(err => { .catch(err => {
...@@ -38,33 +38,31 @@ function Notice() { ...@@ -38,33 +38,31 @@ function Notice() {
} }
return ( return (
<div> <div>
<Menu /> {(localStorage.getItem("token") !== null) ? (
<div className="container-fluid"> <Menu />
<div className="row justify-content-center vw-100 vh-90"> ) : (
<div className="col-md-7 col-12"> <Menu expand="md" variant="dark">
<Navbar.Brand>회원가입</Navbar.Brand>
<h2 className="p-3 border-bottom">공지사항</h2> </Menu>
)}
<div id="accordion w-90 pt-1"> <Container fluid>
<Row className="justify-content-center vw-100 vh-90">
<Col md={7}>
<h2 className="p-3 border-bottom">공지사항 <Link to="/write"> 작성</Link></h2>
<Accordion>
{notices.map((notice, index) => {notices.map((notice, index) =>
<div className="card"> <Card>
<div className="card-header collapsed card-link w-100 row m-0 p-1" id={"Hnotice_" + index} data-toggle="collapse" href={"#notice_" + index}> <Card.Header>
<div> <Accordion.Toggle as={Button} variant="link" eventKey={index + 1}>{notice.notice_title} <span className="text-right">{dateForm(notice.post_date)}</span></Accordion.Toggle>
<div className="col-6 p-0">{notice.notice_title}</div> </Card.Header>
<div className="col-3 p-0 text-center">{notice.notice_author}</div> <Accordion.Collapse eventKey={index + 1}>
<div className="col-3 p-0 text-right">{dateForm(notice.post_date)}</div> <Card.Body>{notice.notice_content}</Card.Body>
</div> </Accordion.Collapse>
</div> </Card>)}
<div id={"notice_" + index} aria-labelledby={"Hnotice_" + index} className="collapse" data-parent="#accordion"> </Accordion>
<div className="card-body">{notice.notice_content}</div> </Col>
</div> </Row>
</div> </Container>
)}
</div>
</div>
</div >
</div >
</div> </div>
) )
} }
......
...@@ -2,16 +2,15 @@ import React, { useState } from 'react'; ...@@ -2,16 +2,15 @@ import React, { useState } from 'react';
import { Field, Formik } from 'formik'; import { Field, Formik } from 'formik';
import * as Yup from 'yup'; import * as Yup from 'yup';
import axios from 'axios'; import axios from 'axios';
import 'bootstrap/dist/css/bootstrap.css';
import { Link, Redirect } from 'react-router-dom'; import { Link, Redirect } from 'react-router-dom';
import styled from 'styled-components'; import styled from 'styled-components';
import { Col, Container, Navbar, Button } from 'react-bootstrap';
const Nav = styled.nav` const Menu = styled(Navbar)`
background-color: #7B031D; background-color: #7B031D;
height: 10vh;
a { a {
color: #ffffff; color : white;
} }
` `
...@@ -23,7 +22,7 @@ const Wow = styled.div` ...@@ -23,7 +22,7 @@ const Wow = styled.div`
} }
& #reCheck:not(.right) { & #reCheck:not(.right) {
content: '비밀번호가 다릅니다.'; content: '비밀번호가 일치하지 않습니다.';
color: red; color: red;
} }
...@@ -40,15 +39,14 @@ function Signup() { ...@@ -40,15 +39,14 @@ function Signup() {
if (state) { if (state) {
return <Redirect to="/login" />; return <Redirect to="/login" />;
} }
return ( return (
<div className="vh-100"> <div className="vh-100">
<Nav className="navbar sticky-top navbar-expand-md"> <Menu expand="md" variant="dark">
<a class="navbar-brand" href="#">회원가입</a> <Navbar.Brand>회원가입</Navbar.Brand>
</Nav> </Menu>
<div className="container-fluid"> <Container fluid>
<Wow className="row justify-content-center rrooww"> <Wow className="row justify-content-center">
<div className="col-md-4 col-12 d-flex align-items-center h-100"> <Col md={3} xs={11} className="p-0">
<Formik <Formik
initialValues={{ name: '', id: '', password: '', password2: '', question: '', answer: '' }} initialValues={{ name: '', id: '', password: '', password2: '', question: '', answer: '' }}
validationSchema={Yup.object({ validationSchema={Yup.object({
...@@ -94,10 +92,7 @@ function Signup() { ...@@ -94,10 +92,7 @@ function Signup() {
isSubmitting, isSubmitting,
}) => ( }) => (
< form onSubmit={handleSubmit} className="asd"> < form onSubmit={handleSubmit} className="asd">
{/* col-sm-3 */}
<div className="form-group "> <div className="form-group ">
{/* mb-4 */}
<div className={touched.name && errors.name ? "text-danger" : ""}>이름을 입력하세요</div> <div className={touched.name && errors.name ? "text-danger" : ""}>이름을 입력하세요</div>
<input <input
className={(touched.name && errors.name ? 'form-control is-invalid' : "form-control")} className={(touched.name && errors.name ? 'form-control is-invalid' : "form-control")}
...@@ -106,10 +101,9 @@ function Signup() { ...@@ -106,10 +101,9 @@ function Signup() {
{...getFieldProps('name')} {...getFieldProps('name')}
placeholder="이름" /> placeholder="이름" />
</div> </div>
<div className="form-group"> <div className="form-group">
{/* mb-4 */}
<div className={touched.id && errors.id ? "text-danger" : ""}>학번을 입력하세요</div> <div className={touched.id && errors.id ? "text-danger" : ""}>학번을 입력하세요</div>
<input <input
className={(touched.id && errors.id ? 'form-control is-invalid' : "form-control")} className={(touched.id && errors.id ? 'form-control is-invalid' : "form-control")}
type="text" type="text"
...@@ -117,14 +111,10 @@ function Signup() { ...@@ -117,14 +111,10 @@ function Signup() {
{...getFieldProps('id')} {...getFieldProps('id')}
placeholder="학번/교번" placeholder="학번/교번"
/> />
{/* {touched.id && errors.id ? (
<div className="invalid-feedback text-left">{errors.id}</div>
) : null} */}
</div> </div>
<div className="form-group"> <div className="form-group">
{/* mb-4 */}
<div className={touched.password && errors.password ? "text-danger" : ""}>비밀번호를 입력하세요(8자리 이상)</div> <div className={touched.password && errors.password ? "text-danger" : ""}>비밀번호를 입력하세요(8자리 이상)</div>
<input <input
className={(touched.password && errors.password ? 'form-control is-invalid' : "form-control")} className={(touched.password && errors.password ? 'form-control is-invalid' : "form-control")}
type="password" type="password"
...@@ -132,12 +122,9 @@ function Signup() { ...@@ -132,12 +122,9 @@ function Signup() {
{...getFieldProps('password')} {...getFieldProps('password')}
placeholder="비밀번호" placeholder="비밀번호"
/> />
{/* {touched.password && errors.password ? (
<div className="invalid-feedback text-left">{errors.password}</div>
) : null} */}
</div> </div>
<div className="form-group"> <div className="form-group">
{/* mb-4 */}
{touched.password2 && errors.password2 ? setCheckPw(false) : null} {touched.password2 && errors.password2 ? setCheckPw(false) : null}
<div id="reCheck" className={checkPw ? "right" : "err"}></div> <div id="reCheck" className={checkPw ? "right" : "err"}></div>
<input <input
...@@ -147,10 +134,9 @@ function Signup() { ...@@ -147,10 +134,9 @@ function Signup() {
{...getFieldProps('password2')} {...getFieldProps('password2')}
placeholder="비밀번호 확인" placeholder="비밀번호 확인"
/> />
</div> </div>
<div className="form-group"> <div className="form-group">
{/* mb-4 */}
<label>본인 확인 질문</label> <label>본인 확인 질문</label>
<Field as="select" name="question"> <Field as="select" name="question">
<option value="">질문을 선택하세요</option> <option value="">질문을 선택하세요</option>
...@@ -160,9 +146,7 @@ function Signup() { ...@@ -160,9 +146,7 @@ function Signup() {
</Field> </Field>
</div> </div>
<div className="form-group"> <div className="form-group">
{/* mb-4 */}
<div className={touched.answer && errors.answer ? "text-danger" : ""}>답변을 입력해주세요.</div> <div className={touched.answer && errors.answer ? "text-danger" : ""}>답변을 입력해주세요.</div>
<input <input
className={(touched.answer && errors.answer ? 'form-control is-invalid' : "form-control")} className={(touched.answer && errors.answer ? 'form-control is-invalid' : "form-control")}
type="text" type="text"
...@@ -170,19 +154,17 @@ function Signup() { ...@@ -170,19 +154,17 @@ function Signup() {
{...getFieldProps('answer')} {...getFieldProps('answer')}
placeholder="Input answer" /> placeholder="Input answer" />
</div> </div>
<button type="submit" className="btn btn-dark" disabled={isSubmitting}>회원가입</button> <Button type="submit" variant="secondary" disabled={isSubmitting}>회원가입</Button>
<button class="btn btn-light"><Link to="/login">로그인</Link></button> <Button variant="outline-secondary" as={Link} to="/login">로그인하러 가기</Button>
<button class="btn btn-light"><Link to="/"></Link></button>
</form> </form>
)} )}
</Formik> </Formik>
</div> </Col>
</Wow> </Wow>
</div> </Container>
</div > </div >
); );
} }
export default Signup; export default Signup;
\ No newline at end of file
import React, { useState, useEffect } from 'react';
import { Link, Redirect } from 'react-router-dom';
import Menu from '../Components/Menu';
import * as Yup from 'yup';
import axios from 'axios';
import { Container, Row, Col } from 'react-bootstrap';
import { Field, Formik } from 'formik';
function Write() {
const [submitData, setSubmitData] = useState(false);
const [state, setState] = useState(false);
if (state) {
return <Redirect to="/notice" />;
}
return (
<div>
<Menu />
<Container fluid>
<Row className="justify-content-center">
<Col md={12} xl={8} style={{ height: "35em" }}>
<Formik
initialValues={{ title: '', content: '' }}
validationSchema={Yup.object({
title: Yup.string()
.required('제목을 입력해주세요.'),
content: Yup.string()
.required('내용을 입력해주세요.'),
})}
onSubmit={(values, { setSubmitting }) => {
axios({
method: 'post',
url: '/writes',
data: values,
}).then(res => {
if (res.status === 404) return alert(res.data.error)
alert("공지 등록이 완료되었습니다.")
setState(true);
})
.catch(err => {
alert(err.error)
});
setTimeout(() => {
setSubmitting(false);
}, 400); // finish the cycle in handler
}}
>{({
errors,
touched,
handleSubmit,
getFieldProps, // contain values, handleChange, handleBlur
isSubmitting,
}) => (
<form onSubmit={handleSubmit} className="asd">
{/* col-sm-3 */}
<div className="form-group">
{/* mb-4 */}
<div className={touched.name && errors.name ? "text-danger" : ""}>제목</div>
<input className={(touched.name && errors.name ? 'form-control is-invalid' : "form-control")}
type="text"
title="title"
{...getFieldProps('title')}
placeholder="제목" />
</div>
<div className="form-group ">
{/* mb-4 */}
<div className={touched.name && errors.name ? "text-danger" : ""}>내용</div>
<input className={(touched.name && errors.name ? 'form-control is-invalid' : "form-control")}
type="text"
content="content"
{...getFieldProps('content')}
placeholder="내용" />
</div>
<button type="submit" className="btn btn-dark" disabled={isSubmitting}>공지 등록</button>
</form>
)}
</Formik>
</Col>
</Row>
</Container>
</div>
)
}
export default Write
...@@ -16,13 +16,14 @@ import Apply from './Pages/ApplyPage'; ...@@ -16,13 +16,14 @@ import Apply from './Pages/ApplyPage';
import Check from './Pages/CheckPage'; import Check from './Pages/CheckPage';
import Notice from './Pages/NoticePage'; import Notice from './Pages/NoticePage';
import ACheck from './Pages/ACheckPage'; import ACheck from './Pages/ACheckPage';
import Write from './Pages/WritePage';
axios.defaults.validateStatus = function (status) { axios.defaults.validateStatus = function (status) {
return status < 500; // default return status < 500; // default
} }
ReactDOM.render( ReactDOM.render(
<Router> <Router>
<Switch> <Switch>
<PrivateRoute exact path="/" component={Home} /> <PrivateRoute exact path="/" component={Home} />
<Route path="/login" component={Login} /> <Route path="/login" component={Login} />
...@@ -32,11 +33,12 @@ ReactDOM.render( ...@@ -32,11 +33,12 @@ ReactDOM.render(
<Route path="/change" component={Change} /> <Route path="/change" component={Change} />
<Route path="/apply/:id" component={Apply} /> <Route path="/apply/:id" component={Apply} />
<Route path="/check/:id" component={Check} /> <Route path="/check/:id" component={Check} />
<Route path="/write" component={Write} />
<Route path="/notice" component={Notice} /> <Route path="/notice" component={Notice} />
<Route path="/acheck/:id" component={ACheck} /> <Route path="/acheck/:id" component={ACheck} />
<Redirect path="/" to="/" />
<Redirect path="/home" to="/" /> <Redirect path="/home" to="/" />
<Redirect path="/change/:id" to="/change"/> <Redirect path="/change/:id" to="/change" />
<Redirect path="/notice" to="/notice" />
</Switch> </Switch>
</Router>, </Router>,
document.getElementById('root') document.getElementById('root')
......
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