如何向Kubernetes(kubectl)添加用户?

76
我已使用kops在AWS上创建了一个Kubernetes集群,并可以通过本地机器上的kubectl成功管理它。
我可以使用kubectl config view查看当前配置,也可以直接访问存储的状态,如~/.kube/config
apiVersion: v1
clusters:
- cluster:
    certificate-authority-data: REDACTED
    server: https://api.{CLUSTER_NAME}
  name: {CLUSTER_NAME}
contexts:
- context:
    cluster: {CLUSTER_NAME}
    user: {CLUSTER_NAME}
  name: {CLUSTER_NAME}
current-context: {CLUSTER_NAME}
kind: Config
preferences: {}
users:
- name: {CLUSTER_NAME}
  user:
    client-certificate-data: REDACTED
    client-key-data: REDACTED
    password: REDACTED
    username: admin
- name: {CLUSTER_NAME}-basic-auth
  user:
    password: REDACTED
    username: admin

我需要让其他用户也能进行管理。这个user guide描述了如何在其他用户的机器上定义,但没有描述如何在集群本身中创建用户凭据。你怎么做?
此外,只分享cluster.certificate-authority-data是安全的吗?

1
看起来你想要服务账户 - Anirudh Ramanathan
1
我已经阅读了有关服务账户的文档,其中显示它们很容易创建并检索其 ca.crttoken,但这对于设置 kubeconfig 来说还不够或不正确。如果您知道如何配置 kubeconfig,请告诉我。 - peterl
3个回答

108

关于认证的详细概述,请参阅 Kubernetes 官方文档中的 AuthenticationAuthorization

对于用户而言,最好使用 Kubernetes 的身份提供者(OpenID Connect)。

如果您正在使用 GKE / ACS,则需要与相应的身份验证和访问管理框架集成。

如果您自己托管 Kubernetes(当您使用 kops 时),则可以使用 coreos/dex 与 LDAP / OAuth2 身份提供者进行集成 - 可以参考这篇详细的两部分 SSO for Kubernetes 文章。

kops(1.10+)现在具有内置的 authentication support,如果您正在使用 AWS,则可以轻松地将其与 AWS IAM 作为身份提供者进行集成。

对于 Dex,有一些开源的 cli 客户端,如下所示:

如果您正在寻找快速且简便(不是最安全且易于长期管理的方法)入门的方法,则可以滥用serviceaccounts-有两个专业策略选项来控制访问权限(见下文)。

注意:自1.6版本以来,强烈建议使用基于角色的访问控制!本答案不涵盖RBAC设置。

编辑:Bitnami提供了一个出色但过时(2017-2018年)的关于使用RBAC的用户设置的指南。

启用服务帐户访问的步骤如下(根据您的集群配置是否包括RBAC或ABAC策略,这些帐户可能具有完整的管理员权限!):

