OpenStack身份管理
一、身份服务
1、Keystone的概念和功能
1.1、基本概念
- 认证(Authentication)——确认用户身份的过程,又称身份验证。
- 凭证(Credentials)——又称凭据,是用于确认用户身份的数据。
- 令牌(Token)——访问OpenStack API和各种资源需要提供的一种特殊的文本字符串。
- 用户(User)——使用OpenStack云服务的个人、系统或服务的账户名称。
- 项目(Project)——分配和隔离资源或身份对象的一个容器,也是一个权限组织形式。
- 域(Domain)——项目和用户的集合,目的是为身份实体定义管理界限。
- 组(Group)——表示域所拥有的用户集合的容器。
- 角色(Role)——用于定义用户权利和权限的集合。
- 端点(Endpoint)——OpenStack组件能够访问的网络地址,通常是一个URL。
- 服务(Service)——提供一个或多个端点,供用户通过这些端点访问资源和执行操作。
- 分区(Region)——OpenStack部署的通用分区。
1.2、主要功能
- 身份认证(Authentication)——令牌的发放和校验。
- 用户授权(Authorization)——授予用户在一个服务中所拥有的权限。
- 用户管理(Account)——管理用户账户。
- 服务目录(Service Catalog)——为每个OpenStack服务对外提供一个可用的服务目录和相应的API端点。
2、Keystone的管理层次结构
3、Keystone的认证流程
- 用户向Keystone提供身份凭证,Keystone验证通过后向用户返回令牌的同时还会返回一个通用目录
- 用户使用该令牌向该目录列表中的端点请求对应的项目信息,Keystone验证通过后返回用户对应的项目列表
- 用户从列表中选择要访问的项目,再次向Keystone发出请求,Keystone验证通过后返回管理该项目的服务列表和允许访问该项目的令牌
- 用户通过列表和通用目录映射找到服务的端点,并通过端点找到实际服务组件的位置
- 用户凭借项目令牌和端点来访问实际服务的组件
- 服务组件向Keystone提供用户项目令牌进行验证,Keystone验证通过后返回一系列的确认信息和附加信息(用户希望操作的内容)给服务
4、Keystone认证的API操作
4.1、查看当前的Identity API版本
[root@node-a ~]# curl "http://localhost:5000"|python -m json.tool
% Total % Received % Xferd Average Speed Time Time Time Current
Dload Upload Total Spent Left Speed
100 264 100 264 0 0 512 0 --:--:-- --:--:-- --:--:-- 512
{
"versions": {
"values": [
{
"id": "v3.13",
"links": [
{
"href": "http://localhost:5000/v3/",
"rel": "self"
}
],
"media-types": [
{
"base": "application/json",
"type": "application/vnd.openstack.identity-v3+json"
}
],
"status": "stable",
"updated": "2019-07-19T00:00:00Z"
}
]
}
}
4.2、通过API请求认证令牌
- Keystone默认支持的认证方法包括external、password、token、oauth1、mapped和application_credential。
- password和token分别表示密码认证和令牌认证,是常用的两种认证方法。
- 密码认证要求验证两条信息:资源(Resource)信息和身份(Identity)。
- 资源由作用域(Scope)来确定,指定用户要访问的资源(域或项目)。
- 作用域决定获取令牌的有效范围。对于用户、域和项目来说,作用域常常是指实体的所属域。
- 请求一个admin项目作用域的令牌(以密码认证方式通过API获取令牌)
# 查看admin账号密码
[root@node-a ~]# cat /root/keystonerc_admin
...
# 请求一个admin项目作用域的令牌(建议复制到记事本将密码修改后再执行此代码)
# 若是请求一个demo项目作用域的则把下述admin替换成demo
[root@node-a ~]# curl -i -H "Content-Type: application/json" -d '
{ "auth": {
"identity": {
"methods": ["password"],
"password": {
"user": {
"name": "admin",
"domain": { "id": "default" },
"password": "admin账号密码"
}
}
},
"scope": {
"project": {
"name": "admin",
"domain": { "id": "default" }
}
}
}
}' "http://localhost:5000/v3/auth/tokens" ;
# 返回令牌的基本信息(X-Subject-Token的值为令牌ID)等。
# ... X-Subject-Token: gAAAAABmFOkzlHG8K5eX ...
- 导出环境变量OS_TOKEN,将其值设置为上述操作获取的令牌ID。
[root@node-a ~]# export OS_TOKEN="上述获取的令牌ID"
- 以令牌认证方式请求一个认证令牌。
[root@node-a ~]# curl -i \
-H "Content-Type: application/json" \
-d '
{ "auth": {
"identity": {
"methods": ["token"],
"token": {
"id": "'$OS_TOKEN'"
}
}
}
}' \
"http://localhost:5000/v3/auth/tokens"
# 返回结果:这是一个新的认证令牌,由于本例中没有为该令牌指定作用域,这个令牌不能访问任何域或项目资源
# ...
# X-Subject-Token: gAAAAABmFOxda3pDC...
# ...
4.3、使用认证令牌通过API进行身份管理操作
获取认证令牌后,根据该令牌的权限进行身份管理操作。
-
获取域列表。
[root@node-a ~]# curl -s \
-H "X-Auth-Token: $OS_TOKEN" \
"http://localhost:5000/v3/domains" | python -mjson.tool
-
获取项目列表。
[root@node-a ~]# curl -s \
-H "X-Auth-Token: $OS_TOKEN" \
"http://localhost:5000/v3/projects" | python -mjson.tool
# 可以获取到默认的三个项目:admin、demo、services
-
创建一个用户。
[root@node-a ~]# curl -s \
-H "X-Auth-Token: $OS_TOKEN" \
-H "Content-Type: application/json" \
-d '{"user": {"name": "newuser", "password": "changeme"}}' \
"http://localhost:5000/v3/users" | python -mjson.tool
# 查看用户列表,确认创建成功
[root@node-a ~]# curl -s -H "X-Auth-Token: $OS_TOKEN" "http://localhost:5000/v3/users" | python -mjson.tool
二、管理项目、用户和角色
1、项目、用户和角色的概念
- 一个用户必须至少属于一个项目,也可以属于多个项目。
- 至少添加一个项目,再添加用户。
- 在删除用户账户之前,必须从该用户的主项目中删除该用户账户。
-
在OpenStack中可以针对项目(而不是用户)设置配额。
配额选项 | nova.conf配置文件中的对应项 | 默认值 | 说明 |
---|---|---|---|
元数据条目 | metadata_items | 128 | 允许每个实例拥有的元数据数量 |
VCPU数量 | cores | 20 | 允许项目使用的CPU核数 |
实例 | instances | 10 | 允许项目创建的实例数量 |
注入的文件 | injected_files | 5 | 允许注入文件的数量 |
已注入文件内容(Bytes) | injected_file_content_bytes | 10240 | 允许注入文件的字节数 |
密钥对 | key_pairs | 100 | 允许每个用户拥有的密钥对数量 |
注入文件路径的长度 | injected_file_path_bytes | 255 | 允许注入文件路径的字节数 |
卷 | volumes | 10 | 允许每个项目使用的逻辑卷数量 |
- 要将用户分配给多个项目,需要定义一个角色。
- 通常将角色分配给“用户—项目”对,即为某个项目的指定用户分配角色。
- Keystone使用基于角色的访问控制来保护其API。
- admin角色具有最高权限。
- 拥有reader角色的系统用户可以列出所部署的所有项目。
- 拥有reader角色的某个域用户只能查看该域范围的项目。
- member角色更适合于其他服务。
- 创建的所有角色都必须映射到每一个Openstack服务特定的policy.json配置文件中,默认的策略会将大多数服务的管理权限授予admin角色。
2、命令行的身份管理用法
2.1、项目管理
# 列出所有项目的ID和名称,包括禁用的项目。
openstack project list
# 查看项目详细信息。
openstack project show 项目名称或ID
# 创建一个项目的命令。
openstack project create --description 项目描述信息 项目名称 --domain 域名
# 修改项目名称。
openstack project set 项目名称或ID --name 新的项目名称
# 临时禁用某项目。
openstack project set 项目名称或ID --disable
# 激活已禁用项目。
openstack project set 项目名称或ID --enable
# 删除项目。
openstack project delete 项目名称或ID
2.2、用户管理
# 列出用户列表。
openstack user list
# 创建用户。
openstack user create --project 项目 --password 密码 用户名
# 改变用户账户的名称和邮件地址。
openstack user set 用户名或ID --name 新的用户名 --email 邮件地址
# 临时禁用用户账户(不能登录)。
openstack user set 用户名或ID --disable
# 激活已禁用用户账户。
openstack user set 用户名或ID --enable
# 删除用户。
openstack user delete 用户名或ID
2.3、角色管理
# 列出可用的角色。
openstack role list
# 创建一个新的角色。
openstack role create 角色名
# 查看角色详细信息。
openstack role show 角色名或ID
# 将角色分配给“用户—项目”对。
openstack role add --user 用户名或ID --project 项目名或ID 角色名或ID
# 查看某项目某用户的角色分配情况。
openstack role assignment list --user 用户名 --project 项目名 --names
# 删除分配给“用户—项目”对的角色。
openstack role remove --user 用户名或ID --project 用户名或ID 角色名或ID
2.4、专用的服务用户
- 其他OpenStack服务要通过Keystone进行集中统一认证,必须进行注册,即在Keystone中创建相应的项目、用户和角色并进行关联,然后创建服务目录。
- Keystone的服务目录是每个服务的可访问端点列表。
- 所有的OpenStack服务共用一个项目(通常命名为“service”或“services”),所用的角色都是admin,而服务之间的通信也要使用admin角色。
3、基于图形界面的身份管理基本操作
3.1、项目列表
3.2、“创建项目”面板(设置项目信息)
3.3、“创建项目”面板(添加项目成员)
3.4、查看或编辑项目的配额
3.5、用户列表
3.6、创建用户
3.7、管理角色
3.8、查看服务的API端点
4、基于命令行界面的身份管理基本操作
# 加载demo用户的客户端环境脚本。
[root@node-a ~]# source keystonerc_demo
# 查看当前的项目列表,该用户可以访问两个项目。
[root@node-a ~(keystone_demo)]# openstack project list
# 查看用户列表,可以发现demo用户没有被授权此项操作。
[root@node-a ~(keystone_demo)]# openstack user list
# 加载admin用户的客户端环境脚本。
[root@node-a ~(keystone_demo)]# source keystonerc_admin
# 查看当前的项目列表,云管理员可以查看所有的项目。
[root@node-a ~(keystone_admin)]# openstack project list
# 查看云平台上所有的角色分配。
[root@node-a ~(keystone_admin)]# openstack role assignment list --name
# 进一步筛选出系统管理员的角色分配。
[root@node-a ~(keystone_admin)]# openstack role assignment list --names --system all
# 查看当前的API端点列表
[root@node-a ~(keystone_admin)]# openstack endpoint list
报错信息解决!!!!
# 出现报错:
_init__() got an unexpected keyword argument 'token'
# 尝试以下解决:
# 1、xshell退出重新连接
# 2、升级 OpenStack 客户端
# 3、检查环境变量
env | grep OS_
# 4、试使用不同的认证方式
export OS_AUTH_TYPE=password
三、通过oslo.policy库实现权限管理*
1、OpenStack的oslo.policy库*
- OpenStack的oslo.policy库用于实现基于角色的权限访问控制(RBAC).
- 使用策略控制某一个用户权限,规定用户能执行什么操作,不能执行什么操作。
- 当一个API调用某个OpenStack服务时,该服务的策略引擎使用合适的策略定义来决定是否接受该调用。
2、policy.json文件的语法规则*
- 每条策略采用一行语句定义。 "目标" : "规则"
- 策略中的目标,又称操作(Action),表示需要执行的操作。
- 策略中的规则决定API调用在哪些情况或条件下可用,即是否被允许。
-
规则
- 总是允许,可以使用空字符串("")、中括号([])或"@"来表示。
- 总是拒绝,只能使用感叹号("!")来表示。
- 特定的检查结果。
- 两个值的比较。
-
基于简单规则的逻辑表达式。
-
特定的检查结果
- 角色:角色名称——测试API凭证是否包括该角色。
-
规则:规则名称——别名定义。
-
http:目标URL——将检查委托给远程服务器,远程服务器返回True则被授权。
- 两个值的比较采用以下语法格式。 "值1: 值2"
- 策略定义可以采用别名,别名是复杂或难懂的规则的一个名称。 "别名名称" : "<别名定义>"
-
policy.json文件的内容使用符号{}括起来,其中的多条策略之间由逗号分隔。 { "别名1" : "定义1", "别名2" : "定义2", ... "目标1" : "规则1", "目标2" : "规则2", .... }
3、掌握policy.json文件的编写*
# 允许任何实体列出虚拟机实例的策略。
"compute:get_all" : ""
# 使用感叹号表示拒绝。以下这条策略表示不能搁置实例。
"compute:shelve": "!"
# 规定只有云管理员才能在Identity(身份管理)数据库中创建新用户。
"identity:create_user" : "role:admin"
# 编排服务定义一个名为“heat_stack_user”的角色,属于该角色的用户都不被允许创建堆栈。
"stacks:create": "not role:heat_stack_user"
# 只有实例的所有者能够启动它的策略。
"os_compute_api:servers:start" : "project_id:%(project_id)s"