Skip to content

Commit f3f79ed

Browse files
su-bin99rdd9223
authored andcommitted
Refactor: login페이지 nextjs로 이동
1 parent c2687e8 commit f3f79ed

6 files changed

Lines changed: 242 additions & 0 deletions

File tree

Lines changed: 45 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,45 @@
1+
import { StyledInput } from 'components/atoms';
2+
import React from 'react';
3+
import { Form, LoginformWrap } from './style';
4+
5+
interface IProps {
6+
idInputChange: (value: string) => void;
7+
pwdInputChange: (value: string) => void;
8+
isConditionMet: {
9+
email: boolean;
10+
pwd: boolean;
11+
};
12+
}
13+
const errMsg = {
14+
email: '가입되지 않은 이메일입니다',
15+
pwd: '비밀번호를 다시 확인해 주세요',
16+
};
17+
18+
function LoginForm({ idInputChange, isConditionMet, pwdInputChange }: IProps): React.ReactElement {
19+
return (
20+
<LoginformWrap>
21+
<Form>
22+
<StyledInput
23+
placeHolder="이메일을 입력해 주세요"
24+
width="406px"
25+
height="60px"
26+
margin="0 0 9px 0"
27+
onChange={idInputChange}
28+
isConditionMet={isConditionMet.email}
29+
errorMsg={errMsg.email}
30+
/>
31+
<StyledInput
32+
placeHolder="비밀번호를 입력해 주세요"
33+
width="406px"
34+
height="60px"
35+
isPw={true}
36+
onChange={pwdInputChange}
37+
isConditionMet={isConditionMet.pwd}
38+
errorMsg={errMsg.pwd}
39+
/>
40+
</Form>
41+
</LoginformWrap>
42+
);
43+
}
44+
45+
export default LoginForm;
Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
import Styled from 'styled-components';
2+
3+
export const LoginformWrap = Styled.div`
4+
display : flex;
5+
flex-direction : column;
6+
align-items : center;
7+
`;
8+
9+
export const Form = Styled.form`
10+
width : 100%;
11+
`;

components/organisms/index.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,7 @@ export { default as Header } from './Header';
1616
export { default as InterestModal } from './InterestModal';
1717
export { default as JoinCheck } from './JoinCheck';
1818
export { default as JoinForm } from './JoinForm';
19+
export { default as LoginForm } from './LoginForm';
1920
export { default as MyCommentList } from './MyCommentList';
2021
export { default as MyPageCommentModal } from './MyPageCommentModal';
2122
export { default as MyPageHeader } from './MyPageHeader';

pages/login/index.tsx

Lines changed: 88 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,88 @@
1+
import { getUserData, postLogin } from 'apis';
2+
import { useRouter } from 'next/router';
3+
import React, { useEffect, useState } from 'react';
4+
import { useRecoilState } from 'recoil';
5+
import { userState, userStatusState } from 'stores/user';
6+
import LoginTemplate from './template';
7+
8+
function Login(): React.ReactElement {
9+
const history = useRouter();
10+
11+
const [loginData, setLoginData] = useState({
12+
// 값 저장
13+
email: '',
14+
password: '',
15+
});
16+
const [userStatusData, setUserStatusData] = useRecoilState(userStatusState);
17+
const [userData, setUserData] = useRecoilState(userState);
18+
const [isConditionMet, setIsConditionMet] = useState({
19+
email: true,
20+
pwd: true,
21+
});
22+
23+
const idInputChange = (value: string) => {
24+
if (typeof value === 'string') setLoginData({ ...loginData, email: value });
25+
};
26+
const pwdInputChange = (value: string) => {
27+
if (typeof value === 'string') setLoginData({ ...loginData, password: value });
28+
};
29+
const handleLoginBtn = async () => {
30+
const token = await getUserStatusData();
31+
const isSuccess = await getUserDetailData(token);
32+
isSuccess && history.push('/');
33+
};
34+
const getUserStatusData = async () => {
35+
const data = await postLogin(loginData);
36+
if (data) {
37+
if (data.status === 200) {
38+
setUserStatusData({
39+
token: data.token,
40+
userType: data.data.userState,
41+
totalGeneration: data.data.totalGeneration,
42+
registGeneration: data.data.registGeneration,
43+
progressGeneration: data.data.progressGeneration ? data.data.progressGeneration : 0,
44+
});
45+
return data.token;
46+
} else {
47+
if (data.message === '아이디가 존재하지 않습니다') {
48+
setIsConditionMet({ email: false, pwd: true });
49+
} else if (data.message === '비밀번호가 틀렸습니다') {
50+
setIsConditionMet({ email: true, pwd: false });
51+
}
52+
}
53+
} else {
54+
alert('네트워크가 좋지 않습니다');
55+
}
56+
return '';
57+
};
58+
const getUserDetailData = async (token: string): Promise<boolean> => {
59+
if (token) {
60+
const data = await getUserData(token);
61+
if (data !== undefined) {
62+
setUserData(data);
63+
return true;
64+
} else {
65+
alert('네트워크가 좋지 않습니다');
66+
}
67+
}
68+
return false;
69+
};
70+
71+
useEffect(() => {
72+
if (userStatusData && userData) {
73+
alert('이미 로그인이 되어있습니다. ');
74+
history.push('/');
75+
}
76+
}, []);
77+
78+
return (
79+
<LoginTemplate
80+
handleLoginBtn={handleLoginBtn}
81+
idInputChange={idInputChange}
82+
pwdInputChange={pwdInputChange}
83+
isConditionMet={isConditionMet}
84+
/>
85+
);
86+
}
87+
88+
export default Login;

