理解OpenShift(4):用户及权限管理

当前位置:首页百苑国际网址 >

百苑国际网址

理解OpenShift(4):用户及权限管理

时间:2019-06-10本站浏览次数:50

       

理解OpenShift(1):网络之 Router 和 Route

理解OpenShift(2):网络之 DNS(域名服务)

理解OpenShift(3):网络之 SDN

理解OpenShift(4):用户及权限管理

 

OpenShift 支持 RBAC(Role Based Access Controll),基于角色的访问控制。它涉及诸多概念,本文尝试着做一些概念上的梳理,很多细节还需要进一步研究。

1. 主要概念及其之间的联系

1.1 用户(User)

我试着把一个OpenShift 环境中的所有用户分为三大类:

应用用户:部署在集群之中的应用自己的用户。一般来说每个应用都有自己的用户管理系统,与平台无关。也有一些应用,比如 Jenkins,支持与OpenShift 用户系统集成,也就是Jenkins允许用户在通过了OpenShift 用户认证后对其进行访问。这部分不是本文的讨论范围之内。OpenShift 用户:访问OpenShift 资源的用户。根据其特征,又将其分为三个子类:Regular user:代表一个自然人用户,比如部署应用的一个开发者。System user:OpenShift 系统用户,大部分在集群创建时被自动创建,比如每个node都有一个system user。因为这部分主要和OpenShift自身系统相关,与一般用户关系不太大,因此本文不会具体介绍这部分。Service account:服务账户。这是跟一个项目关联的特殊系统用户,每个用户被一个 ServiceAccount 对象表示,通常是指 pod 中运行主进程的用户。后文会有具体介绍。操作系统用户:访问操作系统资源的用户,又分为容器内的操作系统用户,和宿主机上的操作系统用户。

1.2 身份(Identity)与认证(Authentication)

认证是确认用户身份是否合法的过程。这可以有多种实现方式,比如用户名/密码、令牌(token)、证书等。不同类型的用户有不同的身份管理方式:

对于 regular user,每个用户有一个身份(identity)用于认证。OpenShift  以插件形式支持多种 identity provider,比如在测试环境中常用的 htpasswd,生产环境中常用的 LDAP 等。这些 provider 中会保存用户身份信息,比如用户名和密码。useridentitymapping 对象将 user 对象和 identity 对象联系在一起。对于 service account,一方面它需要访问 OpenShift 集群资源比如 API 和内部镜像仓库中的镜像,另一方面它可能需要访问 pod 中和宿主机上的操作系统资源,比如宿主机上的文件或网络。对于前者,每个 service account 使用 secret 来进行身份认证,包括用户 API 访问的 token 和用于从镜像仓库拉取代码的 secret。对于后者,本来有 user namespace(用户命名空间)来支持,但是似乎OpenShift 还不支持该功能。

1.3 角色(Role)/权限(Permission)与授权(Authorization)

授权是对被认证了的用户访问受控制的资源的权限进行控制。按照资源类型,OpenShift 将授权管理方式分为两大类:

对于 OpenShift 集群资源,比如 pod,deployment,route 等,通过 role (角色)进行控制。从范围(scope)上分,role 可分为集群角色(clusterRole)和项目角色(role)。每个角色定义了受控制的对象(subject)、允许的操作(verb)和范围(集群还是项目)。用户(user)和角色(role/clusterRole)之间通过 rolebinding/clusterrolebinding 对象进行绑定。对于操作系统资源,这只针对服务账户。宿主机上的用户访问宿主机上的资源,这由宿主机操作系统进行控制。pod 中的用户(serviceaccount)访问pod内和宿主机上操作系统资源,由 scc(security context constraints)进行控制。

2. 身份 (Identity) 与认证(Authentication)

就像人的身份证一样,identity 是一个 user 的身份信息,该信息用于用户认证。OpenShift 灵活地支持多种 identity provider,实现各种不同的身份管理方案。每种实现都以不同的方式保存着用户的身份信息,比如保存在LDAP 中,保存在  htpasswd 文件中,保存在 OpenStack Keystone 中。

