Showing
19 changed files
with
417 additions
and
36 deletions
... | @@ -4,6 +4,7 @@ import './App.css'; | ... | @@ -4,6 +4,7 @@ import './App.css'; |
4 | import LoginPage from './pages/LoginPage'; | 4 | import LoginPage from './pages/LoginPage'; |
5 | import RegisterPage from './pages/RegisterPage'; | 5 | import RegisterPage from './pages/RegisterPage'; |
6 | import HomePage from './pages/HomePage'; | 6 | import HomePage from './pages/HomePage'; |
7 | +import SettingPage from './pages/SettingPage'; | ||
7 | 8 | ||
8 | function App() { | 9 | function App() { |
9 | return ( | 10 | return ( |
... | @@ -11,6 +12,7 @@ function App() { | ... | @@ -11,6 +12,7 @@ function App() { |
11 | <Route component={HomePage} path={['/@:username', '/']} exact /> | 12 | <Route component={HomePage} path={['/@:username', '/']} exact /> |
12 | <Route component={LoginPage} path="/login" /> | 13 | <Route component={LoginPage} path="/login" /> |
13 | <Route component={RegisterPage} path="/register" /> | 14 | <Route component={RegisterPage} path="/register" /> |
15 | + <Route component={SettingPage} path="/setting" /> | ||
14 | </> | 16 | </> |
15 | ); | 17 | ); |
16 | } | 18 | } | ... | ... |
1 | +import React from 'react'; | ||
2 | +import styled from 'styled-components'; | ||
3 | +import { NavLink } from 'react-router-dom'; | ||
4 | + | ||
5 | +const categories = [ | ||
6 | + { | ||
7 | + name: 'home', | ||
8 | + text: '홈', | ||
9 | + }, | ||
10 | + { | ||
11 | + name: 'setting', | ||
12 | + text: '설정', | ||
13 | + }, | ||
14 | +]; | ||
15 | + | ||
16 | +const CategoriesBlock = styled.div` | ||
17 | + display: flex; | ||
18 | + padding: 1rem; | ||
19 | + margin: 0 auto; | ||
20 | + @media screen and (max-width: 768px) { | ||
21 | + width: 100%; | ||
22 | + overflow-x: auto; | ||
23 | + } | ||
24 | +`; | ||
25 | + | ||
26 | +const Category = styled(NavLink)` | ||
27 | + font-size: 1.2rem; | ||
28 | + cursor: pointer; | ||
29 | + white-space: pre; | ||
30 | + text-decoration: none; | ||
31 | + color: inherit; | ||
32 | + padding-bottom: 0.25rem; | ||
33 | + &:hover { | ||
34 | + color: #495057; | ||
35 | + } | ||
36 | + & + & { | ||
37 | + margin-left: 2rem; | ||
38 | + } | ||
39 | + &.active { | ||
40 | + font-weight: 600; | ||
41 | + border-bottom: 2px solid #22b8cf; | ||
42 | + color: #22b8cf; | ||
43 | + &:hover { | ||
44 | + color: #3bc9db; | ||
45 | + } | ||
46 | + } | ||
47 | +`; | ||
48 | + | ||
49 | +const Categories = () => { | ||
50 | + return ( | ||
51 | + <CategoriesBlock> | ||
52 | + {categories.map((c) => ( | ||
53 | + <Category | ||
54 | + activeClassName="active" | ||
55 | + key={c.name} | ||
56 | + exact={c.name === 'home'} | ||
57 | + to={c.name === 'home' ? '/' : `/${c.name}`} | ||
58 | + > | ||
59 | + {c.text} | ||
60 | + </Category> | ||
61 | + ))} | ||
62 | + </CategoriesBlock> | ||
63 | + ); | ||
64 | +}; | ||
65 | + | ||
66 | +export default Categories; |
... | @@ -3,6 +3,7 @@ import styled from 'styled-components'; | ... | @@ -3,6 +3,7 @@ import styled from 'styled-components'; |
3 | import Responsive from './Responsive'; | 3 | import Responsive from './Responsive'; |
4 | import Button from './Button'; | 4 | import Button from './Button'; |
5 | import { Link } from 'react-router-dom'; | 5 | import { Link } from 'react-router-dom'; |
6 | +import Categories from './Categories'; | ||
6 | 7 | ||
7 | const HeaderBlock = styled.div` | 8 | const HeaderBlock = styled.div` |
8 | position: fixed; | 9 | position: fixed; |
... | @@ -35,7 +36,7 @@ const UserInfo = styled.div` | ... | @@ -35,7 +36,7 @@ const UserInfo = styled.div` |
35 | margin-right: 1rem; | 36 | margin-right: 1rem; |
36 | `; | 37 | `; |
37 | 38 | ||
38 | -const Header = ({ user, onLogout }) => { | 39 | +const Header = ({ user, onLogout, category, onSelect }) => { |
39 | return ( | 40 | return ( |
40 | <> | 41 | <> |
41 | <HeaderBlock> | 42 | <HeaderBlock> |
... | @@ -43,6 +44,11 @@ const Header = ({ user, onLogout }) => { | ... | @@ -43,6 +44,11 @@ const Header = ({ user, onLogout }) => { |
43 | <Link to="/" className="logo"> | 44 | <Link to="/" className="logo"> |
44 | 작심삼일 | 45 | 작심삼일 |
45 | </Link> | 46 | </Link> |
47 | + <Categories | ||
48 | + category={category} | ||
49 | + onSelect={onSelect} | ||
50 | + className="right" | ||
51 | + /> | ||
46 | {user ? ( | 52 | {user ? ( |
47 | <div className="right"> | 53 | <div className="right"> |
48 | <UserInfo>{user.username}</UserInfo> | 54 | <UserInfo>{user.username}</UserInfo> | ... | ... |
1 | +import React from 'react'; | ||
2 | +import styled from 'styled-components'; | ||
3 | +import Button from '../common/Button'; | ||
4 | +import palette from '../../lib/styles/palette'; | ||
5 | +const BJIDFormBlock = styled.div` | ||
6 | + width: 100%; | ||
7 | + border-top: 1px solid ${palette.gray[2]}; | ||
8 | + padding-top: 2rem; | ||
9 | + h4 { | ||
10 | + color: ${palette.gray[8]}; | ||
11 | + margin-top: 0; | ||
12 | + margin-bottom: 0.5rem; | ||
13 | + } | ||
14 | +`; | ||
15 | + | ||
16 | +const BJIDForm = ({ onChange, onBJIDSubmit, profile, onSyncBJIDSubmit }) => { | ||
17 | + return ( | ||
18 | + <BJIDFormBlock> | ||
19 | + <h4>백준 아이디</h4> | ||
20 | + <form onSubmit={onBJIDSubmit}> | ||
21 | + <input | ||
22 | + name="userBJID" | ||
23 | + onChange={onChange} | ||
24 | + value={profile.userBJID} | ||
25 | + placeholder="백준 아이디" | ||
26 | + /> | ||
27 | + <button type="submit">등록</button> | ||
28 | + </form> | ||
29 | + <button onClick={onSyncBJIDSubmit}>동기화</button> | ||
30 | + </BJIDFormBlock> | ||
31 | + ); | ||
32 | +}; | ||
33 | +export default BJIDForm; |
1 | +import React from 'react'; | ||
2 | +import styled from 'styled-components'; | ||
3 | +import Button from '../common/Button'; | ||
4 | +import palette from '../../lib/styles/palette'; | ||
5 | +import BJIDForm from './BJIDForm'; | ||
6 | + | ||
7 | +const SettingFormBlock = styled.div` | ||
8 | + h3 { | ||
9 | + margin: 0; | ||
10 | + color: ${palette.gray[8]}; | ||
11 | + margin-bottom: 1rem; | ||
12 | + } | ||
13 | + background: ${palette.gray[2]}; | ||
14 | + margin: 0 auto; | ||
15 | + display: flex; | ||
16 | + flex-direction: column; | ||
17 | +`; | ||
18 | +const StyledInput = styled.input` | ||
19 | + font-size: 1rem; | ||
20 | + border: none; | ||
21 | + border-bottom: 1px solid ${palette.gray[5]}; | ||
22 | + padding-bottom: 0.5rem; | ||
23 | + outline: none; | ||
24 | + &:focus { | ||
25 | + color: $oc-teal-7; | ||
26 | + border-bottom: 1px solid ${palette.gray[7]}; | ||
27 | + } | ||
28 | + & + & { | ||
29 | + margin-top: 1rem; | ||
30 | + } | ||
31 | +`; | ||
32 | +const SectionContainer = styled.div` | ||
33 | + display: flex; | ||
34 | +`; | ||
35 | + | ||
36 | +const SettingForm = ({ onChange, onBJIDSubmit, profile, onSyncBJIDSubmit }) => { | ||
37 | + return ( | ||
38 | + <SettingFormBlock> | ||
39 | + <SectionContainer> | ||
40 | + <h3>{profile.username}</h3> | ||
41 | + <p>입력</p> | ||
42 | + </SectionContainer> | ||
43 | + | ||
44 | + <SectionContainer> | ||
45 | + <BJIDForm | ||
46 | + profile={profile} | ||
47 | + onChange={onChange} | ||
48 | + onBJIDSubmit={onBJIDSubmit} | ||
49 | + onSyncBJIDSubmit={onSyncBJIDSubmit} | ||
50 | + /> | ||
51 | + </SectionContainer> | ||
52 | + | ||
53 | + <SectionContainer> | ||
54 | + <h3>친구</h3> | ||
55 | + <StyledInput name="BJID" placeholder="친구 아이디" /> | ||
56 | + <Button>추가</Button> | ||
57 | + </SectionContainer> | ||
58 | + <h3>친구 리스트</h3> | ||
59 | + </SettingFormBlock> | ||
60 | + ); | ||
61 | +}; | ||
62 | + | ||
63 | +export default SettingForm; |
... | @@ -4,6 +4,7 @@ import Header from '../../components/common/Header'; | ... | @@ -4,6 +4,7 @@ import Header from '../../components/common/Header'; |
4 | import { logout } from '../../modules/user'; | 4 | import { logout } from '../../modules/user'; |
5 | const HeaderContainer = () => { | 5 | const HeaderContainer = () => { |
6 | const { user } = useSelector(({ user }) => ({ user: user.user })); | 6 | const { user } = useSelector(({ user }) => ({ user: user.user })); |
7 | + | ||
7 | const dispatch = useDispatch(); | 8 | const dispatch = useDispatch(); |
8 | const onLogout = () => { | 9 | const onLogout = () => { |
9 | dispatch(logout()); | 10 | dispatch(logout()); | ... | ... |
1 | +import React, { useEffect, useState } from 'react'; | ||
2 | +import { useDispatch, useSelector } from 'react-redux'; | ||
3 | +import { withRouter } from 'react-router-dom'; | ||
4 | +import { | ||
5 | + changeField, | ||
6 | + setBJID, | ||
7 | + getPROFILE, | ||
8 | + syncBJID, | ||
9 | +} from '../../modules/profile'; | ||
10 | +import SettingForm from '../../components/setting/SettingForm'; | ||
11 | +import { sync } from '../../../node_modules/fast-glob/index'; | ||
12 | +const SettingContainer = ({ history }) => { | ||
13 | + const dispatch = useDispatch(); | ||
14 | + const [error, setError] = useState(null); | ||
15 | + const { user, profile } = useSelector(({ user, profile }) => ({ | ||
16 | + user: user.user, | ||
17 | + profile: profile, | ||
18 | + })); | ||
19 | + | ||
20 | + const onChange = (e) => { | ||
21 | + const { value, name } = e.target; | ||
22 | + dispatch( | ||
23 | + changeField({ | ||
24 | + key: name, | ||
25 | + value: value, | ||
26 | + }), | ||
27 | + ); | ||
28 | + }; | ||
29 | + | ||
30 | + const onSyncBJIDSubmit = (e) => { | ||
31 | + e.preventDefault(); | ||
32 | + let username = profile.username; | ||
33 | + dispatch(syncBJID({ username })); | ||
34 | + }; | ||
35 | + | ||
36 | + const onBJIDSubmit = (e) => { | ||
37 | + e.preventDefault(); | ||
38 | + let username = profile.username; | ||
39 | + let userBJID = profile.userBJID; | ||
40 | + | ||
41 | + dispatch(setBJID({ username, userBJID })); | ||
42 | + }; | ||
43 | + | ||
44 | + useEffect(() => { | ||
45 | + console.log('1'); | ||
46 | + let username = JSON.parse(user).username; | ||
47 | + dispatch(getPROFILE({ username })); | ||
48 | + //Do Init Form | ||
49 | + }, [dispatch]); | ||
50 | + | ||
51 | + return ( | ||
52 | + <SettingForm | ||
53 | + type="setting" | ||
54 | + onChange={onChange} | ||
55 | + onBJIDSubmit={onBJIDSubmit} | ||
56 | + onSyncBJIDSubmit={onSyncBJIDSubmit} | ||
57 | + profile={profile} | ||
58 | + ></SettingForm> | ||
59 | + ); | ||
60 | +}; | ||
61 | + | ||
62 | +export default withRouter(SettingContainer); |
jaksimsamil-page/src/lib/api/profile.js
0 → 100644
1 | +import client from './client'; | ||
2 | + | ||
3 | +export const setBJID = ({ username, userBJID }) => | ||
4 | + client.post('api/profile/setprofile', { | ||
5 | + username: username, | ||
6 | + userBJID: userBJID, | ||
7 | + }); | ||
8 | + | ||
9 | +export const getPROFILE = ({ username }) => | ||
10 | + client.post('api/profile/getprofile', { username }); | ||
11 | + | ||
12 | +export const syncBJ = ({ username }) => | ||
13 | + client.patch('api/profile/syncBJ', { username }); |
... | @@ -5,19 +5,19 @@ import createRequestSaga, { | ... | @@ -5,19 +5,19 @@ import createRequestSaga, { |
5 | createRequestActionTypes, | 5 | createRequestActionTypes, |
6 | } from '../lib/createRequestSaga'; | 6 | } from '../lib/createRequestSaga'; |
7 | import * as authAPI from '../lib/api/auth'; | 7 | import * as authAPI from '../lib/api/auth'; |
8 | -const CHAGE_FIELD = 'auth/CHANGE_FIELD'; | 8 | +const CHANGE_FIELD = 'auth/CHANGE_FIELD'; |
9 | const INITIALIZE_FORM = 'auth/INITIALIZE_FORM'; | 9 | const INITIALIZE_FORM = 'auth/INITIALIZE_FORM'; |
10 | 10 | ||
11 | -const REGISTER = 'auth/REGISTER'; | 11 | +const [REGISTER, REGISTER_SUCCESS, REGISTER_FAILURE] = createRequestActionTypes( |
12 | -const REGISTER_SUCCESS = 'auth/REGISTER_SUCCESS'; | 12 | + 'auth/REGISTER', |
13 | -const REGISTER_FAILURE = 'auth/REGISTER_FAILURE'; | 13 | +); |
14 | 14 | ||
15 | -const LOGIN = 'auth/LOGIN'; | 15 | +const [LOGIN, LOGIN_SUCCESS, LOGIN_FAILURE] = createRequestActionTypes( |
16 | -const LOGIN_SUCCESS = 'auth/LOGIN_SUCCESS'; | 16 | + 'auth/REGISTER', |
17 | -const LOGIN_FAILURE = 'auth/LOGIN_FAILURE'; | 17 | +); |
18 | 18 | ||
19 | export const changeField = createAction( | 19 | export const changeField = createAction( |
20 | - CHAGE_FIELD, | 20 | + CHANGE_FIELD, |
21 | ({ form, key, value }) => ({ | 21 | ({ form, key, value }) => ({ |
22 | form, | 22 | form, |
23 | key, | 23 | key, |
... | @@ -59,7 +59,7 @@ export function* authSaga() { | ... | @@ -59,7 +59,7 @@ export function* authSaga() { |
59 | 59 | ||
60 | const auth = handleActions( | 60 | const auth = handleActions( |
61 | { | 61 | { |
62 | - [CHAGE_FIELD]: (state, { payload: { form, key, value } }) => | 62 | + [CHANGE_FIELD]: (state, { payload: { form, key, value } }) => |
63 | produce(state, (draft) => { | 63 | produce(state, (draft) => { |
64 | draft[form][key] = value; | 64 | draft[form][key] = value; |
65 | }), | 65 | }), | ... | ... |
... | @@ -3,15 +3,17 @@ import { all } from 'redux-saga/effects'; | ... | @@ -3,15 +3,17 @@ import { all } from 'redux-saga/effects'; |
3 | import auth, { authSaga } from './auth'; | 3 | import auth, { authSaga } from './auth'; |
4 | import loading from './loading'; | 4 | import loading from './loading'; |
5 | import user, { userSaga } from './user'; | 5 | import user, { userSaga } from './user'; |
6 | +import profile, { profileSaga } from './profile'; | ||
6 | 7 | ||
7 | const rootReducer = combineReducers({ | 8 | const rootReducer = combineReducers({ |
8 | auth, | 9 | auth, |
9 | loading, | 10 | loading, |
10 | user, | 11 | user, |
12 | + profile, | ||
11 | }); | 13 | }); |
12 | 14 | ||
13 | export function* rootSaga() { | 15 | export function* rootSaga() { |
14 | - yield all([authSaga(), userSaga()]); | 16 | + yield all([authSaga(), userSaga(), profileSaga()]); |
15 | } | 17 | } |
16 | 18 | ||
17 | export default rootReducer; | 19 | export default rootReducer; | ... | ... |
jaksimsamil-page/src/modules/profile.js
0 → 100644
1 | +import { createAction, handleActions } from 'redux-actions'; | ||
2 | +import createRequestSaga, { | ||
3 | + createRequestActionTypes, | ||
4 | +} from '../lib/createRequestSaga'; | ||
5 | +import produce from 'immer'; | ||
6 | +import * as profileAPI from '../lib/api/profile'; | ||
7 | +import { takeLatest } from 'redux-saga/effects'; | ||
8 | + | ||
9 | +const INITIALIZE = 'profile/INITIALIZE'; | ||
10 | +const CHANGE_FIELD = 'profile/CHANGE_FIELD'; | ||
11 | +const [SET_BJID, SET_BJID_SUCCESS, SET_BJID_FAILURE] = createRequestActionTypes( | ||
12 | + 'profile/SET_BJID', | ||
13 | +); | ||
14 | +const [ | ||
15 | + GET_PROFILE, | ||
16 | + GET_PROFILE_SUCCESS, | ||
17 | + GET_PROFILE_FAILURE, | ||
18 | +] = createRequestActionTypes('profile/GET_PROFILE'); | ||
19 | + | ||
20 | +const [ | ||
21 | + SYNC_BJID, | ||
22 | + SYNC_BJID_SUCCESS, | ||
23 | + SYNC_BJID_FAILURE, | ||
24 | +] = createRequestActionTypes('profile/SYNC_BJID'); | ||
25 | + | ||
26 | +export const syncBJID = createAction(SYNC_BJID, ({ username }) => ({ | ||
27 | + username, | ||
28 | +})); | ||
29 | +export const setBJID = createAction(SET_BJID, ({ username, userBJID }) => ({ | ||
30 | + username, | ||
31 | + userBJID, | ||
32 | +})); | ||
33 | + | ||
34 | +export const changeField = createAction(CHANGE_FIELD, ({ key, value }) => ({ | ||
35 | + key, | ||
36 | + value, | ||
37 | +})); | ||
38 | + | ||
39 | +export const getPROFILE = createAction(GET_PROFILE, ({ username }) => ({ | ||
40 | + username, | ||
41 | +})); | ||
42 | +const initialState = { | ||
43 | + username: '', | ||
44 | + userBJID: '', | ||
45 | + solvedBJ: '', | ||
46 | + friendList: [], | ||
47 | + profileError: '', | ||
48 | +}; | ||
49 | +const getPROFILESaga = createRequestSaga(GET_PROFILE, profileAPI.getPROFILE); | ||
50 | +const setBJIDSaga = createRequestSaga(SET_BJID, profileAPI.setBJID); | ||
51 | +const syncBJIDSaga = createRequestSaga(SYNC_BJID, profileAPI.syncBJ); | ||
52 | +export function* profileSaga() { | ||
53 | + yield takeLatest(SET_BJID, setBJIDSaga); | ||
54 | + yield takeLatest(GET_PROFILE, getPROFILESaga); | ||
55 | + yield takeLatest(SYNC_BJID, syncBJIDSaga); | ||
56 | +} | ||
57 | + | ||
58 | +export default handleActions( | ||
59 | + { | ||
60 | + [INITIALIZE]: (state) => initialState, | ||
61 | + [CHANGE_FIELD]: (state, { payload: { key, value } }) => | ||
62 | + produce(state, (draft) => { | ||
63 | + draft[key] = value; | ||
64 | + }), | ||
65 | + [GET_PROFILE_SUCCESS]: ( | ||
66 | + state, | ||
67 | + { payload: { username, userBJID, solvedBJ, friendList } }, | ||
68 | + ) => ({ | ||
69 | + ...state, | ||
70 | + username: username, | ||
71 | + userBJID: userBJID, | ||
72 | + solvedBJ: solvedBJ, | ||
73 | + friendList: friendList, | ||
74 | + profileError: null, | ||
75 | + }), | ||
76 | + [GET_PROFILE_FAILURE]: (state, { payload: error }) => ({ | ||
77 | + ...state, | ||
78 | + profileError: error, | ||
79 | + }), | ||
80 | + | ||
81 | + [SET_BJID_SUCCESS]: (state, { payload: { userBJID } }) => ({ | ||
82 | + ...state, | ||
83 | + userBJID: userBJID, | ||
84 | + profileError: null, | ||
85 | + }), | ||
86 | + [SET_BJID_FAILURE]: (state, { payload: error }) => ({ | ||
87 | + ...state, | ||
88 | + profileError: error, | ||
89 | + }), | ||
90 | + [SYNC_BJID_SUCCESS]: (state, { payload: { solvedBJ } }) => ({ | ||
91 | + ...state, | ||
92 | + solvedBJ, | ||
93 | + profileError: null, | ||
94 | + }), | ||
95 | + [SYNC_BJID_FAILURE]: (state, { payload: error }) => ({ | ||
96 | + ...state, | ||
97 | + profileError: error, | ||
98 | + }), | ||
99 | + }, | ||
100 | + initialState, | ||
101 | +); |
jaksimsamil-page/src/pages/SettingPage.js
0 → 100644
1 | +import React from 'react'; | ||
2 | +import HeaderContainer from '../containers/common/HeaderContainer'; | ||
3 | +import SettingForm from '../components/setting/SettingForm'; | ||
4 | +import SettingContainer from '../containers/setting/SettingContainer'; | ||
5 | + | ||
6 | +const SettingPage = () => { | ||
7 | + return ( | ||
8 | + <div> | ||
9 | + <HeaderContainer /> | ||
10 | + <SettingContainer></SettingContainer> | ||
11 | + </div> | ||
12 | + ); | ||
13 | +}; | ||
14 | + | ||
15 | +export default SettingPage; |
... | @@ -18,20 +18,22 @@ | ... | @@ -18,20 +18,22 @@ |
18 | 18 | ||
19 | ## API Table | 19 | ## API Table |
20 | 20 | ||
21 | -| group | description | method | URL | Detail | Auth | | 21 | +| group | description | method | URL | Detail | Auth | |
22 | -| ------- | --------------------------- | ------ | ------------------------ | -------- | --------- | | 22 | +| ------- | --------------------------- | --------- | ------------------------ | -------- | --------- | |
23 | -| user | 유저 등록 | POST | api/user | 바로가기 | JWT Token | | 23 | +| user | 유저 등록 | POST | api/user | 바로가기 | JWT Token | |
24 | -| user | 유저 삭제 | DELETE | api/user:id | 바로가기 | JWT Token | | 24 | +| user | 유저 삭제 | DELETE | api/user:id | 바로가기 | JWT Token | |
25 | -| user | 특정 유저 조회 | GET | api/user:id | 바로가기 | None | | 25 | +| user | 특정 유저 조회 | GET | api/user:id | 바로가기 | None | |
26 | -| user | 전체 유저 조회 | GET | api/user | 바로가기 | JWT Token | | 26 | +| user | 전체 유저 조회 | GET | api/user | 바로가기 | JWT Token | |
27 | -| friend | 유저 친구 등록 | POST | api/friend | 바로가기 | JWT Token | | 27 | +| friend | 유저 친구 등록 | POST | api/friend | 바로가기 | JWT Token | |
28 | -| friend | 유저의 친구 조회 | GET | api/friend:id | 바로가기 | None | | 28 | +| friend | 유저의 친구 조회 | GET | api/friend:id | 바로가기 | None | |
29 | -| profile | 유저가 푼 문제 조회(백준) | GET | api/profile/solvedBJ:id | 바로가기 | None | | 29 | +| profile | 유저가 푼 문제 조회(백준) | GET | api/profile/solvedBJ:id | 바로가기 | None | |
30 | -| profile | 유저가 푼 문제 동기화(백준) | PATCH | api/profile/syncBJ | 바로가기 | None | | 30 | +| profile | 유저가 푼 문제 동기화(백준) | PATCH | api/profile/syncBJ | 바로가기 | None | |
31 | -| profile | 유저 정보 수정 | POST | api/profile/setprofile | 바로가기 | JWT TOKEN | | 31 | +| profile | 유저 정보 수정 | POST | api/profile/setprofile | 바로가기 | JWT TOKEN | |
32 | -| profile | 추천 문제 조회 | GET | api/profile/recommend:id | 바로가기 | None | | 32 | +| profile | 유저 정보 받아오기 | POST | api/profile/getprofile | 바로가기 | JWT | |
33 | -| notify | 슬랙 메시지 전송 요청 | POST | api/notify/slack | 바로가기 | Jwt Token | | 33 | +| profile | 추천 문제 조회 | GET | api/profile/recommend:id | 바로가기 | None | |
34 | -| auth | 로그인 | POST | api/auth/login | 바로가기 | None | | 34 | +| notify | 슬랙 메시지 전송 요청 | POST | api/notify/ | |
35 | -| auth | 로그아웃 | POST | api/auth/logout | 바로가기 | JWT Token | | 35 | +| slack | 바로가기 | Jwt Token | |
36 | -| auth | 회원가입 | POST | api/auth/register | 바로가기 | None | | 36 | +| auth | 로그인 | POST | api/auth/login | 바로가기 | None | |
37 | -| auth | 로그인 확인 | GET | api/auth/check | 바로가기 | None | | 37 | +| auth | 로그아웃 | POST | api/auth/logout | 바로가기 | JWT Token | |
38 | +| auth | 회원가입 | POST | api/auth/register | 바로가기 | None | | ||
39 | +| auth | 로그인 확인 | GET | api/auth/check | 바로가기 | None | | ... | ... |
... | @@ -88,7 +88,6 @@ exports.login = async (ctx) => { | ... | @@ -88,7 +88,6 @@ exports.login = async (ctx) => { |
88 | GET api/auth/check | 88 | GET api/auth/check |
89 | */ | 89 | */ |
90 | exports.check = async (ctx) => { | 90 | exports.check = async (ctx) => { |
91 | - console.log(ctx.state); | ||
92 | const { user } = ctx.state; | 91 | const { user } = ctx.state; |
93 | if (!user) { | 92 | if (!user) { |
94 | ctx.status = 401; | 93 | ctx.status = 401; | ... | ... |
... | @@ -7,4 +7,5 @@ profile.get("/solvednum:id"); | ... | @@ -7,4 +7,5 @@ profile.get("/solvednum:id"); |
7 | profile.get("/recommendps:id"); | 7 | profile.get("/recommendps:id"); |
8 | profile.patch("/syncBJ", profileCtrl.syncBJ); | 8 | profile.patch("/syncBJ", profileCtrl.syncBJ); |
9 | profile.post("/setprofile", profileCtrl.setProfile); | 9 | profile.post("/setprofile", profileCtrl.setProfile); |
10 | +profile.post("/getprofile", profileCtrl.getProfile); | ||
10 | module.exports = profile; | 11 | module.exports = profile; | ... | ... |
... | @@ -13,6 +13,24 @@ exports.checkObjectId = (ctx, next) => { | ... | @@ -13,6 +13,24 @@ exports.checkObjectId = (ctx, next) => { |
13 | } | 13 | } |
14 | return next(); | 14 | return next(); |
15 | }; | 15 | }; |
16 | +/*POST /api/profile/getprofile | ||
17 | +{ | ||
18 | + username: "username" | ||
19 | +} | ||
20 | +*/ | ||
21 | +exports.getProfile = async (ctx) => { | ||
22 | + try { | ||
23 | + const { username } = ctx.request.body; | ||
24 | + const profile = await Profile.findByUsername(username); | ||
25 | + if (!profile) { | ||
26 | + ctx.status = 401; | ||
27 | + return; | ||
28 | + } | ||
29 | + ctx.body = profile; | ||
30 | + } catch (e) { | ||
31 | + ctx.throw(500, e); | ||
32 | + } | ||
33 | +}; | ||
16 | /* | 34 | /* |
17 | POST /api/proflie/setprofile | 35 | POST /api/proflie/setprofile |
18 | { | 36 | { | ... | ... |
... | @@ -3,14 +3,11 @@ const User = require("../models/user"); | ... | @@ -3,14 +3,11 @@ const User = require("../models/user"); |
3 | 3 | ||
4 | const jwtMiddleware = async (ctx, next) => { | 4 | const jwtMiddleware = async (ctx, next) => { |
5 | const token = ctx.cookies.get("access_token"); | 5 | const token = ctx.cookies.get("access_token"); |
6 | - console.log("1"); | 6 | + |
7 | - console.log(token); | ||
8 | if (!token) { | 7 | if (!token) { |
9 | - console.log("1"); | ||
10 | return next(); | 8 | return next(); |
11 | } | 9 | } |
12 | try { | 10 | try { |
13 | - console.log("1"); | ||
14 | const decoded = jwt.verify(token, process.env.JWT_SECRET); | 11 | const decoded = jwt.verify(token, process.env.JWT_SECRET); |
15 | ctx.state.user = { | 12 | ctx.state.user = { |
16 | _id: decoded._id, | 13 | _id: decoded._id, |
... | @@ -25,7 +22,7 @@ const jwtMiddleware = async (ctx, next) => { | ... | @@ -25,7 +22,7 @@ const jwtMiddleware = async (ctx, next) => { |
25 | httpOnly: true, | 22 | httpOnly: true, |
26 | }); | 23 | }); |
27 | } | 24 | } |
28 | - console.log(decoded); | 25 | + |
29 | return next(); | 26 | return next(); |
30 | } catch (e) { | 27 | } catch (e) { |
31 | return next(); | 28 | return next(); | ... | ... |
-
Please register or login to post a comment