pages/login/template/index.tsx

Lines changed: 36 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,36 @@
1+
import { LineIcon } from 'public/assets/images';
2+
import { Link } from 'components/atoms';
3+
import { LoginForm } from 'components/organisms';
4+
import React from 'react';
5+
import { ButtonWrapper, FindPwdBtn, JoinBtn, Line, LoginBtn, LoginContainer, LoginLabel } from './style';
6+
7+
interface IProps {
8+
handleLoginBtn: () => Promise<void>;
9+
idInputChange: (value: string) => void;
10+
pwdInputChange: (value: string) => void;
11+
isConditionMet: {
12+
email: boolean;
13+
pwd: boolean;
14+
};
15+
}
16+
17+
function LoginTemplate({ handleLoginBtn, idInputChange, pwdInputChange, isConditionMet }: IProps): React.ReactElement {
18+
return (
19+
<LoginContainer>
20+
<LoginLabel>로그인</LoginLabel>
21+
<LoginForm idInputChange={idInputChange} pwdInputChange={pwdInputChange} isConditionMet={isConditionMet} />
22+
<LoginBtn onClick={handleLoginBtn}>로그인</LoginBtn>
23+
<ButtonWrapper>
24+
<Link to="/setting/password/find">
25+
<FindPwdBtn>비밀번호 찾기</FindPwdBtn>
26+
</Link>
27+
<Line src={LineIcon}></Line>
28+
<Link to="/join">
29+
<JoinBtn>회원가입</JoinBtn>
30+
</Link>
31+
</ButtonWrapper>
32+
</LoginContainer>
33+
);
34+
}
35+
36+
export default LoginTemplate;

pages/login/template/style.ts

Lines changed: 61 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,61 @@
1+
import { Button, Img, Label } from 'components/atoms';
2+
import Styled from 'styled-components';
3+
import { palette } from 'styled-tools';
4+
5+
export const Line = Styled(Img)`
6+
background-color : ${palette('grayscale', 4)};
7+
width : 1px;
8+
height : 16px;
9+
object-fit : contain;
10+
`;
11+
12+
export const LoginBtn = Styled(Button)`
13+
margin-top : 14px;
14+
border-radius: 4px;
15+
background-image: linear-gradient(to right, ${palette('primary', 3)},${palette('primary', 0)} );
16+
width: 406px;
17+
height: 60px;
18+
color : ${palette('grayscale', 0)};
19+
font-size : 16px;
20+
font-weight : bold;
21+
`;
22+
23+
export const JoinBtn = Styled(Button)`
24+
margin-left : 15px;
25+
line-height : 1.5;
26+
color : ${palette('grayscale', 4)};
27+
font-family: AppleSDGothicNeo;
28+
font-size : 16px;
29+
font-weight : bold;
30+
`;
31+
32+
export const FindPwdBtn = Styled(Button)`
33+
margin-right : 15px;
34+
line-height : 1.5;
35+
color : ${palette('grayscale', 4)};
36+
font-family: AppleSDGothicNeo;
37+
font-size : 16px;
38+
`;
39+
40+
export const ButtonWrapper = Styled.div`
41+
display : flex;
42+
align-items: center;
43+
margin-top : 20px;
44+
`;
45+
46+
export const LoginLabel = Styled(Label)`
47+
margin-bottom : 60px;
48+
font-size: 40px;
49+
font-weight: bold;
50+
`;
51+
52+
export const LoginContainer = Styled.div`
53+
display : flex;
54+
position: relative;
55+
top: -60px;
56+
flex-direction : column;
57+
align-items : center;
58+
justify-content: center;
59+
width: 100%;
60+
height: 100vh;
61+
`;

0 commit comments

Comments
 (0)