因此,OpenShift 对 user 身份的校验是通过这些配置了的 identity provider 进行的。因此,还需要 OpenShift user 和这些 provider 里面的 identity 的映射关系。OpenShfit 支持四种映射管理,claim,lookup,generate,add。具体请参考官网 https://docs.openshift.com/container-platform/3.11/install_config/configuring_authentication.html#identity-providers_parameters。

上图中以 htpasswd 这种 identity provider 为例,说明了从零创建一个 openshift user,在 htpasswd 中创建 user 及其密码,然后创建 openshift identity 对象以及 useridentitymapping 对象的过程。

用户获取用于身份认证的token的过程:

所有申请 OAuth token 的请求都要发到 <master>/oauth/authorize和<master>/oauth/token。每个申请 OAuth token 的请求中都必须带有 OAuth client 标识,这是一个 OAuthClient  对象。具体请参阅官方文档。OpenShift master 节点上内置有一个 OAuth server。用户从 OAuth 获取 token 后再用它去访问 API 就可以认证通过了。当一个 user 申请一个 OAuth token 时,OAuth 使用配置的 identity provider 去确定该申请用户的身份。它在确定该用户所映射到的 identity后,会为该用户创建一个 token,然后返回该token。

3. 角色(Role)和授权(Authorization)

前文说了,角色用于控制对 OpenShift 资源的访问权限,它分为项目角色和集群角色。

OpenShift 系统默认会创建很多的集群角色。常用的角色的简单描述如下: 

adminproject manager如果用于本地 rolebinding,那么用户将能查看和修改所在项目中的所有资源
basic-useruser 可以获取关于项目和用户的基本信息
cluster-admin用户可以在任何项目中做任何操作(超级用户)如何用于本地 rolebinding,那么用户将拥有所在project的所有权限,包括控制quota和role
cluster-status用户可以获取集群的基本状态信息
edit用户可以修改项目中的大部分对象;但是不能查看或修改 role 和 rolebinding
self-provisioner所有用户的默认role,可以创建自己的project
view用户可以查看项目中的大部分对象,除了 role 和 rolebinding用户不能做任何修改任何对象 

可以查看所有角色,比如 system:router 角色:

可以使用 oc adm policy 命令向用户或用户授予角色:

user、group、role、rolebinding 之间的关系:

更多对 role 的说明,可参见官方文档。 

4. Service Account 用户

 

OpenShift 的 service account 比较复杂,和很多概念都有关联。官方文档在  https://docs.openshift.com/container-platform/3.11/dev_guide/service_accounts.html。该文档对为什么需要这个概念的说明是:当一个自然人用户访问 OpenShfit API 时,OpenShift 对它进行用户认证和权限控制。但是,有时候做操作的并不是自然人用户,比如:

Replication Controller 调用 API 去创建或者删除 pod容器中的应用调用 API外部应用调用 API 去进行监控或者整合

为了这种访问,OpenShift 创造了 Service Account (简称sa)概念。每个项目(project)默认都会自动创建3个sa user: 

Service AccountUsage

builder

用于 build pod。它被授予了 system:image-builder 角色,因此被允许向内部镜像仓库中的任意 image stream 上push 镜像。

deployer

用于 deployment pod。被授予了 system:deployer 角色,因此被允许查看和修改集群中的 RC 及其 pod。

default

当一个 pod 没有显式指定 service account 默认都会使用该 sa user。

4.1 身份

sa 利用 secret(token)来保存其身份信息。默认情况下,每个 sa 用户都有两种token,即访问 OpenShift API 的token和访问内部镜像仓库的token。以系统默认的 『builder』 sa user 为例,它包含一个用于拉取镜像的token secret,两个访问API 的token secret,三个secret 中只有两个能被以卷的形式挂接给pod:

可以按需求修改一个 sa 账户的这些token。可参考 https://docs.openshift.com/enterprise/3.0/dev_guide/image_pull_secrets.html 为service account 创建和添加新的用于拉取镜像的token secret。具体请参考官方文档。

其中,sa 的 API token 会被挂接到 pod 的 目录的 token 文件,从而使得 pod 中的应用可以读取该 token 去访问 OpenShift API:

