权限管理「基于角色的访问控制(RBAC)」

Java3y

共 2746字,需浏览 6分钟

 ·

2020-01-10 23:22


本文公众号来源:编程新说作者:编程新说李新杰本文已收录至我的GitHub
很多时候,需要对一些事物进行控制,如一个房间,为了不让人随便进,通常会装一把锁,如果要想进入,你必须得有一把钥匙,且还得和这个锁匹配才行。

基于此做一个抽象,其实包含三方面内容:

1)一个是被控制的事物,通常就算资源。

2)一个是想访问这些资源的人所必须拥有的东西,通常就算凭证。

3)还有一个就是进行凭证和资源的匹配。


Web应用中的资源


网络时代绝大多数都是web应用。web应用的一大特点就是Client和Server。客户端发起一个请求,服务器就给出一个响应。

对客户端的要求只有一个,那就是要知道请求对应的URL。客户端请求不同的URL就可以得到不同的内容,或者反过来说,客户端为了得到不同的内容只要请求不同的URL即可。

这些内容可以认为是服务器开放给客户端的资源,所以站在客户端的角度,服务器上的资源就是由许多URL组成的,因为客户端只能通过URL的方式和服务器打交道。

URL可以说是一个底层本质的东西,它的上面会有很多不同的展现形式:

菜单可以对应URL

页面可以对应URL

按钮可以对应URL

Ajax可以对应URL

服务API可以对应URL

文件下载可以对应URL

静态文件css、js、images可以对应URL

这些就是通常我们见到的资源,它们就是要被控制访问的事物。


把凭证授给用户


凭证这个东西的作用,大家都很熟悉,就是可以用来证明一个事物的合法性。比如一个身份证可以证明你是一个合法公民。一张车票可以证明你是一个合法乘客。

但是对凭证的存在形式,其实并没有什么硬性规定,因为随着时间的推移,它是会变的,也就是说具有阶段性。

就拿锁来说,它的凭证以前是一把钥匙,后来变成一串数字密码,再后来变成一个指纹,现在又变成一张人脸或一个声纹,再往未来发展,可能就是一种意念了。

web应用中的资源就是URL,我们可以把这个URL直接作为凭证授予用户,只需把这些授予关系存储起来即可,说白了就是,哪个用户可以访问哪些URL。

或者也可以把这些URL进行等价变形,把变形后的产物授予用户,总之,只要能建立起合理的映射关系就行了。


角色出现的必然性


假如有一个新闻系统,为了让某人能顺利的发新闻,需要由技术人员授予她一大堆的URL。这样一个“简单”的事情中,就存在两个潜在的弊端。

一个是必须由技术人员来做,因为非技术人员可能连URL这个词都不知道是什么。一个是一大堆的URL,太多了,操作麻烦,还可能漏掉某个。

究竟由谁发新闻,这是业务和管理上的事情,不应该由技术来做,他们不做的原因是因为门槛太高,所以技术应该想办法来降低工作的门槛。

可能领导觉得现在的新闻发布人员工作很认真,于是让她去审核新闻了,又来了一个新的新闻发布人员。这下又要“折腾”技术人员了。

技术需要先把她的发布新闻URL去掉,授给她审核新闻的URL,然后再把发布新闻的URL授给新来的人员。可能过两天又来了一个新闻发布人员。

这可简直要了技术人员的“命”了,所以技术应该想办法来降低工作的繁琐性,绝对是利人又利己。

在计算机里,解决此类问题的一个“标准指导方针”就是,抽象和封装。抽象出一层来,把复杂的东西封装起来。

就是让不该看的人看不到他不该看的东西,只让他看到他该看到的东西。就像同一个事物在不同人眼里是不一样的。

一栋大楼,在设计人员眼里就是一堆图纸,在工程人员眼里就是一堆结构和承重计算的公式,在建筑工人眼里就是一堆钢筋和混凝土,在装修人员眼里就是毛坯房,在业主眼里就是他自己未来的家。

最终角色这个东西就是被抽象出来的一层,它起到过渡的作用,从这一层向下是技术人员负责的,从这一层向上是业务管理人员负责的。

技术人员预定义好一些角色,比如新闻发布员、新闻审核员,然后把和发布相关的所有URL授予发布员这个角色,把和审核相关的所有URL授予审核员这个角色。

剩下的工作就交给业务管理人员来做,他们把角色授予某个人,只需一步即可,也不涉及什么技术知识。这真是各管各的,两全其美。

其实这个角色就是上面提到的一堆URL的等价变形,最终起到的也是一个传递映射关系的桥梁作用。


凭证和资源的匹配方式


在持有凭证去访问资源的时候需要进行凭证和资源的匹配。就像进考场要看准考证、上车前要验票一样。

凭证的存在形式不同,匹配的方式也不同,如果是钥匙,需要机械匹配。如果是密码,需要相等性匹配。

如果是指纹、图像、声纹,需要的是概率性匹配,因为这些东西貌似无法相等,只有一个匹配度。

对于web应用的URL,只有用户访问时才需要匹配,我们就在请求必经的路上设置一到多道关卡进行拦截,常用的就是过滤器和拦截器。

在被拦截以后,从请求中解析出本次访问的URL,从当前登陆用户信息中拿到具有的角色和能访问的URL,然后按自己设定的一套逻辑去匹配。

如果匹配成功就放行,会自动进行后续处理。匹配不成功就禁止通行,告诉他不能通行的原因,结束本次访问。


基于角色的访问控制


其实上面讲的就是基于角色的访问控制的原理。原理很简单,如果没有特殊要求的话,实现也不难。

就是经典的五张表:

1)权限表,也称资源表,记录所有的资源URL。

2)角色表,记录所有的角色。

3)角色权限表,记录每个角色都能访问哪些权限。

4)用户表,记录所有用户。

5)用户角色表,记录每个用户被授予的角色。

按实际需求决定的部分:

1)一个用户是只能有一个角色,还是可以有多个,这个依托用户角色表即可实现。

2)角色之间是否可以继承,是单继承还是多继承,这个需要一个单独的角色继承表来存储。

两个特殊的事物:

1)一个是没有任何限制的公共资源,如js、css、images等,可以设置一个白名单,把它们放入其中,这些URL相当于“免检”。

2)一个特殊的用户,如超级管理员,这个需要在用户表进行标识,遇到它后直接放行,因为它也是“免检”。


是否选择现成的框架


常用的现成的框架就是Spring SecurityApache Shiro。它们属于上手不难,想用好却不简单的那种。

我觉得可以按以下情况来选择:

1)有专门团队或人员维护的,可以选择从零研发或基于框架的深度扩展。

2)没有专人负责,也不想麻烦的,建议不要用框架,应该自己写代码简单实现。

3)不怕麻烦的,爱研究的,可以选择框架,掌握使用方式,明白运行原理,看看底层源码。

总之,一定要做到可控,特别是自身或团队在条件不允许的情况下,千万别去捅马蜂窝。


欢迎加入交流群学习,备注加群说实话在这个群,哪怕您不说话,光看聊天记录,都能学到东西

两年呕心沥血的文章「面试题」「基础」「进阶」这里全都有!

300多篇原创技术文章加入交流群学习海量视频资源精美脑图面试题

长按扫码可关注获取 

在看和分享对我非常重要!

浏览 12
点赞
评论
收藏
分享

手机扫一扫分享

分享
举报
评论
图片
表情
推荐
点赞
评论
收藏
分享

手机扫一扫分享

分享
举报