permission.js 8.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259
  1. import auth from "/src/plugins/auth";
  2. import router, { constantRoutes, dynamicRoutes } from "/src/router";
  3. import { getRouters } from "/src/api/menu";
  4. import Layout from "/src/layout/index";
  5. import ParentView from "/src/components/ParentView";
  6. import InnerLink from "/src/layout/components/InnerLink";
  7. // 匹配views里面所有的.vue文件
  8. const modules = import.meta.glob("./../../views/**/*.vue");
  9. const usePermissionStore = defineStore("permission_sd", {
  10. state: () => ({
  11. routes: [],
  12. addRoutes: [],
  13. defaultRoutes: [],
  14. topbarRouters: [],
  15. sidebarRouters: [],
  16. }),
  17. actions: {
  18. setRoutes(routes) {
  19. this.addRoutes = routes;
  20. this.routes = constantRoutes.concat(routes);
  21. },
  22. setDefaultRoutes(routes) {
  23. this.defaultRoutes = constantRoutes.concat(routes);
  24. },
  25. setTopbarRoutes(routes) {
  26. this.topbarRouters = routes;
  27. },
  28. setSidebarRouters(routes) {
  29. this.sidebarRouters = routes;
  30. },
  31. generateRoutes(roles) {
  32. return new Promise((resolve) => {
  33. // 向后端请求路由数据
  34. getRouters().then((res) => {
  35. if (roles.user.userId === "1699598709941104641") {
  36. res.data[0].children[7].children = res.data[0].children[7].children.concat([
  37. {
  38. type: 1,
  39. name: "Distribution-of-goods",
  40. path: "distribution-of-goods",
  41. hidden: false,
  42. component: "group/data-board/distribution-of-goods/index",
  43. meta: {
  44. title: "配货看板",
  45. icon: "#",
  46. noCache: false,
  47. link: null,
  48. },
  49. },
  50. {
  51. type: 1,
  52. name: "Daily-board",
  53. path: "daily-board",
  54. hidden: false,
  55. component: "group/data-board/daily-board/index",
  56. meta: {
  57. title: "每日看板",
  58. icon: "#",
  59. noCache: false,
  60. link: null,
  61. },
  62. },
  63. {
  64. type: 1,
  65. name: "Bom-quoted-price",
  66. path: "bom-quoted-price",
  67. hidden: false,
  68. component: "group/data-board/quoted-price/index",
  69. meta: {
  70. title: "BOM报价看板",
  71. icon: "#",
  72. noCache: false,
  73. link: null,
  74. },
  75. },
  76. {
  77. type: 1,
  78. name: "Sku-quoted-price",
  79. path: "sku-quoted-price",
  80. hidden: false,
  81. component: "group/data-board/sku-quoted-price/index",
  82. meta: {
  83. title: "SKU报价看板",
  84. icon: "#",
  85. noCache: false,
  86. link: null,
  87. },
  88. },
  89. {
  90. type: 1,
  91. name: "Turnover-rate",
  92. path: "turnover-rate",
  93. hidden: false,
  94. component: "group/data-board/turnover-rate/index",
  95. meta: {
  96. title: "周转率",
  97. icon: "#",
  98. noCache: false,
  99. link: null,
  100. },
  101. },
  102. {
  103. type: 1,
  104. name: "Subsidiary-sales-volume",
  105. path: "subsidiary-sales-volume",
  106. hidden: false,
  107. component: "group/data-board/subsidiary-sales-volume/index",
  108. meta: {
  109. title: "事业部销量看板",
  110. icon: "#",
  111. noCache: false,
  112. link: null,
  113. },
  114. },
  115. {
  116. type: 1,
  117. name: "Safety-stock",
  118. path: "safety-stock",
  119. hidden: false,
  120. component: "group/data-board/safety-stock/index",
  121. meta: {
  122. title: "成品安全库存看板",
  123. icon: "#",
  124. noCache: false,
  125. link: null,
  126. },
  127. },
  128. {
  129. type: 1,
  130. name: "Sales-volume",
  131. path: "sales-volume",
  132. hidden: false,
  133. component: "group/data-board/sales-volume/index",
  134. meta: {
  135. title: "三十天销量看板",
  136. icon: "#",
  137. noCache: false,
  138. link: null,
  139. },
  140. },
  141. {
  142. type: 1,
  143. name: "Calculator",
  144. path: "calculator",
  145. hidden: false,
  146. component: "group/BOM/calculator/index",
  147. meta: {
  148. title: "裸垫价格计算器",
  149. icon: "#",
  150. noCache: false,
  151. link: null,
  152. },
  153. },
  154. ]);
  155. }
  156. const sdata = JSON.parse(JSON.stringify(res.data));
  157. const rdata = JSON.parse(JSON.stringify(res.data));
  158. const defaultData = JSON.parse(JSON.stringify(res.data));
  159. const sidebarRoutes = filterAsyncRouter(sdata);
  160. const rewriteRoutes = filterAsyncRouter(rdata, false, true);
  161. const defaultRoutes = filterAsyncRouter(defaultData);
  162. const asyncRoutes = filterDynamicRoutes(dynamicRoutes);
  163. asyncRoutes.forEach((route) => {
  164. router.addRoute(route);
  165. });
  166. this.setRoutes(rewriteRoutes);
  167. this.setSidebarRouters(constantRoutes.concat(sidebarRoutes));
  168. this.setDefaultRoutes(sidebarRoutes);
  169. this.setTopbarRoutes(defaultRoutes);
  170. resolve(rewriteRoutes);
  171. });
  172. });
  173. },
  174. },
  175. });
  176. // 遍历后台传来的路由字符串,转换为组件对象
  177. function filterAsyncRouter(asyncRouterMap, lastRouter = false, type = false) {
  178. return asyncRouterMap.filter((route) => {
  179. if (type && route.children) {
  180. route.children = filterChildren(route.children);
  181. }
  182. if (route.component) {
  183. // Layout ParentView 组件特殊处理
  184. if (route.component === "Layout") {
  185. route.component = Layout;
  186. } else if (route.component === "ParentView") {
  187. route.component = ParentView;
  188. } else if (route.component === "InnerLink") {
  189. route.component = InnerLink;
  190. } else {
  191. route.component = loadView(route.component);
  192. }
  193. }
  194. if (route.children != null && route.children && route.children.length) {
  195. route.children = filterAsyncRouter(route.children, route, type);
  196. } else {
  197. delete route["children"];
  198. delete route["redirect"];
  199. }
  200. return true;
  201. });
  202. }
  203. function filterChildren(childrenMap, lastRouter = false) {
  204. var children = [];
  205. childrenMap.forEach((el, index) => {
  206. if (el.children && el.children.length) {
  207. if (el.component === "ParentView" && !lastRouter) {
  208. el.children.forEach((c) => {
  209. c.path = el.path + "/" + c.path;
  210. if (c.children && c.children.length) {
  211. children = children.concat(filterChildren(c.children, c));
  212. return;
  213. }
  214. children.push(c);
  215. });
  216. return;
  217. }
  218. }
  219. if (lastRouter) {
  220. el.path = lastRouter.path + "/" + el.path;
  221. }
  222. children = children.concat(el);
  223. });
  224. return children;
  225. }
  226. // 动态路由遍历,验证是否具备权限
  227. export function filterDynamicRoutes(routes) {
  228. const res = [];
  229. routes.forEach((route) => {
  230. if (route.permissions) {
  231. if (auth.hasPermiOr(route.permissions)) {
  232. res.push(route);
  233. }
  234. } else if (route.roles) {
  235. if (auth.hasRoleOr(route.roles)) {
  236. res.push(route);
  237. }
  238. }
  239. });
  240. return res;
  241. }
  242. export const loadView = (view) => {
  243. let res;
  244. for (const path in modules) {
  245. const dir = path.split("views/")[1].split(".vue")[0];
  246. if (dir === view) {
  247. res = () => modules[path]();
  248. }
  249. }
  250. return res;
  251. };
  252. export default usePermissionStore;