学习一下如何为一个集群生成kubeconfig

18,202 阅读5分钟

引言

作为一个云原生的开发者,我们常常会与k8s集群打交道,与集群打交道的第一步,那肯定就是kubeconfig了。不知道从何时起,我们对kubeconfig的理解停留在了非常浅薄的程度,仅限于知道如何使用kubeconfig来连接k8s集群,但是,了解到这个程度真的够么???

今天我就抽空梳理了有关kubeconfig相关的知识点以及一些常用的方法,旨在帮助大家深入了解kubeconfig。

简介

首先我们需要明确的是,用于配置集群访问的文件称为 kubeconfig 文件,并不是说有某一个文件的文件名叫kubeconfig。默认情况下,kubectl$HOME/.kube 目录下查找名为 config 的文件。 此外,还可以通过设置 KUBECONFIG 环境变量或者设置 --kubeconfig参数来指定其他 kubeconfig 文件。

  • 如果 KUBECONFIG 环境变量不存在,kubectl 将使用默认的 kubeconfig 文件:$HOME/.kube/config
  • --kubeconfig的用法:
kubectl --kubeconfig /custom/path/kube.config get pods -n default

kubeconfig组成

我们一起来看一下kubeconfig的组成:

除了apiVersion,kind等常见字段,我们重点看以下3个字段:

clusters

// Clusters is a map of referencable names to cluster configs
Clusters map[string]*Cluster `json:"clusters"`

// Cluster contains information about how to communicate with a kubernetes cluster
type Cluster struct {
   // LocationOfOrigin indicates where this object came from.  It is used for round tripping config post-merge, but never serialized.
   // +k8s:conversion-gen=false
   LocationOfOrigin string
   // Server is the address of the kubernetes cluster (https://hostname:port).
   Server string `json:"server"`
   // TLSServerName is used to check server certificate. If TLSServerName is empty, the hostname used to contact the server is used.
   // +optional
   TLSServerName string `json:"tls-server-name,omitempty"`
   // InsecureSkipTLSVerify skips the validity check for the server's certificate. This will make your HTTPS connections insecure.
   // +optional
   InsecureSkipTLSVerify bool `json:"insecure-skip-tls-verify,omitempty"`
   // CertificateAuthority is the path to a cert file for the certificate authority.
   // +optional
   CertificateAuthority string `json:"certificate-authority,omitempty"`
   // CertificateAuthorityData contains PEM-encoded certificate authority certificates. Overrides CertificateAuthority
   // +optional
   CertificateAuthorityData []byte `json:"certificate-authority-data,omitempty"`
   // ProxyURL is the URL to the proxy to be used for all requests made by this
   // client. URLs with "http", "https", and "socks5" schemes are supported.  If
   // this configuration is not provided or the empty string, the client
   // attempts to construct a proxy configuration from http_proxy and
   // https_proxy environment variables. If these environment variables are not
   // set, the client does not attempt to proxy requests.
   //
   // socks5 proxying does not currently support spdy streaming endpoints (exec,
   // attach, port forward).
   // +optional
   ProxyURL string `json:"proxy-url,omitempty"`
   // Extensions holds additional information. This is useful for extenders so that reads and writes don't clobber unknown fields
   // +optional
   Extensions map[string]runtime.Object `json:"extensions,omitempty"`
}

clusters是map类型,键是集群的名称,是集群的唯一标识,值是一个名为Cluster的结构体。虽然Clusters这个结构体中包含的字段很多,但是常用的就是以下4个字段:

  • server(必填):kube-apiserver的地址,通常是如下格式:https://hostname:port,如果忽略了port,则默认port是443.
  • insecure-skip-tls-verify(可选):默认是false,当设置为true时,将跳过证书认证。
  • certificate-authority(可选):填写的是ca证书的存放路径。
  • certificate-authority-data(可选):填写的是ca证书的内容。

Clusters 中的certificate-authority表示的是服务端的ca证书,用于验证服务端证书apiserver.crt的正确性。

users

// AuthInfos is a map of referencable names to user configs
AuthInfos map[string]*AuthInfo `json:"users"`

