RBAC con Kubernetes en Minikube
Tags: kubernetes, spanish, docker
Published: 2020-06-23 14:03:04

![Alt Text](https://dev-to-uploads.s3.amazonaws.com/i/9u7rvubwhxhd8767ji8y.jpg)

Holaaa gente, seguimos con temas de Kubernetes. Para aquell@s que se han preguntado sobre como manejar manejar aspectos de permisos y roles dentro del cluster de K8s, pues acá les tengo un post al respecto. Los guiaré sobre cómo usar RBAC con Minikube. El objetivo es crear usuarios con acceso limitado y controlado a los recursos de kubernetes.

RBAC o control de acceso basado en roles es un enfoque de seguridad para otorgar acceso a recursos específicos a usuarios asignados.

<h2>Pero antes debes saber esto</h2>
Pero antes de crear un usuario y otorgarle permisos, necesitamos saber algunas cosas sobre la Administración de usuarios en Kubernetes: no tiene una API para crear usuarios. Sin embargo, puede autenticar y autorizar a los usuarios.

Para autenticar las solicitudes de API, k8s utiliza las siguientes opciones: certificados de cliente, tokens, proxy de autenticación o autenticación básica HTTP.

En este blog post utilizaré la autenticación basada en certificados para agregar usuarios.   
Kubernetes se crea utilizando una Autoridad de certificación (CA).Todos los certificados SSL firmados con esta CA serán aceptados por la API de Kubernetes.
Posibles opciones para crear certificados: OpenSSL o el Kit de herramientas PKI de CloudFlare. En este blog post usaré OpenSSL. Dos campos importantes en los certificados SSL: Nombre común (CN): Kubernetes interpretará este valor como el Usuario. Organización (O): Kubernetes interpretará este valor como el Grupo.


<h2>Manos a la obra</h2>

<h3>1. Crear un certificado de cliente</h3>
Crearemos una solicitud de clave y firma de certificado (CSR) necesaria para crear el certificado. Vamos a crear un directorio donde guardar los certificados. Lo llamaré cert:
```
mkdir cert && cd cert
```
Voy a generar una clave usando OpenSSL:
```
openssl genrsa -out developer.key 2048
```
Lo siguiente es generar una solicitud de firma de cliente (CSR):
```
openssl req -new -key developer.key -out developer.csr -subj "/CN=developer/O=devs"
```

Hasta acá, todo bien. Ejecutemos los siguientes comandos 
```
cd ~/.minikube
ls
``` 
y compruebe que los archivos ca.crt y ca.key existan en esta ubicación. Además, mueva los archivos  developer.key y developer.csr (creados anteriormente)  dentro de este directorio.

Lo siguiente es generar el certificado (CRT):

```
openssl x509 -req -in developer.csr -CA ~/.minikube/ca.crt -CAkey ~/.minikube/ca.key -CAcreateserial -out developer.crt -days 500
```
Listos con el certificado, ahora que tenemos .key y .crt, podemos crear un usuario.

<h3>2- Crear un usuario</h3>

<h4>2.1. Establecer una entrada de usuario en kubeconfig</h4>
```
kubectl config set-credentials developer --client-certificate = developer.crt --client-key = developer.key
```

<h4>2.2. Establecer una entrada de contexto en kubeconfig</h4>
```
kubectl config set-context dev-context --cluster = minikube --user = developer
```
Verifiquemos que se haya agregado correctamente a kubeconfig:

```
kubectl config view
```

<h4>2.3. Cambiar al usuario creado</h4>
Ahora, en lugar de usar el contexto minikube, queremos usar dev-context:
```
$ kubectl config use-context developer-context
$ kubectl config current-context # comprueba el contexto actual
developer-context
```

Pero, ahora, el usuario developer  no tiene privilegios de acceso al clúster. Debido a eso tendremos acceso denegado si intentamos crear algún recurso:
```
kubectl create namespace ns-test
Error from server (Forbidden): namespaces is forbidden: User "developer" cannot create resource "namespaces" in API group "" at the cluster scope
```

<h3>3. Conceder acceso al usuario</h3>
Para dar acceso a la administración de los recursos de k8s al usuario developer, necesitamos crear un Rol y un BindingRole.

<h4>3.1. Crear un role</h4>
Creemos un objeto Role en el archivo role.yaml. El Rol definirá a qué recursos se podría acceder y qué operaciones / verbos se podrían usar.
```
kind: Role
apiVersion: rbac.authorization.k8s.io/v1
metadata:
  namespace: default
  name: pod-reader
rules:
- apiGroups: [“”] # “” indicates the core API group
  resources: [“pods”]
  verbs: [“get”, “watch”, “list”]
```

Recursos: pod, deployment, namespace, secret, configmap, service, persistentvolume…

Verbos: get, list, watch, create, delete, update, edit, exec.

<h4>3.2. Crear un BindingRole</h4>
Queremos hacer coincidir el usuario developer con el rol creado anteriormente llamado: pod-reader. Para hacer eso, necesitamos usar RoleBinding.
```
kind: RoleBinding
apiVersion: rbac.authorization.k8s.io/v1
metadata:
  name: read-pods
  namespace: default
subjects:
- kind: User
  name: developer # Name is case sensitive
  apiGroup: rbac.authorization.k8s.io
roleRef:
  kind: Role #this must be Role or ClusterRole
  name: pod-reader # must match the name of the Role
  apiGroup: rbac.authorization.k8s.io
```

Lo siguiente es implementar el role.yaml y role-binding.yaml en k8s en el contexto de minikube:
```
kubectl config use-context minikube
Switched to context "minikube".
kubectl apply -f role.yaml
role.rbac.authorization.k8s.io/pod-reader created
kubectl apply -f role-binding.yaml
rolebinding.rbac.authorization.k8s.io/read-pods created
```

Verifiquemos que Role and BindingRole se hayan creado correctamente:
```
kubectl get roles
NAME       AGE
pod-reader 2m

kubectl get rolebindings
NAME        AGE
read-pods   2m
```
Por cierto, utilizamos Role para abarcar las reglas a un solo namespace, pero también podemos usar ClusterRole para definir más de un espacio de nombres y cubrir el cluster. RoleBinding se usa para enlazar a Role y ClusterRoleBinding se usa para enlazar a ClusterRole.

<h3>4- Llegó la hora de probar las operaciones permitidas para el usuario</h3>

Vuelva a cambiar al contexto dev-context e intente una de las operaciones no permitidas como crear un espacio de nombres. Esto fallará porque el usuario developer no tiene permiso para hacerlo.

```
kubectl config use-context dev-context
kubectl create namespace ns-test # won't succeed, Forbidden
```
Pero, cuando intente una de las operaciones permitidas, como obtener los pods:

```
kubectl get pods # this will succeed !
```

Al final, hemos creado un usuario con acceso limitado a los recursos de k8s. El usuario developer se autenticará a través de su certificado y se le otorgará acceso a través de Role y RoleBinding.

Si deseas saber más sobre Kubernetes, te invito a seguir mi canal en youtube:

{% youtube 8VGveS41xUU %}

Facebook: https://www.facebook.com/falconcoach87
Twitter: https://twitter.com/gelopfalcon