Control de acceso basado en roles (RBAC) en Kubernetes

El control de acceso basado en roles (RBAC) se utiliza para asignar el acceso a un equipo o a los recursos de la red en el clúster de Kubernetes.

En este artículo, entenderemos los fundamentos del RBAC y crearemos los objetos Role, ClusterRole, RoleBinding y ClusterRoleBinding.

A continuación, crearemos un archivo kubeconfig para dar acceso limitado a un usuario concreto en un espacio de nombres seleccionado.

Pero antes de continuar, entendamos primero lo básico.

  1. Un Rol o ClusterRole contiene un conjunto de permisos.
  2. Un Rol establece los permisos dentro de un espacio de nombres concreto y el ClusterRole es un recurso sin espacio de nombres.
  3. Un RoleBinding concede los permisos definidos en un rol a un usuario o conjunto de usuarios, mientras que el ClusterRoleBinding concede ese acceso a todo el clúster
  4. Un RoleBinding puede hacer referencia a cualquier rol del mismo espacio de nombres. Alternativamente, un RoleBinding puede hacer referencia a un ClusterRole y vincular ese ClusterRole al espacio de nombres del RoleBindin
  5. Un archivo kubeconfig es un archivo utilizado para configurar el acceso a Kubernetes desde la herramienta de línea de comandos kubectl.

Para entender el RBAC en detalle, visita la documentación oficial de Kubernetes aquí.

Note: Refer screenshots to avoid any confusion before executing the commands. ( ubuntu@master = master node and ubuntu@ip-172-31-25-70 = user machine)

Requisitos previos

  1. Cluster de Kubernetes con al menos 1 nodo trabajador.
    Si quieres aprender a crear un Cluster de Kubernetes, haz clic aquí. Esta guía te ayudará a crear un clúster Kubernetes con 1 Maestro y 2 Nodos en Instancias EC2 de AWS Ubuntu 18.04.

¿Qué vamos a hacer?

  1. Crear archivos de objetos Role, Role Binding, Cluster Role, Cluster Role Binding.
  2. Crear objetos Role, Role Binding, Cluster Role, Cluster Role Binding en el cluster.
  3. Proporcionar acceso a los usuarios mediante el archivo kubeconfig.
  4. Resumen de la creación del archivo kubeconfig.

Crear un archivo de objetos Role, Role Binding, Cluster Role Binding.

Crea un archivo para crear un Rol en el espacio de nombres «por defecto» que pueda utilizarse para conceder el acceso get, watch y list a los pods.

vim my-role.yml
kind: Role
apiVersion: rbac.authorization.k8s.io/v1beta1
metadata:
  namespace: default
  name: pod-reader
rules:
- apiGroups: [""]
  resources: ["pods"]
  verbs: ["get", "watch", "list"]

mi-rol

Crea un nuevo archivo para crear un RoleBinding que permita el Role «pod-reader» al usuario «jane» dentro del espacio de nombres «por defecto».

vim my-role-binding.yml
kind: RoleBinding
apiVersion: rbac.authorization.k8s.io/v1beta1
metadata:
  name: read-pods
  namespace: default
subjects:
- kind: User
  name: jane
  apiGroup: rbac.authorization.k8s.io
roleRef:
  kind: Role
  name: pod-reader
  apiGroup: rbac.authorization.k8s.io

mi-role-binding

Crea un archivo para crear un ClusterRole que pueda utilizarse para conceder el acceso «get», «watch» y «list» a los secretos en cualquier espacio de nombres concreto, o en todos los espacios de nombres, dependiendo de cómo se vincule.

vim my-cluster-role.yml
kind: ClusterRole
apiVersion: rbac.authorization.k8s.io/v1beta1
metadata:
  name: secret-reader
rules:
- apiGroups: [""]
  resources: ["secrets"]
  verbs: ["get", "watch", "list"]

mi-rol-cluster

Crea un nuevo archivo para crear un ClusterRoleBinding que permita a cualquier usuario del grupo «manager» leer secretos en cualquier espacio de nombres.

vim my-cluster-role-binding.yml
kind: ClusterRoleBinding
apiVersion: rbac.authorization.k8s.io/v1beta1
metadata:
  name: read-secrets-global
subjects:
- kind: Group
  name: manager
  apiGroup: rbac.authorization.k8s.io
roleRef:
  kind: ClusterRole
  name: secret-reader
  apiGroup: rbac.authorization.k8s.io

mi-cluster-role-binding

Crea un objeto Roles, un objeto vinculado a un rol, un objeto vinculado a un rol de clúster y un objeto vinculado a un rol de clúster.

Obtén una lista de Roles y ClusterRoles existentes en el clúster.

kubectl  get roles
kubectl  get clusterroles

get-default-role-clusterrole

Obtén una lista de RoleBindings y ClusterRoleBindings existentes en el clúster.

kubectl  get rolebinding
kubectl  get clusterrolebinding