编辑: 这里有一个Bash脚本可以自动化创建服务账户——请参考下面的步骤

  1. Create service account for user Alice

    kubectl create sa alice
    
  2. Get related secret

    secret=$(kubectl get sa alice -o json | jq -r .secrets[].name)
    
  3. Get ca.crt from secret (using OSX base64 with -D flag for decode)

    kubectl get secret $secret -o json | jq -r '.data["ca.crt"]' | base64 -D > ca.crt
    
  4. Get service account token from secret

    user_token=$(kubectl get secret $secret -o json | jq -r '.data["token"]' | base64 -D)
    
  5. Get information from your kubectl config (current-context, server..)

    # get current context
    c=$(kubectl config current-context)
    
    # get cluster name of context
    name=$(kubectl config get-contexts $c | awk '{print $3}' | tail -n 1)
    
    # get endpoint of current context 
    endpoint=$(kubectl config view -o jsonpath="{.clusters[?(@.name == \"$name\")].cluster.server}")
    
  6. On a fresh machine, follow these steps (given the ca.cert and $endpoint information retrieved above:

    1. Install kubectl

       brew install kubectl
      
    2. Set cluster (run in directory where ca.crt is stored)

       kubectl config set-cluster cluster-staging \
         --embed-certs=true \
         --server=$endpoint \
         --certificate-authority=./ca.crt
      
    3. Set user credentials

       kubectl config set-credentials alice-staging --token=$user_token
      
    4. Define the combination of alice user with the staging cluster

       kubectl config set-context alice-staging \
         --cluster=cluster-staging \
         --user=alice-staging \
         --namespace=alice
      
    5. Switch current-context to alice-staging for the user

       kubectl config use-context alice-staging
      
要使用策略(使用ABAC)控制用户访问权,您需要创建一个policy文件(例如):
{
  "apiVersion": "abac.authorization.kubernetes.io/v1beta1",
  "kind": "Policy",
  "spec": {
    "user": "system:serviceaccount:default:alice",
    "namespace": "default",
    "resource": "*",
    "readonly": true
  }
}

在每个主节点上提供此policy.json文件,并在API服务器中添加--authorization-mode=ABAC --authorization-policy-file=/path/to/policy.json标志。

这将允许Alice(通过她的服务帐户)仅对默认名称空间中的所有资源具有只读权限。


太好了,这正是我在寻找的。不过需要澄清一下:第三步创建了一个ca.crt文件,但第6.2步骤需要一个ca.pem文件。是否需要进行翻译,还是只是笔误? - peterl
还有一点需要注意的是,你可以在自己的机器上使用 export KUBECONFIG=alice-config 命令来生成一个包含证书的单独的 alice-config 文件,并将该文件发送给 Alice(告诉她将它复制到 ~/kube/config 目录下) - 但是如果 Alice 需要管理多个集群和上下文,则这会使她的任务变得更加复杂。 - Vincent De Smet
太棒了。非常感谢。也许你甚至会考虑为Kubernetes.io撰写一些内容。 - peterl
1
@VincentDeSmet,你说“更好地支持用户对象仍在计划中”,你知道自那时以来有什么变化吗?也许在kubernetes/kubernetes中有RFC或开放的PRs/issues? - oldhomemovie
嗨@DavidHam - 请阅读完整的答案 - 您需要为用户提供身份验证提供程序。服务帐户基本上为API访问提供JWT,并且可用于机器人/程序,不应用于用户,如答案中详细说明。 - Vincent De Smet
显示剩余6条评论

4

您说:

我需要使其他用户也能管理。

但根据文档的说法:

普通用户被认为是由一个外部独立的服务来管理的。管理员分发私钥,用户存储库如Keystone或Google账户,甚至是一个包含用户名和密码列表的文件。在这方面,Kubernetes没有代表普通用户帐户的对象。普通用户不能通过API调用添加到集群中。

您必须使用第三方工具才能实现此功能。

== 编辑 ==

一个解决方法是在kubeconfig文件中手动创建用户条目。根据文档:

# create kubeconfig entry
$ kubectl config set-cluster $CLUSTER_NICK \
    --server=https://1.1.1.1 \
    --certificate-authority=/path/to/apiserver/ca_file \
    --embed-certs=true \
    # Or if tls not needed, replace --certificate-authority and --embed-certs with
    --insecure-skip-tls-verify=true \
    --kubeconfig=/path/to/standalone/.kube/config

# create user entry
$ kubectl config set-credentials $USER_NICK \
    # bearer token credentials, generated on kube master
    --token=$token \
    # use either username|password or token, not both
    --username=$username \
    --password=$password \
    --client-certificate=/path/to/crt_file \
    --client-key=/path/to/key_file \
    --embed-certs=true \
    --kubeconfig=/path/to/standalone/.kube/config

# create context entry
$ kubectl config set-context $CONTEXT_NAME \
    --cluster=$CLUSTER_NICK \
    --user=$USER_NICK \
    --kubeconfig=/path/to/standalone/.kube/config

1
我也在文档中读到了这一点,但问题是我使用Kops创建了我的集群,并且它创建了初始管理员用户,因此必须有一种方法来创建另一个管理员用户。 - peterl
2
是的,一旦用户在集群中创建成功,您将使用kubectl config命令,并按照我在原始问题中提到的set-clusterset-credentialsset-context指令进行操作。但是,您如何在集群中创建实际的用户呢?您从哪里获取随这些指令一起提供的实际证书呢? - peterl
嗨@peterl,我有同样的疑问...你解决了吗? - caarlos0
是的,我使用了Vincent De Smet的解决方案,它非常有效。 - peterl

2

1
你是不是指的是RBAC?你能再解释一下吗,这似乎只是一个链接。 - Blue

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接