import { createWebHistory, createRouter } from "vue-router"; import store from "./AppStore"; // 공통페이지 import Intro from "./user/intro/Intro.vue"; // 기업 import IntroduceSelectList from "./user/company/introduce/IntroduceSelectList.vue"; import Enroll from "./user/company/consulting/Enroll.vue"; // 관리자 import CommonSelectList from "./adm/boardManagement/template/commonTemplate/CommonSelectList.vue"; import CommonSelectListOne from "./adm/boardManagement/template/commonTemplate/CommonSelectListOne.vue"; const beforeRoutes = [ /* 메인화면 */ { path: "/", name: "Intro", component: Intro }, // 기업 { path: "/company", children: [ { path: "introduceSelectList.page", name: "IntroduceSelectList", component: IntroduceSelectList }, { path: "consulting.page", name: "Enroll", component: Enroll }, ], }, // 관리자 { path: "/adm", children: [ { path: "commonSelectListOne.page", name: "CommonSelectListOne", component: CommonSelectListOne }, { path: "commonSelectList.page", name: "CommonSelectList", component: CommonSelectList }, ], }, ]; import { findAll, accessCheck } from "../../resources/api/router"; import { save } from "../../resources/api/cntnStats"; // 라우터 정보 호출 async function fetchRoutes() { try { const res = await findAll(); if (res.status == 200) { const newRoutes = res.data.data.map(route => ({ path: route.pageCrs, name: route.contsEngNm, component: () => import(`${route.compnCrs}`), meta: { authrt: route.authrtList, typeId: route.contsId } })); return newRoutes; } } catch (error) { return []; } } // 접근 제어 확인 async function accessUrl(path) { try { const res = await accessCheck({ path: path }); if (res.status == 200) { return res.data.data; } } catch (error) { return false; } } // 사용자 권한과 라우터에 포함되어 있는 권한을 비교하여 최종 권한 추출 function mergeAuth(userRoles, routeMeta) { const result = { inqAuthrt: 'N', // 읽기 권한 regAuthrt: 'N', // 쓰기 권한 mdfcnAuthrt: 'N', // 수정 권한 delAuthrt: 'N', // 삭제 권한 fileDwnldAuthrt: 'N', // 파일 다운로드 권한 } if (!routeMeta || !routeMeta.authrt || routeMeta.authrt.length === 0) { return result; } routeMeta.authrt.forEach(auth => { if (userRoles.includes(auth.authrtCd)) { if (auth.inqAuthrt === 'Y') result.inqAuthrt = 'Y'; if (auth.regAuthrt === 'Y') result.regAuthrt = 'Y'; if (auth.mdfcnAuthrt === 'Y') result.mdfcnAuthrt = 'Y'; if (auth.delAuthrt === 'Y') result.delAuthrt = 'Y'; if (auth.fileDwnldAuthrt === 'Y') result.fileDwnldAuthrt = 'Y'; } }); return result; } // 통계 등록 async function cntnStatsSave(typeId, roles) { try { const cntnStats = { 'typeId': typeId, 'mbrAuthList': roles } await save(cntnStats); } catch (error) { } } // 권한 검증 function isValidRole() { const roles = store.state.roles; if (!Array.isArray(roles)) { store.commit("setStoreReset"); return false; } for (const role of roles) { if (typeof role !== 'object' || !role.hasOwnProperty('authority')) { store.commit("setStoreReset"); return false; } } return true; } export default async function createAppRouter() { const dynamicRoutes = await fetchRoutes(); // DB에 적재된 라우터 정보 호출 const newRoutes = beforeRoutes.concat(dynamicRoutes); // 기존 라우터 정보와 합치기 const AppRouter = createRouter({ history: createWebHistory(), routes: newRoutes, }); AppRouter.beforeEach(async (to, from, next) => { const routeExists = AppRouter.getRoutes().some(route => route.path === to.path || (route.name && route.name === to.name)); if (!routeExists) { next({ name: 'notfound' }); return; } // 접근 제어 확인(미확인 시 이전 페이지로 이동) const accesCheck = await accessUrl(to.path); const roleCheck = isValidRole(); if (!accesCheck || !roleCheck) { alert('접근이 불가합니다.\n관리자에게 문의하세요.'); next('/'); } // 경로에 따른 사용자 타입 설정 if (to.path === '/') { store.commit('setUserType', null) } else if (to.path.startsWith('/adm')) { store.commit('setUserType', 'adm'); } else if (to.path.startsWith('/company')) { store.commit('setUserType', 'company'); } else if (to.path.startsWith('/government')) { store.commit('setUserType', 'government'); } if (to.path === '/login.page') { store.commit('setPath', to.path); next(); return; } const isLogin = store.state.authorization; // 토큰 정보 호출(로그인 유무 확인) const mbrAuth = store.state.roles.map(auth => auth.authority); // 사용자 권한 정보 const pageAuth = mergeAuth(mbrAuth, to.meta); sessionStorage.setItem("redirect", to.fullPath); // 메인 페이지 or 기업 페이지 or 로그인 페이지 if (to.path === '/' || to.path.startsWith('/company/') || to.path.includes('/login.page') || to.path.startsWith('/cmmn/') || to.path.includes('/searchId.page') || to.path.includes('/resetPswd.page')) { let path = to.path; // 게시판일 경우 .page로 끝나는 경로가 있으므로 마지막 '/' 이전 경로로 설정 if (to.path.includes('BBS_MNG')) { const lastSlashIndex = to.path.lastIndexOf('/'); // 마지막 '/' 인덱스 path = to.path.substring(0, lastSlashIndex); // 마지막 '/' 이전 경로 } store.commit('setPath', path); store.commit('setPageAuth', pageAuth); if (path.includes('/main.page')) { await cntnStatsSave(null, mbrAuth); // 메인 페이지 접속 시 사용자 접속 통계 증가 } else if (path.startsWith('/company/')) { await cntnStatsSave(to.meta.typeId, mbrAuth); // 기업 페이지의 각 종류(게시판, 콘텐츠)에 맞는 통계 증가 } next(); } else if (isLogin) { // 로그인 상태이고, 권한이 허용인 경우 검사 // const hasAcc = true; const hasAcc = to.matched.some(record => { if (!record.meta.authrt) return false; return record.meta.authrt.some(auth => { // 경로별 권한 검사 if (to.path.includes('/list.page')) { // 목록 권한 검증 return mbrAuth.includes(auth.authrtCd) && auth.inqAuthrt === 'Y'; } else if (to.path.includes('/insert.page')) { // 등록 및 수정 권한 검증 return mbrAuth.includes(auth.authrtCd) && auth.regAuthrt === 'Y'; } else if (to.path.includes('/view.page')) { // 상세조회 권한 검증 return mbrAuth.includes(auth.authrtCd) && auth.inqAuthrt === 'Y'; } else if (to.path.includes('/main.page')) { // 메인 페이지 권한 검증 return mbrAuth.includes(auth.authrtCd) && auth.inqAuthrt === 'Y'; } else if (to.path.includes('/search.page')) { return mbrAuth.includes(auth.authrtCd) && auth.inqAuthrt === 'Y'; } else { return false; } }); }); // 권한이 있고 접근 가능한 경우 if (hasAcc) { if (to.path.includes('.page')) { const lastSlashIndex = to.path.lastIndexOf('/'); // 마지막 '/' 인덱스 const path = to.path.substring(0, lastSlashIndex); // 마지막 '/' 이전 경로 store.commit('setPath', path); } // 접속 통계 if (to.path.includes('/main.page')) { await cntnStatsSave(null, mbrAuth); // 메인 페이지 접속 시 사용자 접속 통계 증가 } else { await cntnStatsSave(to.meta.typeId, mbrAuth); // 그외에는 각 종류(게시판, 콘텐츠)에 맞는 통계 증가 } store.commit('setPageAuth', pageAuth); next(); // 권한이 없는 경우 이전 페이지 or / 이동 } else { alert('접근 권한이 없습니다.'); window.history.back(); // next(from.fullPath ? from.fullPath : '/'); } } else { // sessionStorage.setItem("redirect", to.fullPath); next({ path: "/login.page" }); } }); return AppRouter; }