get-default-role-binding-clusterrole-binding

Ahora crea un Role, RoleBinding y ClusterRole ClusterRoleBinding utilizando los archivos que hemos creado en los pasos anteriores.

kubectl create -f my-role.yml
kubectl create -f my-role-binding.yml
kubectl create -f my-cluster-role.yml
kubectl create -f my-cluster-role-binding.yml

crear-rol-y-objetos-vinculantes

Con los siguientes comandos verifica si los objetos se han creado.

kubectl  get roles | grep pod-reader
kubectl  get rolebinding | grep read-pods
kubectl  get clusterroles | grep secret-reader
kubectl  get clusterrolebinding | grep read-secrets-global

get-role-and-binding-objects

En la captura de pantalla anterior, puedes ver que se ha creado el Role, RoleBinding y ClusterRole, ClusterRoleBinding.

Proporciona acceso a los usuarios mediante el archivo kubeconfig(config).

Ahora, en esta sección, crearemos un archivo de configuración que pueda ser compartido con un usuario. Para probar este escenario, crearemos un usuario «bob» en el servidor Linux y compartiremos este archivo de configuración con el usuario «bob». A continuación, intentaremos realizar las operaciones permitidas y no permitidas a ese usuario. Vincularemos un ClusterRole de administrador al usuario «bob» que dará acceso a todos los objetos del espacio de nombres «bob».

En los nodos maestros crea una clave y una solicitud de firma de certificado (CSR) utilizando openssl.

pwd
mkdir user-bob
cd user-bob/
openssl req -new -newkey rsa:4096 -nodes -keyout bob-k8s.key -out bob-k8s.csr -subj "/CN=bob/O=devops"
cat bob-k8s.csr | base64 | tr -d '\n'

Crea un archivo de definición del objeto CertificateSigningRequest que contenga la CSR que hemos generado en el paso anterior. En el archivo de abajo añade la salida del comando «cat bob-k8s.csr | base64 | tr -d ‘\n'» a la propiedad «request».

vim k8s-csr.yaml
apiVersion: certificates.k8s.io/v1beta1
kind: CertificateSigningRequest
metadata:
  name: bob-k8s-access
spec:
  groups:
  - system:authenticated
  request: # replace output of: cat bob-k8s.csr | base64 | tr -d '\n'
  usages:
  - client auth
cat k8s-csr.yaml

crear-clave-y-crear-certificado-firmar-archivo-de-objeto-de-solicitud

Crea un objeto CertificateSigningRequest en Kubernetes que contenga el CSR que hemos generado en el paso anterior.

kubectl  get csr
kubectl  create -f k8s-csr.yaml
kubectl  get csr

Ahora queremos aprobar el objeto CSR (CertificateSigningRequest) que hemos creado en el paso anterior.

kubectl  get csr
kubectl certificate approve bob-k8s-access
kubectl  get csr

aprobar-solicitud-de-firma-de-certificado

En la captura de pantalla anterior, puedes ver que el CSR ha sido Aprobado, Emitido.

Recupera el certificado disponible en el campo ‘status.certificate’ del objeto CSR.

ls -lt
kubectl get csr bob-k8s-access -o jsonpath='{.status.certificate}' | base64 --decode > bob-k8s-access.crt
ls -lt
cat bob-k8s-access.crt

recuperar-el-certificado

Recupera el certificado de la CA del clúster que es el siguiente requisito para el archivo kubeconfig de Bob y guárdalo en el archivo «k8s-ca.crt».

ls -lt
kubectl config view -o jsonpath='{.clusters[0].cluster.certificate-authority-data}' --raw | base64 --decode - > k8s-ca.crt
ls -lt
cat k8s-ca.crt

get-cluster-CA-certificate

Establece la configuración del clúster en el archivo kubeconfig de Bob. Todos estos detalles se pondrán a partir de nuestro kubeconfig existente utilizando el siguiente comando.

ls -lt
kubectl config set-cluster $(kubectl config view -o jsonpath='{.clusters[0].name}') --server=$(kubectl config view -o jsonpath='{.clusters[0].cluster.server}') --certificate-authority=k8s-ca.crt --kubeconfig=bob-k8s-config --embed-certs
ls -lt
cat bob-k8s-config

configuración del clúster para bob

Configura el usuario que importará la clave y el cert de Bob en el archivo de configuración.

ls -lt
kubectl config set-credentials bob --client-certificate=bob-k8s-access.crt --client-key=bob-k8s.key --embed-certs --kubeconfig=bob-k8s-config
ls -lt
cat bob-k8s-config

configuración-del-usuario-bob

Crea un contexto para el archivo config de «Bob» utilizando el siguiente comando.

ls -lt
kubectl config set-context bob --cluster=$(kubectl config view -o jsonpath='{.clusters[0].name}') --namespace=bob --user=bob --kubeconfig=bob-k8s-config
ls -lt
cat bob-k8s-config

configurar-el-contexto-para-bob-configuración