// AuthInfo contains information that describes identity information.  This is use to tell the kubernetes cluster who you are.
type AuthInfo struct {
   // LocationOfOrigin indicates where this object came from.  It is used for round tripping config post-merge, but never serialized.
   // +k8s:conversion-gen=false
   LocationOfOrigin string
   // ClientCertificate is the path to a client cert file for TLS.
   // +optional
   ClientCertificate string `json:"client-certificate,omitempty"`
   // ClientCertificateData contains PEM-encoded data from a client cert file for TLS. Overrides ClientCertificate
   // +optional
   ClientCertificateData []byte `json:"client-certificate-data,omitempty"`
   // ClientKey is the path to a client key file for TLS.
   // +optional
   ClientKey string `json:"client-key,omitempty"`
   // ClientKeyData contains PEM-encoded data from a client key file for TLS. Overrides ClientKey
   // +optional
   ClientKeyData []byte `json:"client-key-data,omitempty" datapolicy:"security-key"`
   // Token is the bearer token for authentication to the kubernetes cluster.
   // +optional
   Token string `json:"token,omitempty" datapolicy:"token"`
   // TokenFile is a pointer to a file that contains a bearer token (as described above).  If both Token and TokenFile are present, Token takes precedence.
   // +optional
   TokenFile string `json:"tokenFile,omitempty"`
   // Impersonate is the username to act-as.
   // +optional
   Impersonate string `json:"act-as,omitempty"`
   // ImpersonateUID is the uid to impersonate.
   // +optional
   ImpersonateUID string `json:"act-as-uid,omitempty"`
   // ImpersonateGroups is the groups to impersonate.
   // +optional
   ImpersonateGroups []string `json:"act-as-groups,omitempty"`
   // ImpersonateUserExtra contains additional information for impersonated user.
   // +optional
   ImpersonateUserExtra map[string][]string `json:"act-as-user-extra,omitempty"`
   // Username is the username for basic authentication to the kubernetes cluster.
   // +optional
   Username string `json:"username,omitempty"`
   // Password is the password for basic authentication to the kubernetes cluster.
   // +optional
   Password string `json:"password,omitempty" datapolicy:"password"`
   // AuthProvider specifies a custom authentication plugin for the kubernetes cluster.
   // +optional
   AuthProvider *AuthProviderConfig `json:"auth-provider,omitempty"`
   // Exec specifies a custom exec-based authentication plugin for the kubernetes cluster.
   // +optional
   Exec *ExecConfig `json:"exec,omitempty"`
   // Extensions holds additional information. This is useful for extenders so that reads and writes don't clobber unknown fields
   // +optional
   Extensions map[string]runtime.Object `json:"extensions,omitempty"`
}

users字段同样是一个map类型,键是user的名称,值是名为AuthInfo的结构体。users中主要是包含了用户的证书和密钥,用于校验用户的身份。

context

集群参数和用户参数可以同时设置多对,而context的作用就是集群参数和用户参数关联起来,current-context的参数则是指定该kubeconfig默认使用的cluster和user。

// Contexts is a map of referencable names to context configs
Contexts map[string]*Context `json:"contexts"`
// CurrentContext is the name of the context that you would like to use by default
CurrentContext string `json:"current-context"`

kubeconfig生成

本节介绍如何使用kubectl的方式生成kubeconfig。

场景:假设要给用户jack生成一个kubeconfig,只具有jack命名空间下的所有pod的get,list和watch的权限。

  1. 生成证书

证书的生成参考:kubernetes.io/zh-cn/docs/…

  1. 创建Role和RoleBinding
kind: Role
apiVersion: rbac.authorization.k8s.io/v1beta1
metadata:
  namespace: jack
  name: test-role
rules:
- apiGroups: [""]
  resources: ["pods"]
  verbs: ["*"]
---
kind: RoleBinding
apiVersion: rbac.authorization.k8s.io/v1beta1
metadata:
  name: test-jack
  namespace: jack
subjects:
- kind: User
  name: jack
  apiGroup: ""
roleRef:
  kind: Role
  name: test-role
  apiGroup: ""
  1. 生成kubeconfig
# set-cluster 设置集群参数
kubectl config set-cluster kubernetes \
  --certificate-authority=/etc/kubernetes/pki/ca.pem \
  --embed-certs=true \
  --server=https://xx:6443 \
  --kubeconfig=jack.conf

# set-credentials 设置证书参数
kubectl config set-credentials jack \
  --client-certificate=/etc/kubernetes/pki/jack.pem \
  --embed-certs=true \
  --client-key=/etc/kubernetes/pki/jack-key.pem \
  --kubeconfig=jack.conf

# set-context 设置上下文参数
kubectl config set-context jack@kubernetes \
  --cluster=kubernetes \
  --user=jack \
  --kubeconfig=jack.conf

# set default context 设置默认的上下文
kubectl config use-context jack@kubernetes --kubeconfig=jack.conf

参考文档