文章目录
- casbin
- casbin工作原理——PERM
- 请求——Request
- 策略——Policy
- 匹配器——Matcher
- 效果——Effect
- Model语法
- Request定义
- Policy定义
- Policy effect定义
- Matchers定义
- 编辑器
- 例子1
- 例子2
- 例子3
- 例子4
- 例子5
- 例子6
- 例子7
- 例子8
- 例子9
casbin
Casbin是一个强大且高效的开源访问控制库,支持各种访问控制模型,用于在全局范围内执行授权。
casbin工作原理——PERM
在 Casbin 中, 访问控制模型被抽象为基于 PERM (Policy, Effect, Request, Matcher) 的一个文件。 因此,切换或升级项目的授权机制与修改配置一样简单。 您可以通过组合可用的模型来定制您自己的访问控制模型。
例如,您可以在一个model中结合RBAC角色和ABAC属性,并共享一组policy规则。
PERM模式由四个基础(政策、效果、请求、匹配)组成,描述了资源与用户之间的关系。
请求——Request
定义请求参数。基本请求是一个元组对象,至少需要主题(访问实体)、对象(访问资源) 和动作(访问方式)
例如,一个请求可能长这样: r={sub,obj,act}
它实际上定义了我们应该提供访问控制匹配功能的参数名称和顺序。
策略——Policy
定义访问策略模式。事实上,它是在政策规则文件中定义字段的名称和顺序。
例如: p={sub, obj, act}
或 p={sub, obj, act, eft}
注:如果未定义eft (policy result),则策略文件中的结果字段将不会被读取, 和匹配的策略结果将默认被允许。
匹配器——Matcher
匹配请求和政策的规则。
例如: m = r.sub == p.sub && r.act == p.act && r.obj == p.obj
这个简单和常见的匹配规则意味着如果请求的参数(访问实体,访问资源和访问方式)匹配, 如果可以在策略中找到资源和方法,那么策略结果(p.eft
)便会返回。 策略的结果将保存在 p.eft
中。
效果——Effect
它可以被理解为一种模型,在这种模型中,对匹配结果再次作出逻辑组合判断。
例如: e = some (where (p.eft == allow))
这句话意味着,如果匹配的策略结果有一些是允许的,那么最终结果为真。
让我们看看另一个示例: e = some (where (p.eft == allow)) && !some(where (p.eft == deny)
此示例组合的逻辑含义是:如果有符合允许结果的策略且没有符合拒绝结果的策略, 结果是为真。 换言之,当匹配策略均为允许(没有任何否认)是为真(更简单的是,既允许又同时否认,拒绝就具有优先地位)。
Casbin中最基本、最简单的model是ACL。ACL中的model 配置为:
# Request definition
[request_definition]
r = sub, obj, act
# Policy definition
[policy_definition]
p = sub, obj, act
# Policy effect
[policy_effect]
e = some(where (p.eft == allow))
# Matchers
[matchers]
m = r.sub == p.sub && r.obj == p.obj && r.act == p.act
ACL模型的一个示例策略类似:
p, alice, data1, read
p, bob, data2, write
它意味着:
- alice可以读取data1
- bob可以编写data2
我们还支持多行模式,通过在结尾处追加“\”:
# 匹配器
[matchers]
m = r.sub == p.sub && r.obj == p.obj \
&& r.act == p.act
此外,对于 ABAC,您在可以在 Casbin golang 版本中尝试下面的in
(jCasbin 和 Node-Casbin 尚不支持) 操作:
# Matchers
[matchers]
m = r.obj == p.obj && r.act == p.act || r.obj in ('data2', 'data3')
但是你应确保数组的长度大于 1,否则的话将会导致 panic 。
Model语法
- Model CONF 至少应包含四个部分:
[request_definition], [policy_definition], [policy_effect], [matchers]
。 - 如果 model 使用 RBAC, 还需要添加
[role_definition]
部分。 - Model CONF 文件可以包含注释。注释以
#
开头,#
会注释该行剩余部分。
Request定义
[request_definition]
部分用于request的定义,它明确了 e.Enforce(...)
函数中参数的含义。
[request_definition]
r = sub, obj, act
sub, obj, act
表示经典三元组: 访问实体 (Subject),访问资源 (Object) 和访问方法 (Action)。
但是, 你可以自定义你自己的请求表单, 如果不需要指定特定资源,则可以这样定义 sub、act
,或者如果有两个访问实体, 则为 sub、sub2、obj、act
。
Policy定义
[policy_definition]
部分是对policy的定义,以下文的 model 配置为例:
[policy_definition]
p = sub, obj, act
p2 = sub, act
这些是我们对policy规则的具体描述
p, alice, data1, read
p2, bob, write-all-objects
policy部分的每一行称之为一个策略规则, 每条策略规则通常以形如p
, p2
的policy type
开头。 如果存在多个policy定义,那么我们会根据前文提到的policy type
与具体的某条定义匹配。 上面的policy的绑定关系将会在matcher中使用, 罗列如下:
(alice, data1, read) -> (p.sub, p.obj, p.act)
(bob, write-all-objects) -> (p2.sub, p2.act)
TIP
策略规则中的元素总被视为字符串
Policy effect定义
[policy_effect]
是策略效果的定义。 它确定如果多项政策规则与请求相符,是否应批准访问请求。 例如,一项规则允许,另一项规则则加以拒绝。
[policy_effect]
e = some(where (p.eft == allow))
上面的策略效果表示如果有任何匹配的策略规则 允许
, 最终效果是 允许
(aka allow-override). p.eft
是策略的效果,它可以 允许
或 否定
。 它是可选的,默认值是 允许
。 因为我们没有在上面指定它,所以它使用默认值。
策略效果的另一个例子是:
[policy_effect]
e = !some(where (p.eft == deny))
这意味着如果没有匹配的政策规则为否定
, 最终效果是 允许
(别名为拒绝). some
表示:如果存在一个匹配的策略规则。 any
意味着:所有匹配的政策规则(这里不使用)。 策略效果甚至可以与逻辑表达式相关联:
[policy_effect]
e = some(where (p.eft == allow)) && !some(where (p.eft == deny))
这意味着至少有一个匹配的策略规则允许
,并且没有匹配的否定的
的策略规则。 因此,允许和拒绝授权都得到支持,拒绝则被推翻。
NOTE
尽管我们设计了政策效果的语法。 目前的执行只是使用硬编码的政策效果,因为我们认为这种灵活性没有多大必要。 所以现在您必须使用内置的政策效果之一,而不是自定义您自己的效果。
支持的内在政策效应是:
Policy effect | 意义 | 示例 |
---|---|---|
some(where (p.eft == allow)) | allow-override | ACL, RBAC, etc. |
!some(where (p.eft == deny)) | deny-override | Deny-override |
some(where (p.eft == allow)) && !some(where (p.eft == deny)) | allow-and-deny | Allow-and-deny |
priority(p.eft) || deny | priority | Priority |
subjectPriority(p.eft) | 基于角色的优先级 | 主题优先级 |
Matchers定义
[matchers]
是策略匹配程序的定义。匹配程序是表达式。它定义了如何根据请求评估策略规则。
[matchers]
m = r.sub == p.sub && r.obj == p.obj && r.act == p.act
上述匹配器是最简单的,这意味着请求中的主题、对象和行动应该与政策规则中的匹配。
您可以在匹配器中使用诸如 +, -, *, /
和逻辑操作员,例如 &&, ||, !
编辑器
例子1
模型ACL
当请求为alice, data1, read
时,执行结果为true。当请求为alice, data1, write
时,返回false。以上为最简单的ACL模型。
例子2
模型ACL
当为Policy添加effect时,如下
当策略为deny时,执行结果为false。修改策略为allow时,返回true。
例子3
模型ACL
当策略中存在deny和allow时,成功匹配,返回true。但是实际中,我们应以拒绝优先。此时,我们可以考虑修改Policy effect,运用内建的allow-and-deny
条目。
some(where (p.eft == allow)) && !some(where (p.eft == deny))
条目可以解释为,有一条通过,没有一条等于deny。
必须使用内建的策略规则,就是上面表格那5条
例子4
RBAC模型
匹配data1_admin
角色,角色包含write
权限,匹配通过
例子5
RBAC模型
策略直接匹配bob
用户通过
例子6
RBAC模型
策略直接限制bob
用户无法通过
例子7
RBAC模型
在例子6中添加一条策略g, bob, data2_admin
得例子7。此时,匹配data2_admin
域,但是bob
用户本身无法通过
例子8
RBAC模型
修改名字为bob1
,添加策略g, bob1, data2_admin
,通过。p, bob, data2, write, deny
策略无法限制用户bob1
例子9
模型RBAC with domains/tenants
请求匹配admin
角色,但是domain2
域内只有一条,仅可操作data2
数据,与请求中的data1
数据不符,故无法通过。
添加策略p, admin, domain2, data1, read
或者p, alice, domain2, data1, read
可以通过。