场景描述:有权限的路由表
朋友问了我一个问题,他在做权限相关的开发,需要把本地的路由表根据服务端返回的权限表做一个过滤,返回过滤后的路由表。 问我应该如何去写。
路由表和权限表如下:
//路由:
const routes = [
{
name: 'page1',
auth: 'auth1',
children: [
{
name: 'child-page1',
auth: 'child-auth1',
children: [
{
name: 'child-child-page1',
auth: 'child-child-auth1'
}
]
}
]
},
{
name: 'page2',
auth: 'auth2',
children: [
{
name: 'child-page2',
auth: 'child-auth2'
}
]
},
{
name: 'page3',
auth: 'auth3'
}
];
//权限:
const auths = [
{
auth: 'auth1',
children: [
{
auth: 'child-auth1',
children: [
{
auth: 'child-child-auth1'
}
]
}
]
},
{
auth: 'auth3'
}
];
处理过程:递归遍历路由数组,递归遍历权限数组
我想了一下,权限表和路由表是两个数组,保存的对象都是树形的对象,整个过程需要遍历路由数组,然后遍历路由数组的过程中通过遍历权限的数组来过滤。
整个过程中深层遍历的过程是需要复用的,于是我把这个遍历过程封装了一下。
const deepTraversal = (func) => {
const traversal = (obj) => {
func(obj);
if (obj.children) {
obj.children.forEach((item) => {traversal(item)});
}
}
return traversal;
}
使用方式如下:
// 遍历路由数组
deepTraversal((obj) => {
console.log('路由:' + obj.name);
})(routes);
接下来的工作就剩下遍历路由数组的过程中进行过滤,把过滤后的路由保存到另一个数组中,是否过滤通过遍历权限数组来决定。
const filteredRoute = [];
routes.forEach(route => {
deepTraversal((routeItem) => {
if (hasAuth(routeItem.auth)) {
filteredRoute.push(routeItem);
}
})(route)
})
console.log(filteredRoute);
遍历routes过程中过滤条件hasAuth如下:
const hasAuth = (targetAuth) => {
let isContain = false;
auths.forEach((auth) => {
deepTraversal((authItem) => {
if (authItem.auth === targetAuth) {
isContain = true;
}
})(auth);
})
return isContain;
}
过滤出的数组就是有权限的路由数组了。
总结
可复用的递归遍历过程:树形对象的遍历过程是可以复用的,通过高阶函数把遍历过程中的操作以参数传入,可以用来遍历、查找、复制等。