From c569b317e8075692c0672d621811706f8b49a219 Mon Sep 17 00:00:00 2001 From: pjkim Date: Mon, 14 Apr 2025 19:08:16 +0900 Subject: [PATCH] =?UTF-8?q?=EA=B3=84=EC=A0=95=20=EB=A1=9C=EA=B7=B8?= =?UTF-8?q?=EC=9D=B8=20API=20=EC=B4=88=EA=B8=B0=20=EC=9E=91=EC=97=85=20?= =?UTF-8?q?=EC=99=84=EB=A3=8C?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/controllers/auth/approveCtr.js | 53 ++++- src/controllers/auth/authControllers.js | 3 +- src/controllers/auth/deleteCtr.js | 42 ++-- src/controllers/auth/getCtr.js | 36 ++-- src/controllers/auth/loginCtr.js | 3 +- src/controllers/auth/logoutCtr.js | 9 +- src/controllers/auth/readme | 59 +++++- src/controllers/auth/rolesCtr.js | 3 +- src/controllers/auth/searchCtr.js | 120 +++++++++-- src/controllers/auth/updateCtr.js | 157 ++++++++++++++- src/models/postgre_SQL.js | 254 ++++++++++-------------- src/models/userAuthController.js | 76 ++++--- src/routes/authRoutes.js | 7 +- src/utils/Global_TP.js | 20 ++ 14 files changed, 585 insertions(+), 257 deletions(-) diff --git a/src/controllers/auth/approveCtr.js b/src/controllers/auth/approveCtr.js index 4026761..4793066 100644 --- a/src/controllers/auth/approveCtr.js +++ b/src/controllers/auth/approveCtr.js @@ -8,12 +8,42 @@ const approveCtr = (req, res) => { req_param: {} } if (req.body) { - // let { id, pw, name, pos, cls } = req.body; + let { id, isApprove } = req.body; // approve 업데이트 전달 + let ret_id = _GTP.STR_VALIDER(id); + if (!ret_id) { + _resp_json.result = "fail"; + _resp_json.reason = "Body 'id' Error"; + res.status(400).json(_resp_json); + return; + } + isApprove = _GTP.TO_BOOLEAN(isApprove); + + _SPM.db.pgSql.Query_AUTH_APPROVE(id, isApprove) + .then((resRow) => { + if (resRow.rowCount) { + _resp_json.result = "ok"; + _resp_json.data = resRow.rows + _resp_json.reason = 'update your accounts'; + res.status(200).json(_resp_json); + } + else { + _resp_json.result = "fail"; + _resp_json.reason = 'not applied'; + res.status(500).json(_resp_json); + } + }) + .catch((error) => { + _resp_json.result = "fail"; + _resp_json.reason = error.message; + res.status(500).json(_resp_json); + }) } else { - + _resp_json.result = "fail"; + _resp_json.reason = 'Bad Request'; + res.status(400).json(_resp_json); } } @@ -25,14 +55,21 @@ const pendingsCtr = (req, res) => { req_body: {}, req_param: {} } - if (req.body) { - // let { id, pw, name, pos, cls } = req.body; - // approve 상태인 애들 쿼리하여 전달 + _SPM.db.pgSql.Query_AUTH_PENDING( + ).then((resRow) => { + if (!resRow.rows.length) throw new Error("pending account is Empty") - } - else { + _resp_json.result = "ok"; + _resp_json.data = resRow.rows + _resp_json.reason = 'get pending accounts'; + res.status(200).json(_resp_json); + }).catch((error) => { + console.log(error); + _resp_json.result = "fail"; + _resp_json.reason = error.message; + res.status(200).json(_resp_json); + }) - } } module.exports = { approveCtr, pendingsCtr }; \ No newline at end of file diff --git a/src/controllers/auth/authControllers.js b/src/controllers/auth/authControllers.js index 5ef8e46..454bcb2 100644 --- a/src/controllers/auth/authControllers.js +++ b/src/controllers/auth/authControllers.js @@ -6,7 +6,7 @@ const loginCtr = require('./loginCtr'); const logoutCtr = require('./logoutCtr'); const searchCtr = require('./searchCtr'); const rolesCtr = require('./rolesCtr'); -const { updateCtr, clsChangeCtr } = require('./updateCtr'); +const updateCtr = require('./updateCtr'); const { approveCtr, pendingsCtr } = require('./approveCtr'); // 각 기능별 컨트롤러를 모아서 export @@ -18,7 +18,6 @@ module.exports = { logout: logoutCtr, search: searchCtr, update: updateCtr, - clsChange : clsChangeCtr, roles: rolesCtr, approve: approveCtr, pendings: pendingsCtr diff --git a/src/controllers/auth/deleteCtr.js b/src/controllers/auth/deleteCtr.js index 6467774..20ef4ea 100644 --- a/src/controllers/auth/deleteCtr.js +++ b/src/controllers/auth/deleteCtr.js @@ -9,20 +9,36 @@ const deleteCtr = (req, res) => { req_body: {}, req_param: {} } - // 인증 관련 모든 요청 처리 - switch(req.method) { - case 'GET': {} - case 'POST': {} - case 'PUT': {} - case 'PATCH': {} - case 'DELETE': { - res.status(200).json({ message: 'This is the auth/delete endpoint!' }); - } break; - default : { - //exception - res.status(405).json({error: 'Method Not Allowed'}); - } + + let { id } = req.query; + let ret_id = _GTP.STR_VALIDER(id); + if (!ret_id) { + _resp_json.result = "fail"; + _resp_json.reason = "Body 'id' Error"; + res.status(400).json(_resp_json); + return; } + _SPM.db.pgSql.Query_AUTH_DELETE(id) + .then((resRow) => { + if (resRow.rowCount) { + _resp_json.result = "ok"; + _resp_json.data = resRow.rows + _resp_json.reason = 'delete account'; + res.status(200).json(_resp_json); + } + else { + _resp_json.result = "fail"; + _resp_json.reason = 'not applied'; + res.status(500).json(_resp_json); + } + }) + .catch((error)=>{ + console.log(error); + _resp_json.result = "fail"; + _resp_json.reason = error.message; + res.status(500).json(_resp_json); + }) + } module.exports = deleteCtr; \ No newline at end of file diff --git a/src/controllers/auth/getCtr.js b/src/controllers/auth/getCtr.js index 9d81a39..016578d 100644 --- a/src/controllers/auth/getCtr.js +++ b/src/controllers/auth/getCtr.js @@ -9,20 +9,30 @@ const getCtr = (req, res) => { req_body: {}, req_param: {} } - // 인증 관련 모든 요청 처리 - switch(req.method) { - case 'GET': { - res.status(200).json({ message: 'This is the auth/get endpoint!' }); - } break; - case 'POST': {} - case 'PUT': {} - case 'PATCH': {} - case 'DELETE': {} - default : { - //exception - res.status(405).json({error: 'Method Not Allowed'}); - } + // + let { id } = req.query; + let ret_id = _GTP.STR_VALIDER(id); + if (!ret_id) { + _resp_json.result = "fail"; + _resp_json.reason = "Body 'id' Error"; + res.status(400).json(_resp_json); + return; } + _SPM.db.pgSql.Query_AUTH_GET(id) + .then((resRow) => { + if (!resRow.rows.length) throw new Error("account is Empty") + + _resp_json.result = "ok"; + _resp_json.data = resRow.rows + _resp_json.reason = 'get account info'; + res.status(200).json(_resp_json); + }) + .catch((error)=>{ + console.log(error); + _resp_json.result = "fail"; + _resp_json.reason = error.message; + res.status(500).json(_resp_json); + }) } module.exports = getCtr; \ No newline at end of file diff --git a/src/controllers/auth/loginCtr.js b/src/controllers/auth/loginCtr.js index eec3d6f..7ea658e 100644 --- a/src/controllers/auth/loginCtr.js +++ b/src/controllers/auth/loginCtr.js @@ -45,7 +45,8 @@ const loginCtr = (req, res) => { //#region 쿠키 확인 let accInfo = { id: id, - pw: rowObj.pw // 해쉬된 pw를 등록 + pw: rowObj.pw, // 해쉬된 pw를 등록 + cls: rowObj.cls }; _SPM.uac.regist_cookie(res, accInfo); //#endregion diff --git a/src/controllers/auth/logoutCtr.js b/src/controllers/auth/logoutCtr.js index 56057f3..afe9354 100644 --- a/src/controllers/auth/logoutCtr.js +++ b/src/controllers/auth/logoutCtr.js @@ -10,15 +10,14 @@ const logoutCtr = (req, res) => { //해당 쿠키 로그아웃 let _cookie_name = _SPM.uac._config.cookie_name; let _isCookie = (req.cookies.SPM!=undefined) ? true : false; - res.clearCookie(_cookie_name); - _isCookie = (req.cookies.SPM==undefined) ? false : true; - if (!_isCookie) { + if (_isCookie) { + res.clearCookie(_cookie_name); _resp_json.result = 'ok'; - _resp_json.reason = `'${_cookie_name}' cookie is deleted` + _resp_json.reason = `cookie is deleted` } else { _resp_json.result = 'fail'; - _resp_json.reason = `'${_cookie_name}' cookie is NOT deleted` + _resp_json.reason = `cookie is NOT deleted` } res.status(200).json(_resp_json); } diff --git a/src/controllers/auth/readme b/src/controllers/auth/readme index 01fec87..a54b58a 100644 --- a/src/controllers/auth/readme +++ b/src/controllers/auth/readme @@ -4,10 +4,57 @@ createCtr.js : 계정 생성용 api rolesCtr.js : role종류 얻기용 api loginCtr.js : login api logoutCtr.js : logout api +approveCtr.js : { + pending : 승인 대기중인 계정 +} +approve : 승인 할 계정 approve 상태 변경 +getCtr.js : 특정 계정 id의 정보 얻기 +deleteCtr.js : 특정 계정 id를 삭제 +updateCtr.js : 계정 정보 변경 +searchCtr.js : 계정 검색 -작업안된 Controller -updateCtr.js -searchCtr.js -getCtr.js -deleteCtr.js -approveCtr.js \ No newline at end of file +🚀API List +🧑‍🚀Auth + - POST + - '/auth/create' : 회원 가입 + - '/auth/login' : 계정 로그인 + - GET + - '/auth/get' : 계정 정보 얻기 + - '/auth/logout' : 계정 로그아웃 + - '/auth/search' : 계정 검색 + parameter : { + "page":"", // page 수 + "limit":"", // 한 page 출력 수 + "sort":"", //CREATE_AT, UPDATE_AT, NAME + "order":"", //DESC or ASC + "filter": { // 내용 생략 가능 + "id":"", // 아이디 + "pos":"", // 직책 + "name":"", // 이름 + "cls":"", // 권한 + "isApprove":"" // 계정 허용 여부 + }, + } + - '/auth/roles' : 권한 종류를 가져옴 + - '/auth/pendings' : 회원가입 후 승인 대기중인 계정들을 가져옴 + - PATCH + - '/auth/update' : 계정의 정보를 변경 + - 로그인한 계정의 pw, name, pos, cls, isApprove를 변경 + body : { + "id":"guest", // 자신의 id + "pw":"1234", // 위에 입력한 id의 기존 pw와 다르면 변경 + "name":"", // 이름 + "pos":"" // 직책 + } + - 다른 계정의 pw, name, pos, cls, isApprove를 변경(관리자) + body : { + "id":"guest", // 자신의 id or 다른 id를 입력 + "pw":"1234", // 위에 입력한 id의 기존 pw와 다르면 변경 + "name":"", // 이름 + "pos":"", // 직책 + "cls":"", // 권한 + "isApprove":"" // 계정 허용 여부 + } + - '/auth/approve' : 회원가입된 계정의 승인(관리자) + - DELETE + - '/auth/delete' : 계정 삭제 diff --git a/src/controllers/auth/rolesCtr.js b/src/controllers/auth/rolesCtr.js index f2de462..912a7f3 100644 --- a/src/controllers/auth/rolesCtr.js +++ b/src/controllers/auth/rolesCtr.js @@ -21,9 +21,8 @@ const rolesCtr = async (req, res) => { console.log(error); _resp_json.result = "fail"; _resp_json.reason = error.message; - res.status(200).json(_resp_json); + res.status(500).json(_resp_json); }) - } module.exports = rolesCtr; \ No newline at end of file diff --git a/src/controllers/auth/searchCtr.js b/src/controllers/auth/searchCtr.js index b1dbb0e..8caf844 100644 --- a/src/controllers/auth/searchCtr.js +++ b/src/controllers/auth/searchCtr.js @@ -9,19 +9,115 @@ const searchCtr = (req, res) => { req_body: {}, req_param: {} } - // 인증 관련 모든 요청 처리 - switch(req.method) { - case 'GET': {} - case 'POST': { - res.status(200).json({ message: 'This is the auth/search endpoint!' }); - } break; - case 'PUT': {} - case 'PATCH': {} - case 'DELETE': {} - default : { - //exception - res.status(405).json({error: 'Method Not Allowed'}); + + try { + let param = req.query; + if (param) { + let { page, limit, sort, order, filter } = param; + + let id, pos, name, cls, isApprove; + let WHEREContext = ""; + if (filter) { + const obj = JSON.parse(filter); + id = obj.authorityType; + pos = obj.pos; + name = obj.name; + cls = obj.cls; + isApprove = obj.isApprove; + } + + let check_filter = 0; + let filters = []; + let ret_id = _GTP.STR_VALIDER(id); + if (ret_id) { + check_filter++; + let _filter_name = `"id" LIKE '${id}%'`; + filters.push(_filter_name); + } + + let ret_pos = _GTP.STR_VALIDER(pos); + if (ret_pos) { + check_filter++; + let _filter_name = `"pos" LIKE '${pos}%'`; + filters.push(_filter_name); + } + let ret_name = _GTP.STR_VALIDER(name); + if (ret_name) { + check_filter++; + let _filter_name = `"name" LIKE '${name}%'`; + filters.push(_filter_name); + } + let ret_cls = _GTP.STR_VALIDER(cls); + if (ret_cls) { + check_filter++; + let _filter_name = `"cls" LIKE '${cls}%'`; + filters.push(_filter_name); + } + let ret_isApprove = _GTP.BOOL_VALIDER(isApprove); + if (ret_isApprove) { + check_filter++; + let _filter_name = `"isApprove"=${isApprove}`; + filters.push(_filter_name); + } + + + if (check_filter == 1) { + WHEREContext = `WHERE ${filters.join(', ')}`; + } + else if(check_filter >= 2) { + WHEREContext = `WHERE `; + for (let i = 0; i < filters.length; i++) { + WHEREContext += filters[i]; + if (i != (filters.length - 1)) WHEREContext += ` AND ` + } + } + + let ret_page = _GTP.STR_VALIDER(page); + if (!ret_page) page = 1; + let ret_limit = _GTP.STR_VALIDER(limit); + if (!ret_limit) limit = 1; + if (typeof page === 'string') page = Number(page) + if (typeof limit === 'string') limit = Number(limit) + if (page < 1) page = 1; + if (limit < 1) limit = 1; + + let ret_sort = _GTP.STR_VALIDER(sort); + if (!ret_sort) ret_sort = "CREATE_AT"; + else ret_sort = sort; + let ret_order = _GTP.STR_VALIDER(order); + if (!ret_order) ret_order = "DESC"; + else ret_order = order; + + let _query_data = { + page: page, + limit: limit, + sort: ret_sort, + order: ret_order, + where: WHEREContext + }; + + _SPM.db.pgSql.Query_AUTH_SEARCH(_query_data).then((resRow) => { + _resp_json.result = "ok"; + _resp_json.reason = `account search`; + _resp_json.data = resRow.result_val; + res.status(200).json(_resp_json); + }) + .catch((error)=>{ + _resp_json.result = "fail"; + _resp_json.reason = 'Internal Select Query Error'; + res.status(500).json(_resp_json); + }) } + else { + _resp_json.result = "fail"; + _resp_json.reason = 'Bad Request'; + res.status(400).json(_resp_json); + } + } + catch(error) { + _resp_json.result = "fail"; + _resp_json.reason = error.message; + res.status(500).json(_resp_json); } } diff --git a/src/controllers/auth/updateCtr.js b/src/controllers/auth/updateCtr.js index b8c7afa..34548fc 100644 --- a/src/controllers/auth/updateCtr.js +++ b/src/controllers/auth/updateCtr.js @@ -1,5 +1,6 @@ -const updateCtr = (req, res) => { + +const updateCtr = async (req, res) => { let _resp_json = { result: "ok", reason: { @@ -10,14 +11,152 @@ const updateCtr = (req, res) => { req_param: {} } - res.status(200).json({ message: 'This is the auth/update endpoint!' }); + //-- guest 계정 + //-- id, pw, name, pos + //-- admin 계정 + //-- id, pw, name, pos, cls, isApprove - //예외시 처리리 - //res.status(405).json({error: 'Method Not Allowed'}); + try { + if (req.body) { + let { id, pw, name, pos, cls, isApprove } = req.body; + let _cookieInfo = _SPM.uac.get_cookie_info(req); + if (_cookieInfo) { + let ret_id = _GTP.STR_VALIDER(id); + if (!ret_id) { + _resp_json.result = "fail"; + _resp_json.reason = "Body 'id' Error"; + res.status(400).json(_resp_json); + return; + } + + // _cookieInfo.id; + // _cookieInfo.cls; + if (_cookieInfo.cls == "guest") { + //변경할 pw, name, pos만 변경 가능(요청시 id, pw 쿠키가 동일해야함) + if (_cookieInfo.id != id) { + _resp_json.result = "fail"; + _resp_json.reason = 'Bad Request, is not your id'; + res.status(400).json(_resp_json); + } + } + else if (_cookieInfo.cls == "admin") { + //변경할 pw, name, pos, cls, isApprove(요청시 id, pw 쿠키가 동일해야함) + } + else { + _resp_json.result = "fail"; + _resp_json.reason = 'Bad Request, check login authorization'; + res.status(400).json(_resp_json); + } + + _SPM.db.pgSql.Query_AUTH_ROLES(); + // let checkToken = await _SPM.uac.jwtTokenAuthentication(req, res); + let dbAccProm = _SPM.db.pgSql.Query_AUTH_GETID_ALL(id); + let _checkAcc = await Promise.race([dbAccProm]); + let _userPw = _checkAcc.rows[0].pw + let rolesProm = _SPM.db.pgSql.Query_AUTH_ROLES(); + let _preRoles = await Promise.race([rolesProm]); + var isChanged = { + pw: false, + name: false, + pos: false, + cls: false, + isApprove: false + }; + var setContext = ""; + if (pw != "") { + let compare_prom = _GTP.BCRYPT_COMPARE(pw, _userPw) + let _pre_pwCh = await Promise.race([compare_prom]); + if (typeof _pre_pwCh === "boolean") { + isChanged.pw = _pre_pwCh; // false면, 바뀔게 있으니 pw 변경 진행 + if (!isChanged.pw) { + // hashed + let hashedProm = _GTP.BCRYPT_HASH(pw) + const _hashed_ChPw = await Promise.race([hashedProm]); + if (_hashed_ChPw != undefined) { + setContext = `SET pw='${_hashed_ChPw}'`; + } + } + } + else { + console.log(_pre_pwCh); + } + } + + if (name != "") { + isChanged.name = true; + if (setContext.length) setContext += `, name='${name}'` + else setContext = `SET name='${name}'` + } + if (pos != "") { + isChanged.pos = true; + if (setContext.length) setContext += `, pos='${pos}'` + else setContext = `SET pos='${pos}'` + } + if (_cookieInfo.cls == "admin") { + let rolesProm = _SPM.db.pgSql.Query_AUTH_ROLES(); + let _preRoles = await Promise.race([rolesProm]); + if (_preRoles.rowCount) { + if (cls != undefined) { + let cls_type_check = false; + for (let _row of _preRoles.rows) { + let _cls_name = _row.name; + if (_cls_name == cls) { + cls_type_check = true; + break; + } + } + if (cls_type_check) { + if (setContext.length) setContext += `, cls='${cls}'` + else setContext = `SET cls='${cls}'` + } + } + } + + if (isApprove != undefined && isApprove != "") { + isApprove = _GTP.TO_BOOLEAN(isApprove) + if (setContext.length) setContext += `, "isApprove"=${isApprove}` + else setContext = `SET "isApprove"=${isApprove}` + } + } + + if (setContext.length) { + setContext += `, "mdfDate"=CURRENT_TIMESTAMP`; + let _updateProm = _SPM.db.pgSql.Query_AUTH_UPDATE(id, setContext); + let _updateRes = await Promise.race([_updateProm]); + if (_updateRes.rowCount) { + _resp_json.result = "ok"; + _resp_json.reason = `'${id}' Info Updated`; + res.status(200).json(_resp_json); + } + else { + _resp_json.result = "fail"; + _resp_json.reason = 'Internal Update Query Error'; + res.status(500).json(_resp_json); + } + } + else { + _resp_json.result = "fail"; + _resp_json.reason = 'Bad Request'; + res.status(400).json(_resp_json); + } + } + else { + _resp_json.result = "fail"; + _resp_json.reason = 'please relogin'; + res.status(401).json(_resp_json); + } + } + else { + _resp_json.result = "fail"; + _resp_json.reason = 'Bad Request'; + res.status(400).json(_resp_json); + } + } + catch(error) { + _resp_json.result = "fail"; + _resp_json.reason = error.message; + res.status(500).json(_resp_json); + } } -const clsChangeCtr = (req, res) => { - res.status(200).json({ message: 'This is the auth/update/clsch endpoint!' }); -} - -module.exports = { updateCtr, clsChangeCtr }; \ No newline at end of file +module.exports = updateCtr; \ No newline at end of file diff --git a/src/models/postgre_SQL.js b/src/models/postgre_SQL.js index d40ffc6..b6af784 100644 --- a/src/models/postgre_SQL.js +++ b/src/models/postgre_SQL.js @@ -70,157 +70,8 @@ class PostgreSQL_Helper { console.log(err); }) } - //#region ACCOUNT - async Query_ACCOUNTS() { - try { - let accounts_query = `SELECT * FROM public."VKR_ACCOUNT"`; - return await this.pool.query(accounts_query); - } - catch(err) { - return Promise.reject(err); - } - } - async Query_ACCOUNT_COUNT() { - try { - let count_query = `SELECT COUNT(*) FROM public."VKR_ACCOUNT"`; - return await this.pool.query(count_query); - } - catch(err) { - return Promise.reject(err); - } - } - async Query_ACCOUNT_GET(id) { - try { - let get_query = `SELECT * FROM public."VKR_ACCOUNT" WHERE id='${id}'`; - return await this.pool.query(get_query); - } - catch(err) { - return Promise.reject(err); - } - } - async Query_ACCOUNT_CHECK(id) { - try { - let check_query = `SELECT COUNT(*) FROM public."VKR_ACCOUNT" WHERE id='${id}'`; - return await this.pool.query(check_query); - } - catch(err) { - return Promise.reject(err); - } - } - async Query_ACCOUNT_ADD(data) { - try { - let columns = [ - 'id', 'pwd', 'name', 'email', 'mobile', - '"birthDate"', '"orgName"', '"orgDepart"', - '"orgRole"', '"desc"', '"authorityType"', '"mdfDate"' - ]; - let column_info = `${columns.join(', ')}`; - let values = - `'${data.id}', '${data.pwd}', '${data.name}','${data.email}','${data.mobile}',\ - '${data.birthDate}','${data.orgName}', '${data.orgDepart}',\ - '${data.orgRole}', '${data.desc}', '${data.authorityType}'`; - - let add_query = - `INSERT INTO public."VKR_ACCOUNT"(${column_info}) VALUES (${values}, CURRENT_TIMESTAMP)`; - return await this.pool.query(add_query); - } - catch(err) { - return Promise.reject(err); - } - } - async Query_ACCOUNT_DELETE(id) { - try { - let delete_query = `DELETE FROM public."VKR_ACCOUNT" WHERE id='${id}'`; - return await this.pool.query(delete_query); - } - catch(err) { - return Promise.reject(err); - } - } - async Query_ACCOUNT_UPDATE(data) { - try { - let columns = [ - `id='${data.id}'`, `pwd='${data.pwd}'`, `name='${data.name}'`, - `email='${data.email}'`, `mobile='${data.mobile}'`, - `"birthDate"='${data.birthDate}'`, `"orgName"='${data.orgName}'`, `"orgDepart"='${data.orgDepart}'`, - `"orgRole"='${data.orgRole}'`, `"desc"='${data.desc}'`, `"authorityType"='${data.authorityType}'`, - '"mdfDate"=CURRENT_TIMESTAMP' - ]; - let column_info = `${columns.join(', ')}`; - let update_query = ` - UPDATE public."VKR_ACCOUNT" \ - SET ${column_info} \ - WHERE id = '${data.id}' RETURNING *`; - return this.pool.query(update_query); - } - catch(err) { - return Promise.reject(err); - } - } - async Query_ACCOUNT_SEARCH(data) { - try { - const offset = (Number(data.page) - 1) * Number(data.limit); // OFFSET 계산 - let _pre_query = this.pool.query(` - SELECT COUNT(*) FROM public."VKR_ACCOUNT" - ${data.where} - `).then( - function(query_res) { - return Number(query_res.rows[0].count); - } - ).catch(function (err) { - throw err; - }); - - const _pre_count = await Promise.race([_pre_query]); - - const totalRows = _pre_count; - const totalPages = Math.ceil(totalRows / Number(data.limit)); // 전체 페이지 수 계산 - - const select_query = ` - SELECT "id", "name","authorityType","orgName","orgDepart","orgRole", "mobile" - FROM public."VKR_ACCOUNT" - ${data.where} - ORDER BY "${(data.sort == "CREATE_AT") ? "creDate" : "name"}" ${data.order} - LIMIT ${data.limit} OFFSET ${offset} - `; - const _pre_select = await Promise.race([this.pool.query(select_query)]); - - return { - result_val : { - data: _pre_select.rows, - currentPage: Number(data.page), - totalPages: totalPages, - totalCount: totalRows - }, - row_count:_pre_select.rowCount - }; - } - catch(err) { - return Promise.reject(err); - } - } - async Query_ACCOUNT_IDPW(id) { - try { - let idpwQuery = `SELECT * FROM public."VKR_ACCOUNT" WHERE id='${id}'`; - return await this.pool.query(idpwQuery); - } - catch(err) { - return Promise.reject(err); - } - } - async Query_TEST() { - try { - let accounts_query = `SELECT * FROM public.member`; - return await this.pool.query(accounts_query); - } - catch(err) { - return Promise.reject(err); - } - } - //#endregion - - //#region AUTH Query + //#region AUTH Query ======================================================== AUTH async Query_AUTH_IDCHECK(id) { try { let check_query = `SELECT COUNT(*) FROM public.member WHERE id='${id}'`; @@ -258,8 +109,8 @@ class PostgreSQL_Helper { } async Query_AUTH_CHECK_LOGIN(id) { try { - let delete_query = `SELECT id, pw, "isApprove" FROM public.member WHERE id='${id}'`; - return await this.pool.query(delete_query); + let select_query = `SELECT id, pw, "isApprove", "cls" FROM public.member WHERE id='${id}'`; + return await this.pool.query(select_query); } catch(err) { return Promise.reject(err); @@ -274,6 +125,105 @@ class PostgreSQL_Helper { return Promise.reject(err); } } + async Query_AUTH_APPROVE(id, bApprove=false) { // true or false + try { + // let update_query = `update name, "desc" FROM public.member`; + let update_query = + `UPDATE public.member SET "isApprove"=${bApprove} WHERE id='${id}'`; + return await this.pool.query(update_query); + } + catch(err) { + return Promise.reject(err); + } + } + async Query_AUTH_PENDING() { + try { + let select_query = `SELECT id, name, pos, "isApprove", cls FROM public.member where "isApprove"=false`; + return await this.pool.query(select_query); + } + catch(err) { + return Promise.reject(err); + } + } + async Query_AUTH_GET(id) { + try { + let get_query = `SELECT id, name, pos, cls, "isApprove", "creDate", "mdfDate" FROM public.member WHERE id='${id}'`; + return await this.pool.query(get_query); + } + catch(err) { + return Promise.reject(err); + } + } + async Query_AUTH_GETID_ALL(id) { + try { + let get_query = `SELECT * FROM public.member WHERE id='${id}'`; + return await this.pool.query(get_query); + } + catch(err) { + return Promise.reject(err); + } + } + async Query_AUTH_UPDATE(id, set_context) { + try { + let update_query = + `UPDATE public.member ${set_context} WHERE id='${id}'`; + return await this.pool.query(update_query); + } + catch(err) { + return Promise.reject(err); + } + } + async Query_AUTH_SEARCH(data) { + try { + const offset = (Number(data.page) - 1) * Number(data.limit); // OFFSET 계산 + + let _pre_query = this.pool.query(` + SELECT COUNT(*) FROM public.member + ${data.where} + `).then( + function(query_res) { + return Number(query_res.rows[0].count); + } + ).catch(function (err) { + throw err; + }); + + const _pre_count = await Promise.race([_pre_query]); + + const totalRows = _pre_count; + const totalPages = Math.ceil(totalRows / Number(data.limit)); // 전체 페이지 수 계산 + + let orderBy = 'ORDER BY '; + if (data.sort == "CREATE_AT") { + orderBy += `"creDate" ${data.order}`; + } + else if(data.sort == "UPDATE_AT") { + orderBy += `"mdfDate" ${data.order}`; + } + else { //NAME_AT + orderBy += `"name" ${data.order}`; + } + + const select_query = `SELECT "id", "name", "pos", "cls", "isApprove" + FROM public.member + ${data.where} ${orderBy} + LIMIT ${data.limit} OFFSET ${offset}`; + const _pre_select = await Promise.race([this.pool.query(select_query)]); + + return { + result_val : { + data: _pre_select.rows, + currentPage: Number(data.page), + totalPages: totalPages, + totalCount: totalRows + }, + row_count:_pre_select.rowCount + }; + } + catch(err) { + return Promise.reject(err); + } + } //#endregion //#region EVENT & EVENT LOG diff --git a/src/models/userAuthController.js b/src/models/userAuthController.js index 5e95f89..b34d5ed 100644 --- a/src/models/userAuthController.js +++ b/src/models/userAuthController.js @@ -15,6 +15,9 @@ class UserAuthController { if (parse_cookie) ret_id = parse_cookie.id; return ret_id; } + get_cookie_info(req) { + return this._parseJwt(req.cookies[this._config.cookie_name]); + } _parseJwt(token) { const base64Url = token.split('.')[1]; // payload 부분 const base64 = base64Url.replace(/-/g, '+').replace(/_/g, '/'); @@ -49,7 +52,8 @@ class UserAuthController { return this._jwt.sign( { id: user.id, - pw: user.pw + pw: user.pw, + cls: user.cls }, this._secret_key, { @@ -57,41 +61,51 @@ class UserAuthController { } ); } - jwtTokenAuthentication(req, res, success, error) { - try { - let _cookie_token = req.cookies[this._config.cookie_name]; - if (_cookie_token != undefined) { - console.log('요청한 토큰 ', _cookie_token); - this._jwt.verify(_cookie_token, this._secret_key, (err, user) => { - if (err) { - if (err.name === 'TokenExpiredError') { - err.message = '토큰 만료'; - err.statusCode = 401; + jwtTokenAuthentication(req, res) { + let checkJwTProm = new Promise((resolve, reject) => { + try { + let _cookie_token = req.cookies[this._config.cookie_name]; + if (_cookie_token != undefined) { + console.log('요청한 토큰 ', _cookie_token); + this._jwt.verify(_cookie_token, this._secret_key, (err, user) => { + if (err) { + if (err.name === 'TokenExpiredError') { + err.message = '토큰 만료'; + err.statusCode = 401; + } + else { + err.message = '유효하지 않은 토큰'; + err.statusCode = 403; + } + // if (error) error(err); + reject(err); } else { - err.message = '유효하지 않은 토큰'; - err.statusCode = 403; + //token + let refresh_token = this.generateJWTToken(user); + this.refresh_cookie_token(res, refresh_token); + // if (success) success(); + let resultTk = { + userInfo: user + } + resolve(resultTk); } - if (error) error(err); - } - else { - //token - let refresh_token = this.generateJWTToken(user); - this.refresh_cookie_token(res, refresh_token); - if (success) success(); - } - }); + }); + } + else { + // 토큰 없어도 사용할 수 있도록 임시 오픈 + // if (success) success(); + throw new Error("유효하지 않은 토큰"); + } } - else { - // 토큰 없어도 사용할 수 있도록 임시 오픈 - // if (success) success(); - throw new Error("유효하지 않은 토큰"); + catch (err) { + err.statusCode = 403; + // if (error) error(err); + reject(err); } - } - catch(err) { - err.statusCode = 403; - if (error) error(err); - } + }) + + return checkJwTProm; } } diff --git a/src/routes/authRoutes.js b/src/routes/authRoutes.js index 3e66eb6..cc7858e 100644 --- a/src/routes/authRoutes.js +++ b/src/routes/authRoutes.js @@ -12,18 +12,19 @@ crouter.POST(ar, '/create', authController.create) crouter.POST(ar, '/login', authController.login) //GET -crouter.GET(ar, '/delete', authController.delete) crouter.GET(ar, '/get', authController.get) crouter.GET(ar, '/logout', authController.logout) crouter.GET(ar, '/search', authController.search) crouter.GET(ar, '/roles', authController.roles) -crouter.GET(ar, '/pending', authController.pendings) +crouter.GET(ar, '/pendings', authController.pendings) //PATCH crouter.PATCH(ar, '/update', authController.update) -crouter.PATCH(ar, '/update/clsch', authController.clsChange) crouter.PATCH(ar, '/approve', authController.approve) +//DELETE +crouter.DELETE(ar, '/delete', authController.delete) + // /auth/update/infoch(name, pw change) // /auth/update/clsch // /auth/update/posch diff --git a/src/utils/Global_TP.js b/src/utils/Global_TP.js index aa67903..de886b0 100644 --- a/src/utils/Global_TP.js +++ b/src/utils/Global_TP.js @@ -16,6 +16,26 @@ class Global_TP { if (val == undefined || !(val instanceof Date) || isNaN(val)) return false; return true; } + BOOL_VALIDER(val) { + if (val == undefined || !(typeof val === "boolean")) { + if (typeof val === "string") { + const lower = val.toLowerCase().trim(); + if (lower == 'true' || lower == 'false') return true; + } + return false; + } + return true; + } + TO_BOOLEAN(val) { + if (typeof val === "boolean") return val; + if (typeof val === "string") { + const lower = val.toLowerCase().trim(); + if (lower === "true") return true; + if (lower === "false") return false; + } + + return Boolean(val); + } GET_CURRENTDATE() { const date = new Date(); // 현재 날짜 및 시간 객체 생성