Kubernetes 命名空间默认服务帐户
Kubernetes namespace default service account
如果未指定,pods 在默认服务帐户下 运行。
- 如何查看默认服务帐户被授权执行的操作?
- 我们是否需要将它安装在每个 pod 上?
- 如果不是,我们如何在命名空间级别或集群级别禁用此行为。
- 默认服务帐户应该处理哪些其他用例?
- 我们可以将它用作服务帐户来创建和管理命名空间中的 Kubernetes 部署吗?例如,我们不会使用真实用户帐户在集群中创建东西,因为用户来来去去。
环境:Kubernetes 1.12,带 RBAC
- 为每个命名空间自动创建一个默认服务帐户。
kubectl get serviceaccount
NAME SECRETS AGE
default 1 1d
可以在需要时添加服务帐户。每个 pod 仅与一个服务帐户相关联,但多个 pods 可以使用相同的服务帐户。
一个 pod 只能使用同一命名空间中的一个服务帐户。
通过在 pod 清单中指定帐户名称,将服务帐户分配给 pod。如果你没有明确分配它,pod 将使用默认服务帐户。
服务帐户的默认权限不允许它
列出或修改任何资源。默认服务帐户不允许查看集群状态,更不用说以任何方式修改它了。
默认情况下,命名空间中的默认服务帐户除了未经身份验证的用户没有其他权限。
因此 pods 默认情况下甚至无法查看集群状态。由您授予他们适当的权限来执行此操作。
kubectl exec -it test -n foo sh / # curl
localhost:8001/api/v1/namespaces/foo/services { "kind": "Status",
"apiVersion": "v1", "metadata": {
}, "status": "Failure", "message": "services is forbidden: User
"system:serviceaccount:foo:default" cannot list resource
"services" in API group "" in the namespace "foo"", "reason":
"Forbidden", "details": {
"kind": "services" }, "code": 403
如上所示,默认服务帐户无法列出服务
但当给予适当的角色和角色绑定时,如下所示
apiVersion: rbac.authorization.k8s.io/v1
kind: Role
metadata:
creationTimestamp: null
name: foo-role
namespace: foo
rules:
- apiGroups:
- ""
resources:
- services
verbs:
- get
- list
apiVersion: rbac.authorization.k8s.io/v1
kind: RoleBinding
metadata:
creationTimestamp: null
name: test-foo
namespace: foo
roleRef:
apiGroup: rbac.authorization.k8s.io
kind: Role
name: foo-role
subjects:
- kind: ServiceAccount
name: default
namespace: foo
现在我可以列出资源服务了
kubectl exec -it test -n foo sh
/ # curl localhost:8001/api/v1/namespaces/foo/services
{
"kind": "ServiceList",
"apiVersion": "v1",
"metadata": {
"selfLink": "/api/v1/namespaces/bar/services",
"resourceVersion": "457324"
},
"items": []
为所有服务帐户提供 clusteradmin
ClusterRole 是一个
馊主意。最好只给每个人完成工作所需的权限,而不是再给一个权限。
为每个 pod 创建一个特定的服务帐户是个好主意
然后将其与定制角色或 ClusterRole 通过
角色绑定。
如果您的一个 pods 只需要读取 pods 而另一个还需要修改它们,那么创建两个不同的服务帐户并使这些 pods通过在
pod 规格
您可以参考下面的link以获得深入的解释。
Service account example with roles
您可以检查kubectl explain serviceaccount.automountServiceAccountToken
并编辑服务帐户
kubectl edit serviceaccount default -o yaml
apiVersion: v1
automountServiceAccountToken: false
kind: ServiceAccount
metadata:
creationTimestamp: 2018-10-14T08:26:37Z
name: default
namespace: default
resourceVersion: "459688"
selfLink: /api/v1/namespaces/default/serviceaccounts/default
uid: de71e624-cf8a-11e8-abce-0642c77524e8
secrets:
- name: default-token-q66j4
完成此更改后,您生成的任何 pod 都没有 serviceaccount 令牌,如下所示。
kubectl exec tp -it bash
root@tp:/# cd /var/run/secrets/kubernetes.io/serviceaccount
bash: cd: /var/run/secrets/kubernetes.io/serviceaccount: No such file or directory
通过在部署配置的 serviceAccountName
字段中指定,application/deployment 可以 运行 使用 default
以外的服务帐户。
我的服务帐户或任何其他用户可以执行的操作取决于它被赋予(绑定到)的角色 - 请参阅 roleBindings 或 clusterRoleBindings;动词是每个角色的 apiGroups
和 resources
在 rules
定义下。
默认情况下,default
服务帐户似乎没有被赋予任何角色。可以按照 #2 here.
中所述向 default
服务帐户授予角色
根据 this,“...在 1.6+ 版本中,您可以通过在服务帐户上设置 automountServiceAccountToken: false
来选择不为服务帐户自动挂载 API 凭据” .
HTH
- 如何查看默认服务帐户被授权执行的操作?
没有简单的方法,但 auth can-i
可能会有所帮助。例如
$ kubectl auth can-i get pods --as=system:serviceaccount:default:default
no
对于用户来说有 auth can-i --list
但这似乎不适用于 --as
我怀疑这是一个错误。无论如何,你可以 运行 对几个动词执行上述命令,在所有情况下答案都是否,但我只试了几个。结论:似乎 默认服务帐户默认没有权限(因为在我检查的集群中,我们没有配置它,AFAICT)。
- 我们是否需要将它安装在每个 pod 上?
不确定问题的含义。
- 如果不是,我们如何在命名空间级别或集群级别禁用此行为。
您可以在服务或单个 pod 上设置 automountServiceAccountToken: false
。服务帐户是每个命名空间的,因此在服务帐户上完成后,该命名空间中使用此帐户的任何 pods 都将受到该设置的影响。
- 默认服务帐户应该处理哪些其他用例?
默认服务帐户是后备帐户,如果 pod 未指定,则使用 SA。所以默认服务帐户应该没有任何特权。为什么 pod 默认需要与 kube API 通信?
- 我们可以将它用作服务帐户来在命名空间中创建和管理 Kubernetes 部署吗?
我不建议这样做,请参阅之前的回答。相反,您应该按照最小权限原则为需要访问 API 的每个 pod 类型创建一个服务帐户(绑定到适当的 role/clusterrole)。所有其他 pod 类型都可以使用默认服务帐户,该帐户不应自动挂载 SA 令牌并且不应绑定到任何角色。
kubectl auth can-i --list --as=system:serviceaccount:<namespace>:<serviceaccount> -n <namespace>
作为一个简单的例子。检查 testns 命名空间中的默认服务帐户
kubectl auth can-i --list --as=system:serviceaccount:testns:default -n testns
Resources Non-Resource URLs Resource Names Verbs
selfsubjectaccessreviews.authorization.k8s.io [] [] [create]
selfsubjectrulesreviews.authorization.k8s.io [] [] [create]
[/.well-known/openid-configuration] [] [get]
[/api/*] [] [get]
[/api] [] [get]
[ ... ]
[/readyz] [] [get]
[/version/] [] [get]
[/version/] [] [get]
[/version] [] [get]
[/version] [] [get]
如果未指定,pods 在默认服务帐户下 运行。
- 如何查看默认服务帐户被授权执行的操作?
- 我们是否需要将它安装在每个 pod 上?
- 如果不是,我们如何在命名空间级别或集群级别禁用此行为。
- 默认服务帐户应该处理哪些其他用例?
- 我们可以将它用作服务帐户来创建和管理命名空间中的 Kubernetes 部署吗?例如,我们不会使用真实用户帐户在集群中创建东西,因为用户来来去去。
环境:Kubernetes 1.12,带 RBAC
- 为每个命名空间自动创建一个默认服务帐户。
kubectl get serviceaccount
NAME SECRETS AGE
default 1 1d
可以在需要时添加服务帐户。每个 pod 仅与一个服务帐户相关联,但多个 pods 可以使用相同的服务帐户。
一个 pod 只能使用同一命名空间中的一个服务帐户。
通过在 pod 清单中指定帐户名称,将服务帐户分配给 pod。如果你没有明确分配它,pod 将使用默认服务帐户。
服务帐户的默认权限不允许它 列出或修改任何资源。默认服务帐户不允许查看集群状态,更不用说以任何方式修改它了。
默认情况下,命名空间中的默认服务帐户除了未经身份验证的用户没有其他权限。
因此 pods 默认情况下甚至无法查看集群状态。由您授予他们适当的权限来执行此操作。
kubectl exec -it test -n foo sh / # curl localhost:8001/api/v1/namespaces/foo/services { "kind": "Status",
"apiVersion": "v1", "metadata": {}, "status": "Failure", "message": "services is forbidden: User "system:serviceaccount:foo:default" cannot list resource "services" in API group "" in the namespace "foo"", "reason": "Forbidden", "details": { "kind": "services" }, "code": 403
如上所示,默认服务帐户无法列出服务
但当给予适当的角色和角色绑定时,如下所示
apiVersion: rbac.authorization.k8s.io/v1
kind: Role
metadata:
creationTimestamp: null
name: foo-role
namespace: foo
rules:
- apiGroups:
- ""
resources:
- services
verbs:
- get
- list
apiVersion: rbac.authorization.k8s.io/v1
kind: RoleBinding
metadata:
creationTimestamp: null
name: test-foo
namespace: foo
roleRef:
apiGroup: rbac.authorization.k8s.io
kind: Role
name: foo-role
subjects:
- kind: ServiceAccount
name: default
namespace: foo
现在我可以列出资源服务了
kubectl exec -it test -n foo sh
/ # curl localhost:8001/api/v1/namespaces/foo/services
{
"kind": "ServiceList",
"apiVersion": "v1",
"metadata": {
"selfLink": "/api/v1/namespaces/bar/services",
"resourceVersion": "457324"
},
"items": []
为所有服务帐户提供
clusteradmin
ClusterRole 是一个 馊主意。最好只给每个人完成工作所需的权限,而不是再给一个权限。为每个 pod 创建一个特定的服务帐户是个好主意 然后将其与定制角色或 ClusterRole 通过 角色绑定。
如果您的一个 pods 只需要读取 pods 而另一个还需要修改它们,那么创建两个不同的服务帐户并使这些 pods通过在 pod 规格
您可以参考下面的link以获得深入的解释。
Service account example with roles
您可以检查kubectl explain serviceaccount.automountServiceAccountToken
并编辑服务帐户
kubectl edit serviceaccount default -o yaml
apiVersion: v1
automountServiceAccountToken: false
kind: ServiceAccount
metadata:
creationTimestamp: 2018-10-14T08:26:37Z
name: default
namespace: default
resourceVersion: "459688"
selfLink: /api/v1/namespaces/default/serviceaccounts/default
uid: de71e624-cf8a-11e8-abce-0642c77524e8
secrets:
- name: default-token-q66j4
完成此更改后,您生成的任何 pod 都没有 serviceaccount 令牌,如下所示。
kubectl exec tp -it bash
root@tp:/# cd /var/run/secrets/kubernetes.io/serviceaccount
bash: cd: /var/run/secrets/kubernetes.io/serviceaccount: No such file or directory
通过在部署配置的 serviceAccountName
字段中指定,application/deployment 可以 运行 使用 default
以外的服务帐户。
我的服务帐户或任何其他用户可以执行的操作取决于它被赋予(绑定到)的角色 - 请参阅 roleBindings 或 clusterRoleBindings;动词是每个角色的 apiGroups
和 resources
在 rules
定义下。
默认情况下,default
服务帐户似乎没有被赋予任何角色。可以按照 #2 here.
default
服务帐户授予角色
根据 this,“...在 1.6+ 版本中,您可以通过在服务帐户上设置 automountServiceAccountToken: false
来选择不为服务帐户自动挂载 API 凭据” .
HTH
- 如何查看默认服务帐户被授权执行的操作?
没有简单的方法,但 auth can-i
可能会有所帮助。例如
$ kubectl auth can-i get pods --as=system:serviceaccount:default:default
no
对于用户来说有 auth can-i --list
但这似乎不适用于 --as
我怀疑这是一个错误。无论如何,你可以 运行 对几个动词执行上述命令,在所有情况下答案都是否,但我只试了几个。结论:似乎 默认服务帐户默认没有权限(因为在我检查的集群中,我们没有配置它,AFAICT)。
- 我们是否需要将它安装在每个 pod 上?
不确定问题的含义。
- 如果不是,我们如何在命名空间级别或集群级别禁用此行为。
您可以在服务或单个 pod 上设置 automountServiceAccountToken: false
。服务帐户是每个命名空间的,因此在服务帐户上完成后,该命名空间中使用此帐户的任何 pods 都将受到该设置的影响。
- 默认服务帐户应该处理哪些其他用例?
默认服务帐户是后备帐户,如果 pod 未指定,则使用 SA。所以默认服务帐户应该没有任何特权。为什么 pod 默认需要与 kube API 通信?
- 我们可以将它用作服务帐户来在命名空间中创建和管理 Kubernetes 部署吗?
我不建议这样做,请参阅之前的回答。相反,您应该按照最小权限原则为需要访问 API 的每个 pod 类型创建一个服务帐户(绑定到适当的 role/clusterrole)。所有其他 pod 类型都可以使用默认服务帐户,该帐户不应自动挂载 SA 令牌并且不应绑定到任何角色。
kubectl auth can-i --list --as=system:serviceaccount:<namespace>:<serviceaccount> -n <namespace>
作为一个简单的例子。检查 testns 命名空间中的默认服务帐户
kubectl auth can-i --list --as=system:serviceaccount:testns:default -n testns
Resources Non-Resource URLs Resource Names Verbs
selfsubjectaccessreviews.authorization.k8s.io [] [] [create]
selfsubjectrulesreviews.authorization.k8s.io [] [] [create]
[/.well-known/openid-configuration] [] [get]
[/api/*] [] [get]
[/api] [] [get]
[ ... ]
[/readyz] [] [get]
[/version/] [] [get]
[/version/] [] [get]
[/version] [] [get]
[/version] [] [get]