摘要: Google Zanzibar 权限服务
Zanzibar 是一个用于存储和评估访问控制列表的全球系统。 Zanzibar 提供统一的数据模型和配置语言,用于表达来自 Google 数百个客户端服务的广泛访问控制策略,包括Calendar、Cloud、 Drive、Maps、Photos、YouTube。
ACL 表示为关系元组的对象-用户或对象-对象关系的集合。组只是具有成员资格语义的 ACL。关系元组具有高效的二进制编码,我们使用方便的文本符号表示它们:
⟨*tuple*⟩ ::= ⟨*object*⟩‘#’⟨*relation*⟩‘@’⟨*user*⟩
⟨*object*⟩ ::= ⟨*namespace*⟩‘:’⟨*object id*⟩
⟨*user*⟩ ::= ⟨*user id*⟩ | ⟨*userset*⟩
⟨*userset*⟩ ::= ⟨*object*⟩‘#’⟨*relation*⟩
Simple Example
// user1 has access on dir1
dir1#access@user1
// Have a look on the subjects concept page if you don't know the empty relation.
dir1#parent@(file1#)
// Everyone with access to dir1 has access to file1. This would probably be defined
// through a subject set rewrite that defines this inherited relation globally.
// In this example, we define this tuple explicitly.
file1#access@(dir1#access)
// Direct access on file2 was granted.
file2#access@user1
// user2 is owner of file2
file2#owner@user2
// Owners of file2 have access to it; possibly defined through subject set rewrites.
file2#access@(file2#owner)
Example Tuple | Semantics |
---|---|
doc:readme#owner@10 | User 10 is an owner of doc:readme |
group:eng#member@11 | User 11 is a member of group:eng |
doc:readme#viewer@group:eng#member | Members of group:eng are viewers of doc:readme |
doc:readme#parent@folder:A#… | doc:readme is in folder:A |
为了减少关系元组在表达关系上会出现很多条的关系组,客户端通过关系配置中的用户集重写规则来定义对象不可知的关系。
name: "doc"
relation { name: "owner" }
relation {
name: "editor"
userset_rewrite {
union {
child { _this {} }
child { computed_userset { relation: "owner" } }
}}}
relation {
name: "viewer"
userset_rewrite {
union {
child { _this {} }
child { computed_userset { relation: "editor" } }
child { tuple_to_userset {
tupleset { relation: "parent" }
computed_userset {
object: $TUPLE_USERSET_OBJECT # parent folder
relation: "viewer" }}}
}}}
_this
返回所有用户集合,默认行为
computed_userset
计算出一个新的用户集合,例如使 viewer 用户引用 editor 用户。
tuple_to_userset
从输入对象中获取匹配的关系组,例如匹配其父级文件夹并继承其 viewer 权限
一个用户集表达式也可以由多个子表达式组成,通过并集、交集和排除等操作组合。
aclservers 是主要的服务器类型。它们被组织成集群并响应 Check、Read、Expand 和 Write 请求。请求到达集群中的任何服务器,并且该服务器根据需要将工作分发到集群中的其他服务器。这些服务器可以依次联系其他服务器以计算中间结果。初始服务器收集最终结果并将其返回给客户端。
watchservers 是一种特殊的服务器类型,可以响应 Watch 请求。他们跟踪更改日志并近乎实时地为客户端提供命名空间更改流。