Crea un espacio de nombres para Bob

kubectl  get ns
kubectl create ns bob
kubectl  get ns -o wide
kubectl label ns bob user=bob env=sandbox
kubectl  get ns -o wide

crear un espacio de nombre y etiquetarlo

Especifica el contexto que utilizará Bob para sus comandos kubectl.

cat bob-k8s-config
kubectl config use-context bob --kubeconfig=bob-k8s-config
cat bob-k8s-config

set-contexto-actual

Copia «bob-k8s-config» del nodo maestro al archivo «.kube/config» en el directorio principal de Bob y prueba la kubeconfig de Bob ejecutando la ‘versión kubectl’.

vim .kube/config #All the output of "cat bob-k8s-config" command ran on the master node and save it to /home/bob/.kube/config on the user machine.
kubectl version #Execute this on the user machine

compartir-el-archivo-de-configuración-con-el-usuario-bob

Prueba los permisos ejecutando los siguientes comandos desde la máquina del usuario.

kubectl  get nodes
kubectl  get pods
kubectl  get ns
kubectl  get deployments
kubectl  get all

bob-no-tiene-permisos-aún

En la captura de pantalla anterior puedes ver que el usuario «Bob» no puede realizar ninguna operación, ya que no se le ha dado acceso.

Asigna el rol de clúster «admin» por defecto a Bob para crear la mayoría de los tipos de objetos Kubernetes dentro de su espacio de nombres. Este rol «bob-admin» dará acceso de administrador al usuario «Bob» en el espacio de nombres «bob» utilizando el ClusterRole «admin».

Ejecuta el siguiente comando en el nodo maestro.

kubectl create rolebinding bob-admin --namespace=bob --clusterrole=admin --user=bob 
kubectl  get rolebinding
kubectl  get clusterrole | grep  admin

create-rolebinding-with-admin-clusterrole-for-bob-namespace-only

Obtén los espacios de nombre creados para Bob.

Ahora, ejecuta todos los siguientes comandos desde la máquina del usuario.

kubectl  get ns
kubectl  get ns bob

validar-acceso-en-el-espacio-de-nombres

En la captura de pantalla anterior puedes ver que el usuario «Bob» no puede listar los recursos del «espacio de nombres».

Crea un Pod en el espacio de nombres «bob» establecido como espacio de nombres por defecto en el archivo kubeconfig de Bob.

kubectl  run nginx --image=nginx
kubectl  get pods
kubectl  get pods -o wide

Comprueba el espacio de nombres actual establecido como espacio de nombres por defecto

kubectl config get-contexts

crear-pod-en-el-espacio-de-nombres-permitido

En la captura de pantalla anterior, puedes ver que «Bob» puede crear un Pod en el espacio de nombres «bob», ya que hemos vinculado el rol «admin» al usuario «Bob» para el espacio de nombres «bob».

Intenta crear un pod en un espacio de nombres «predeterminado» en el que Bob no tenga ningún permiso. Como hemos permitido que el usuario «Bob» sólo pueda crear objetos en el espacio de nombres «bob», el usuario Bob no podrá crear ningún recurso en otro espacio de nombres que no sea «bob».

kubectl  run nginx-2 --image=nginx --namespace=default

pod-creation-fails-in-other-namespace

Comprueba el espacio de nombres establecido como espacio de nombres por defecto en el archivo kubeconfig. Esto muestra que el espacio de nombres «bob» está establecido como espacio de nombres por defecto en el archivo de configuración.

kubectl config view --minify | grep namespace:

check-current-namespace-set-as-default-namespace-in-config-file

Resumen de la creación del archivo Kubeconfig

  1. Crea una clave y una solicitud de firma de certificado (CSR) con openssl.
  2. Crea un archivo de definición del objeto CertificateSigningRequest.
  3. Crea un objeto CertificateSigningRequest.
  4. Aprobar la CSR (CertificateSigningRequest).
  5. Recuperar el certificado del objeto CSR.
  6. Recuperar el certificado de la CA del clúster.
  7. Establecer la configuración del clúster en el archivo kubeconfig.
  8. Configurar el usuario.
  9. Crear un contexto.
  10. Crear un espacio de nombres para el usuario.
  11. Especifica el contexto en el archivo kubeconfig.
  12. Pasa la kubeconfig al usuario.
  13. Prueba los permisos utilizando el archivo de configuración del usuario.
  14. Asigna el rol al usuario
  15. Prueba los permisos de nuevo utilizando el archivo de configuración del usuario.

Conclusión

En este artículo hemos visto los fundamentos de Role, RoleBinding y ClusterRole, ClusterRoleBinding, también hemos creado estos objetos en nuestro cluster. A continuación, hemos creado un archivo de configuración que permite a un usuario concreto realizar operaciones en un espacio de nombres determinado. Vimos cómo RBAC puede ayudarnos a restringir el acceso al clúster de Kubernetes.

También te podría gustar...