nodejs acl的用户权限管理详解

2020-06-17 06:43:35易采站长站整理

] }
];

校检

这里是结合express做校检…结果发现acl自己提供的中间件太鸡肋了,这里就重写了一个。


function auth() {
return async function (req, res, next) {
let resource = req.baseUrl;
if (req.route) { // 正常在control中使用有route属性 但是使用app.use则不会有
resource = resource + req.route.path;
}
console.log('resource', resource);

// 容错 如果访问的是 /admin/sign/ 后面为 /符号认定也为过
if (resource[resource.length - 1] === '/') {
resource = resource.slice(0, -1);
}

let role = await acl.hasRole(req.session.userName, 'root');

if (role) {
return next();
}

let result = await acl.isAllowed(req.session.userName, resource, req.method.toLowerCase());
// if (!result) {
// let err = {
// errorCode: 401,
// message: '用户未授权访问',
// };
// return res.status(401).send(err.message);
// }
next();
};
}

有点要说明的是express.Router支持导出一个Router模块 再在app.use使用,但是如果你这样使用 app.use(‘/admin/user’,auth(), userRoute); 那么是在auth这个函数是获取不到 req.route 这个属性的。 因为acl对访问权限做的是强匹配,所以需要有一定的容错

登录的权限分配

result为数据库查询出来的用户信息,或者后台api返给的用户信息,这里的switch可以使用配置文件的形式,因为我这边本次项目只有三个权限,所以就在这里简单写了一下。


let roleName = 'normal';

switch (result.result.privilege) {
case 0:
roleName = 'admin';
break;
case 1:
roleName = 'normal';
break;
case 2:
roleName = 'member';
break;
}

if (result.result.name === 'Nathan') {
roleName = 'root';
}

req.session['role'] = roleName;
// req.session['role'] = 'root'; // test
acl.addUserRoles(result.result.name, roleName);
// acl.addUserRoles(result.result.name, 'root'); // test

pug页面中的渲染逻辑控制

在 express+pug中 app.locals.auth= async function(){} 这个写法在pug渲染的时候是不会得出最终结果的,因为pug是同步的,那么我如何控制当前页面或者说当前页面的按钮用户是否有权限展示出来, 这里通用的做法有

用户在登录的时候有一个路由表和组件表 然后在渲染的时候 根据这个表去渲染
在需要权限控制的地方,使用函数来判断用户是否有权限访问

我这里采用的是结局方案2.因为比较方便, 但是问题来了 express+pug是不支持异步的写法,而acl提供给我们的全是异步的, 因为时间原因,我没有去深究里面的判断,而是采用了一种耦合性比较高但是比较方便的判断方法.