image pull secret 是如何挂载到 pod 的,我还没有找到。而且在 pod spec 中,只看到 API token secret 的 mountpoint,而并没有 imagePullSecret 的 mountpoint:

4.2 权限 - 访问OpenShift 集群资源的权限

和自然人 user 类似,对 sa 用户访问OpenShift 集群资源的权限控制是通过 role 进行的。前面的表格表明,项目的两个默认 sa builder 和 deployer 都被授予了相应的 role,从而能访问指定的资源。而默认的 sa 用户,只被授予了 /system:image-puller 角色。这意味着默认的 sa 用户只能拉取镜像,而不能访问集群其它资源。

下图是项目 stage 中的 rolebinding:

用户组 system:serviceaccounts:stage 中包括该项目中的所有 sa 用户。利用 default sa user 来做下实验。先获取其 API token,然后登录进 OpenShift 集群:

调用 API 获取 pod,结果失败:

向 default sa user 授予 cluster-reader 角色:

然后就可以做集群资源查询操作了。 

4.3 权限 - 访问系统资源的权限

pod 中的应用除了有访问 OpenShift API 和内部镜像仓库之外,还有一些系统资源访问要求。比如:

要求以任意用户甚至是 root 来运行 pod 中的主进程要求访问宿主机上的文件系统要求访问宿主机上的网络

对于这些操作系统资源的访问权限,OpenShift 利用 scc 来进行控制。这就要求:

在 scc 中进行权限控制。这部分在后面介绍。在 servie account 和 sa 之间建立联系。每个 scc 都有指定使用它的用户列表。所有通过身份认证了的用户都只在 restricted 这个 scc 的用户列表之中,包括 service account。因此,pod 默认使用的是 restricted scc。要使它使用其它的scc,就要将它的 service account user 加入到要使用的 scc 的用户列表之中。这在 scc 部分具体介绍。

5. Security Context Constraint(SCC)

前面说过,SCC 用于控制访问系统资源的权限,那说明只有  service account  才需要使用 scc。没在文档中看到自然人用户 user 使用 scc 的例子。

Linux 中的权限控制很是复杂,这里就不说明了,我自己也没怎么弄清楚。OpenShift scc 将系统权限分为几大类,具体见上图中的『权限』部分,然后可以创建 scc 对象来精细地控制对每种权限的控制。

正是因为这非常繁琐,因此 OpenShift 默认创建了几个典型的 scc,列表如下。上图中的『系统预定义scc』部分有简要说明,这里不再重复。

每个 scc 有其用户/用户组列表。以 restricted 为例,所有通过身份验证的用户都在列表中;而 anyuid,只有 cluster-admins 用户组中的用户在里面。

  

因此,要授权 pod 有除了 restricted 定义的权限之外的权限,至少有两种做法:

一是将其 service account 放到目标 scc 的用户列表中。此时建议创建一个新的 service account,而不要使用已有的,考虑到对现有 pod 的影响。比如因为 registry 和 router 服务的 pod 需要使用 host networkinig 网络模式,因此有为它们创建单独的 sa user 并且加入到了 hostnetwork scc 的用户列表中。二是将 service account 加入到目标 scc 的用户组中。

官方建议采用第一种。一个很常用的例子是运行要使用 root 用户的容器。很多的Docker 镜像都使用的是 root 用户。但是,openshift restricted scc 不允许使用 root 用户,而要使用一个用户区间内的用户:

修复步骤:

$ oc create serviceaccount useroot$ oc adm policy add-scc-to-user anyuid -z useroot$ oc patch dc/myAppNeedsRoot --patch "{"spec":{"template":{"spec":{"serviceAccountName": "useroot"}}}}"

说明:

第一步创建名为 userroot 的 sa user第二步将该 sa user 加入到 anyuid scc 的 user 列表中第三步在应用的 DeploymentConfig 中指定 serviceAccountName 为 userroot

 

感谢您的阅读,欢迎关注我的微信公众号:

 

, 1, 0, 9);




公司地址:乐清市经济开发区中心大道261号
联系人:向远方 18821261996
韩立民 15528622781
电话:18556259450 传真:cynze8d3@162.com
邮箱:zoowlarqm@162.com

粤公网安备 44030702001579号

百苑国际平台导航@