鍓嶈█馃憠馃摎VbenAdmin椤圭洰鍒嗘瀽涓庡疄璺点€傛湰鏂囨秹鍙婅鑹叉潈闄愪互澶栫殑鏇村鍐呭锛堣矾鐢辩浉鍏筹級锛屽叿浣撳姛鑳藉疄鐜板皢鍦ㄥ悗闈㈢殑涓撻涓缁嗚璁恒€備负浜嗘洿濂界殑鐞嗚В鏈枃鍐呭锛岃鍏堥槄璇诲畼鏂规枃妗?Permissions銆俻ermission.ts瑙掕壊鏉冮檺鏂囦欢src\store\modules\permission.ts澹版槑瀵煎嚭涓€涓猻tore瀹炰緥usePermissionStore鍜屼竴涓柟娉晆sePermissionStoreWithOut()鐢ㄤ簬鍦ㄤ笉浣跨敤璁剧疆缁勪欢鏃朵娇鐢ㄣ€?/瑙掕壊鏉冮檺淇℃伅瀛樺偍exportconstusePermissionStore=defineStore({id:'app-permission',state:{/*...*/},getters:{/*...*/}actions:{/*...*/}});exportfunctionusePermissionStoreWithOut(){returnusePermissionStoreWithOut(store);}State/Getter鐘舵€佸璞″畾涔夋潈闄愮爜鍒楄〃锛屾槸鍚﹀姩鎬佹坊鍔犺矾鐢憋紝鑿滃崟鏈€鍚庢洿鏂版椂闂达紝鍚庡彴瑙掕壊鏉冮檺鑿滃崟鍒楄〃锛屼互鍙婅鑹叉潈闄愯彍鍗曠殑鍓嶇鍒楄〃銆傚悓鏃舵彁渚涗簡鐩稿簲鐨刧etter鏉ヨ幏鍙栫姸鎬佸€笺€?/鏉冮檺鐘舵€佹帴鍙ermissionState{permCodeList:string[]|鏁板瓧[];//鏉冮檺鐮佸垪琛╥sDynamicAddedRoute:boolean;//鏄惁鍔ㄦ€佹坊鍔犺矾鐢眑astBuildMenuTime:number;//鑿滃崟鏈€鍚庢洿鏂版椂闂碽ackMenuList:Menu[];//鍚庡彴瑙掕壊鏉冮檺鑿滃崟鍒楄〃frontMenuList:Menu[];//鍓嶇瑙掕壊鏉冮檺鑿滃崟鍒楄〃}//鐘舵€佸畾涔夊拰鍒濆鍖栫姸鎬?():PermissionState=>({permCodeList:[],isDynamicAddedRoute:false,lastBuildMenuTime:0,backMenuList:[],frontMenuList:[],}),getters:{getPermCodeList():瀛楃涓瞇]|number[]{杩斿洖this.permCodeList;//鑾峰彇鏉冮檺鐮佸垪琛▆,getBackMenuList():Menu[]{returnthis.backMenuList;//鑾峰彇鍚庣瑙掕壊鏉冮檺鑿滃崟鍒楄〃},getFrontMenuList():Menu[]{returnthis.frontMenuList;//鑾峰彇鍓嶇瑙掕壊鏉冮檺鑿滃崟鍒楄〃},getLastBuildMenuTime():number{returnthis.lastBuildMenuTime;//鑾峰彇鑿滃崟鐨勬渶鍚庢洿鏂版椂闂磢,getIsDynamicAddedRoute():boolean{returnthis.isDynamicAddedRoute;//鑾峰彇鏄惁鍔ㄦ€佹坊鍔犺矾鐢眪,},Actions涓嬮潰鐨勬柟娉曠敤浜庢洿鏂扮姸鎬佸睘鎬с€?/鏇存柊灞炴€ermCodeListsetPermCodeList(codeList:string[]){this.permCodeList=codeList;},//鏇存柊灞炴€ackMenuListsetBackMenuList(list:Menu[]){this.backMenuList=list;list?.length>0&&this.setLastBuildMenuTime();//璁板綍鑿滃崟鐨勬渶鍚庢洿鏂版椂闂磢,//鏇存柊灞炴€rontMenuListsetFrontMenuList(list:Menu[]){this.frontMenuList=list;},//鏇存柊灞炴€astBuildMenuTimesetLastBuildMenuTime(){this.lastBuildMenuTime=newDate().鑾峰彇鏃堕棿锛堬級锛?/琛ㄧず鏃堕棿鐨勫€硷紙浠ユ绉掍负鍗曚綅锛墋,//鏇存柊灞炴€sDynamicAddedRoutesetDynamicAddedRoute(added:boolean){this.isDynamicAddedRoute=added;},//閲嶇疆鐘舵€佸睘鎬esetState():void{this.isDynamicAddedRoute=false;this.permCodeList=[];this.backMenuList=[];this.lastBuildMenuTime=0;}锛屾柟娉昪hangePermissionCode妯℃嫙鍚庡彴鑾峰彇鐢ㄦ埛鏉冮檺鐮侊紝甯哥敤浜庡悗鍙版潈闄愭柟寮忚幏鍙栫敤鎴锋潈闄愮爜銆傞」鐩娇鐢ㄦ湰鍦癕ock鏈嶅姟妯℃嫙銆俛syncchangePermissionCode(){constcodeList=awaitgetPermCode();this.setPermCodeList(codeList);},//src\api\sys\user.tsenumApi{GetPermCode='/getPermCode',}瀵煎嚭鍑芥暟getPermCode(){returndefHttp.get({url:Api.GetPermCode});}浣跨敤鐨勬ā鎷熸帴鍙e拰妯℃嫙鏁版嵁銆?/mock\sys\user.ts{url:'/basic-api/getPermCode',timeout:200,method:'get',response:(request:requestParams)=>{//...constcheckUser=createFakeUserList().find((item)=>item.token===token);constcodeList=fakeCodeList[checkUser.userId];//...杩斿洖缁撴灉鎴愬姛锛堜唬鐮佸垪琛級锛泒,},constfakeCodeList:any={'1':['1000','3000','5000'],'2':['2000','4000','6000'],};鍔ㄦ€佽矾鐢?鏉冮檺杩囨护鏂规硶buildRoutesAction鐢ㄤ簬鍔ㄦ€佽矾鐢卞拰User鏉冮檺杩囨护锛屼唬鐮侀€昏緫缁撴瀯濡備笅锛歛syncbuildRoutesAction():Promise{const{t}=useI18n();//鍥介檯鍖朿onstuserStore=useUserStore();//鐢ㄦ埛淇℃伅瀛樺偍constappStore=useAppStoreWithOut();//椤圭洰閰嶇疆淇℃伅瀛樺偍letroutes:AppRouteRecordRaw[]=[];//鐢ㄦ埛瑙掕壊鍒楄〃constroleList=toRaw(userStore.getRoleList)||[];//璁块棶鏉冮檺妯″紡const{permissionMode=projectSetting.permissionMode}=appStore.getProjectConfig;//鍩轰簬瑙掕壊鐨勮繃婊ゆ柟娉昪onstrouteFilter=(route:AppRouteRecordRaw)=>{/*...*/};//鍩轰簬ignoreRoute灞炴€ц繃婊ゅ櫒constrouteRemoveIgnoreFilter=(route:AppRouteRecordRaw)=>{/*...*/};//涓嶅悓鏉冮檺妯″紡澶勭悊閫昏緫寮€鍏?permissionMode){//鍓嶇妯″紡鎺у埗锛堣彍鍗曞拰璺敱鍒嗗埆閰嶇疆锛塩asePermissionModeEnum.ROLE:/*...*///鍓嶇妯″紡鎺у埗锛堣矾鐢遍厤缃嚜鍔ㄧ敓鎴愯彍鍗曪級casePermissionModeEnum.ROUTE_MAPPING:/*...*///鍚庡彴妯″紡鎺у埗casePermissionModeEnum.BACK:/*...*/}routes.push(ERROR_LOG_ROUTE);//娣诲姞`errorloglist`椤甸潰璺敱//鏍规嵁璁剧疆鐨刪ome璺緞锛屼慨姝outes涓殑璇嶇紑鏍囪锛堜慨澶峢ome椤甸潰锛塩onstpatchHomeAffix=(routes:AppRouteRecordRaw[])=>{/*...*/};patchHomeAffix锛堣矾绾匡級锛涜繑鍥炶矾绾匡紱//杩斿洖璺敱鍒楄〃}锛岄〉闈⑩€滈敊璇棩蹇楀垪琛ㄢ€濊矾鐢卞湴鍧€/error-log/list锛屽姛鑳藉涓嬶細鏉冮檺妯″紡妗嗘灦鎻愪緵浜嗗畬鏁寸殑鍓嶅悗缁堢鏉冮檺绠$悊鏂规锛岄泦鎴愪簡涓夌鏉冮檺澶勭悊鏂瑰紡锛歊OLE閫氳繃鐢ㄦ埛瑙掕壊锛堝墠绔帶鍒讹級杩囨护鑿滃崟锛岃彍鍗曞拰璺敱鍒嗗埆閰嶇疆ROUTE_MAPPING閫氳繃鐢ㄦ埛瑙掕壊锛堝墠绔帶鍒讹級杩囨护鑿滃崟锛岃矾鐢遍厤缃嚜鍔ㄧ敓鎴愯彍鍗曘€侭ACK閫氳繃鍚庡彴鍔ㄦ€佺敓鎴愯矾鐢辫〃锛堝悗鍙版ā寮忔帶鍒讹級銆?/src\settings\projectSetting.ts//椤圭洰閰嶇疆constsetting:ProjectConfig={permissionMode:PermissionModeEnum.ROUTE_MAPPING,//鏉冮檺妯″紡榛樿鍓嶇妯″紡permissionCacheType:CacheTypeEnum.LOCAL,//鏉冮檺缂撳瓨瀛樻斁浣嶇疆瀛樻斁鍦╨ocalStorage榛樿//...}//src\enums\appEnum.ts//鏉冮檺妯″紡鏋氫妇exportenumPermissionModeEnum{ROLE='ROLE',//鍓嶇妯″紡锛堣彍鍗曡矾鐢卞垎绂伙級ROUTE_MAPPING='ROUTE_MAPPING',//鍓嶇妯″紡(鑿滃崟鐢辫矾鐢辩敓鎴?BACK='BACK',//鍚庣妯″紡}鍓嶇鏉冮檺妯″紡鍓嶇鏉冮檺妯″紡鎻愪緵浜嗕袱绉嶅鐞嗛€昏緫锛孯OLE鍜孯OUTE_MAPPING锛屼笅闈㈠垎鍒垎鏋愪竴涓嬩笅涓€涓€傜‖缂栫爜璺敱鐨勬潈闄愪細鍥哄畾鍦ㄥ墠绔紝鍙互鏌ョ湅鎸囧畾璺敱鐨勬潈闄愩€傜郴缁熷湪瀹氫箟璺敱璁板綍鏃舵寚瀹氫簡鍙闂鑹睷oleEnum.SUPER銆?/src\router\routes\modules\demo\permission.ts{璺緞锛?auth-pageA'锛屽悕绉帮細'FrontAuthPageA'锛岀粍浠讹細()=>import('/@/views/demo/permission/front/AuthPageA.vue'),meta:{title:t('routes.demo.permission.frontTestA'),roles:[RoleEnum.SUPER],},}锛岀郴缁熶娇鐢╩eta灞炴€х粰璺敱璁板綍闄勫姞鑷畾涔夋暟鎹紝瀹冨湪璺敱鍦板潃鍜屽鑸畧鍗笂閮藉彲浠ヨ闂€傝鏂规硶浣跨敤鐨勯厤缃睘鎬у涓嬶細exportinterfaceRouteMeta{//鍙闂殑瑙掕壊锛屼粎褰撴潈闄愭ā寮忎负Roleroles?:RoleEnum[];//鏄惁淇鏍囩璇嶇紑锛?boolean;//鑿滃崟鎺掑簭锛屽彧瀵圭涓€灞傛湁鏁坥rderNo?:number;//蹇界暐璺敱銆傜敤浜庣敓鎴愮浉搴旂殑鑿滃崟锛屽拷鐣OUTE_MAPPING鍜孊ACK鏉冮檺妯″紡涓嬬殑璺敱銆傚拷鐣ヨ矾绾匡紵锛氬竷灏斿€硷紱//...}ROLE鍒濆鍖栭€氱敤璺敱琛╝syncRoutes锛岃幏鍙栫敤鎴疯鑹插悗锛岄€氳繃瑙掕壊閬嶅巻璺敱琛紝鑾峰彇瑙掕壊鍙互璁块棶鐨勮矾鐢辫〃锛岀劧鍚庢牸寮忓寲锛岃浆鎹㈠绾outes杞崲涓轰簩绾ц矾鐢卞苟鏈€缁堣繑鍥炶矾鐢辫〃銆?/鍓嶇妯″紡鎺у埗锛堣彍鍗曞拰璺敱鍒嗗埆閰嶇疆锛塱mport{asyncRoutes}from'/@/router/routes';//...casePermissionModeEnum.ROLE://鏍规嵁瑙掕壊杩囨护璺敱=filter(asyncRoutes,璺敱杩囨护鍣?;routes=routes.filter(routeFilter);//灏嗗绾ц矾鐢辫浆鎹负浜岀骇璺敱routes=flatMultiLevelRoutes(routes);break;//src\router\routes\index.tsexportconstasyncRoutes=[PAGE_NOT_FOUND_ROUTE,...routeModuleList];鍦ㄨ矾鐢遍挬瀛愪腑鍔ㄦ€佸垽鏂紝璋冪敤鏂规硶杩斿洖鐢熸垚鐨勮矾鐢辫〃锛岀劧鍚庨€氳繃router.addRoutes娣诲姞鍒拌矾鐢卞疄渚嬩腑锛屽疄鐜版潈闄愮殑杩囨护銆?/src/router/guard/permissionGuard.tsconstroutes=awaitpermissionStore.buildRoutesAction();routes.forEach((route)=>{router.addRoute(routeasunknownasRouteRecordRaw);});//....routeFilter杩囨护鏂规硶routeFilter閫氳繃瑙掕壊閬嶅巻璺敱琛紝鑾峰彇瑙掕壊鍙互璁块棶鐨勮矾鐢辫〃銆俢onstuserStore=useUserStore();//鐢ㄦ埛淇℃伅瀛樺偍constroleList=toRaw(userStore.getRoleList)||[];//鐢ㄦ埛瑙掕壊鍒楄〃constrouteFilter=(route:AppRouteRecordRaw)=>{const{meta}=route;甯搁噺{瑙掕壊}=鍏億|{};濡傛灉锛堬紒瑙掕壊锛夎繑鍥炵湡锛涜繑鍥瀝oleList.some((role)=>roles.includes(role));};flatMultiLevelRoutes鏂规硶flatMultiLevelRoutes灏嗗绾ц矾鐢辫浆鎹负浜岀骇璺敱锛屼笅鍥炬槸鏈鐞嗙殑璺敱琛ㄤ俊鎭細涓嬪浘鏄牸寮忓寲鍚庣殑浜岀骇璺敱琛ㄤ俊鎭細ROUTE_MAPPINGROUTE_MAPPING鍜孯OLE閫昏緫鐩稿悓锛屼笉鍚屼箣澶勪細鑷姩鐢熸垚鏍规嵁璺嚎鐨勮彍鍗曘€?/鍓嶇妯″紡鎺у埗锛堣矾鐢遍厤缃嚜鍔ㄧ敓鎴愯彍鍗曪級casePermissionModeEnum.ROUTE_MAPPING://鏍规嵁瑙掕壊杩囨护璺敱routes=filter(asyncRoutes,routeFilter);routes=routes.filter(routeFilter);//閫氳繃璺敱杞崲鐢熸垚鑿滃崟constmenuList=transformRouteToMenu(routes,true);//鍒犻櫎灞炴€eta.ignoreRouterouteroutes=filter(routes,routeRemoveIgnoreFilter);routes=routes.filter(routeRemoveIgnoreFilter);menuList.sort((a,b)=>{return(a.meta?.orderNo||0)-(b.meta?.orderNo||0);});//閫氳繃璺敱杞崲鐢熸垚鑿滃崟this.setFrontMenuList(menuList);//灏嗗绾ц矾鐢辫浆鎹负涓ょ骇璺敱routes=flatMultiLevelRoutes(routes);浼戞伅;璋冪敤transformRouteToMenu鏂规硶灏嗚矾鐢辫浆鍖栦负鑿滃崟锛岃皟鐢ㄨ繃婊ゆ柟娉時outeRemoveIgnoreFilter蹇界暐璁剧疆浜唅gnoreRoute灞炴€х殑璺敱鑿滃崟銆俢onstrouteRemoveIgnoreFilter=(route:AppRouteRecordRaw)=>{const{meta}=route;const{ignoreRoute}=meta||{};杩斿洖锛乮gnoreRoute锛泒锛涚郴缁熺ず渚嬶紝璺敱涓嬩笉鍚岃矾寰勫弬鏁扮敓鎴愯彍鍗曘€?/src\router\routes\modules\demo\feat.ts{璺緞锛?testTab/:id'锛屽悕绉帮細'TestTab'锛岀粍浠讹細()=>import('/@/views/demo/feat/tab-params/index.vue'),meta:{hidePathForChildren:true,},children:[{path:'testTab/id1',name:'TestTab1',缁勪欢:()=>import('/@/views/demo/feat/tab-params/index.vue'),meta:{ignoreRoute:true,},},{path:'testTab/id2',name:'TestTab2',缁勪欢:()=>import('/@/views/demo/feat/tab-params/index.vue'),meta:{ignoreRoute:true,},},],},BACK鍚庣鏉冮檺鏂瑰紡绫讳技ROUTE_MAPPING閫昏緫澶勭悊锛屽彧鏄矾鐢辫〃datasource鏄粠鍚庡彴鑾峰彇鐨勮皟鐢ㄦ帴鍙c€?/鍚庡彴妯″紡鎺у埗妗堜緥PermissionModeEnum.BACK:letrouteList:AppRouteRecordRaw[]=[];//鑾峰彇鍚庡彴杩斿洖鐨勮彍鍗曢厤缃畉his.changePermissionCode();//妯℃嫙浠庡悗鍙拌幏鍙栨潈闄愮爜routeList=(awaitgetMenuList())asAppRouteRecordRaw[];//妯℃嫙浠庡悗鍙拌幏鍙栬彍鍗曚俊鎭?/鏍规嵁璺敱鍔ㄦ€佸紩鍏ョ浉鍏崇粍浠秗outeList=transformObjToRoute(routeList);//灏嗚矾鐢卞垪琛ㄨ浆鎹负鑿滃崟constbackMenuList=transformRouteToMenu(routeList);//璁剧疆鑿滃崟鍒楄〃this.setBackMenuList(backMenuList);//绉婚櫎灞炴€eta.ignoreRoute璺敱routeList=filter(routeList,routeRemoveIgnoreFilter);routeList=routeList.filter(routeRemoveIgnoreFilter);//灏嗗绾ц矾鐢辫浆鎹负浜岀骇璺敱routeList=flatMultiLevelRoutes(routeList);routes=[PAGE_NOT_FOUND_ROUTE,...routeList];浼戞伅;馃摎鍙傝€?鐩稿叧闃呰銆妑outelocationnormalized銆嬨€乿ue-router\銆奙eta閰嶇疆璇存槑銆嬨€乿vbin.cn\銆奃ate/getTime銆嬨€丮DN\銆妕oraw銆嬶紝濡傛灉鏈枃瀵规偍鏈夊府鍔╋紝璇峰叧娉ㄢ灂锛岀偣璧烉煈嶏紝鍜屼功绛锯瓙锛佹偍鐨勮鍙槸瀵规垜鏈€澶х殑鏀寔锛佹湰鏂囧凡鏀跺綍鍦ㄤ笓鏍忦煈囷紝鍙互鐩存帴鍏虫敞銆?/p>