Gestionar certificados SSL puede ser un dolor de cabeza, pero por suerte en Kubernetes podemos usar cert-manager y dejar que éste se encargue de todo para crear de forma fácil cualquier certificado que necesitemos.
En este how-to vamos a cubrir desde la instalación de cert-manager a cómo configurarlo para realizar la validación por HTTP. También aprenderemos a crear un nuevo certificado para nuestro host simplemente añadiendo una annotation a nuestro ingress.
¡Suena bien! ¿Qué necesito?
Deberías cumplir con estos requisitos:
- Tener un clúster k8s funcional con nginx como ingress-controller
- Tener helm instalado (lee aquí cómo instalar helm)
- Tener un dominio en tu posesión que apunte hacia el clúster
- Ganas de aprender algo nuevo 🙂
¡Empecemos!
Primero necesitamos añadir el repositorio de helm para cert-manager:
helm repo add jetstack https://charts.jetstack.io
Ahora procederemos a crear el nuevo namespace y hacer el deploy de cert-manager:
kubectl create ns cert-manager helm upgrade --install cert-manager --namespace cert-manager --version v1.0.3 jetstack/cert-manager --set installCRDs=true
Dale unos segundos de margen para que termine y deberías ver un mensaje de finalización con éxito.
Creando un ClusterIssuer
Podemos usar tanto un Issuer como un ClusterIssuer (namespace vs cluster-scoped). Es exactamente lo mismo, solo cambia el scope. El Issuer/ClusterIssuer representa la CA de la que queremos obtener el nuevo certificado, en este caso usaremos LetsEncrypt.
Fíjate a continuación que el objeto ClusterIssuer realmente es muy simple. Tanto el nombre como el nombre del secret pueden ser lo que tú quieras:
apiVersion: cert-manager.io/v1alpha3 kind: ClusterIssuer metadata: name: my-cluster-issuer spec: acme: email: {{ tu email }} privateKeySecretRef: name: my-cluster-issuer server: https://acme-v02.api.letsencrypt.org/directory solvers: - http01: ingress: class: nginx
Expidiendo un nuevo certificado
Vamos a hacer un deploy muy simple con un nginx, lo expondremos como servicio y después crearemos un ingress. Así pues, vamos allá:
kubectl create deployment nginx --image nginx:alpine --namespace test kubectl expose deployment nginx --port 80 --target-port 80 --namespace test
Ahora crearemos un nuevo objeto ingress para hacer accesible el servicio a través del ingress controller. Recuerda reemplazar a continuación las ocurrencias del host con tu propio dominio:
apiVersion: extensions/v1beta1 kind: Ingress metadata: annotations: nginx.ingress.kubernetes.io/ssl-redirect: "true" labels: app: nginx name: nginx namespace: test spec: rules: - host: nginx.{{ tu dominio }} http: paths: - backend: serviceName: nginx servicePort: 80 path: / tls: - hosts: - nginx.{{ tu dominio }} secretName: nginx-certificate
Aplicamos el nuevo manifest:
kubectl apply -f ingress.yaml
Si ahora intentas acceder al host que has definido en el ingress verás un mensaje de error conforme tu certificado no es válido («Your connection is not private»). Para solucionarlo, vamos a expedir un nuevo certificado. Edita el ingress que has creado y añade la siguiente anotación, reemplazando el valor por el nombre que hayas puesto en tu ClusterIssuer:
cert-manager.io/cluster-issuer: my-cluster-issuer
Aplica el ingress de nuevo (o guarda los cambios si estás haciendo un edit) y revisa el estado del objeto «cert». Deberías ver algo así:
kubectl get cert -n test NAME READY SECRET AGE nginx-certificate False nginx-certificate 21s
Ahora espera 1 o 2 minutos y cuando lo revises de nuevo…
kubectl get cert -n test NAME READY SECRET AGE nginx-certificate True nginx-certificate 93s
… ¡hemos conseguido el certificado! Haz un test refrescando la página o abriendo una nueva pestaña y deberías ver el mensaje de bienvenida de Nginx. Si inspeccionas el certificado, verás que efectivamente éste ha sido expedido por LetsEncrypt:
Resumiendo
Lo que hemos visto aquí es:
- Como instalar cert-manager
- Como configurar un nuevo ClusterIssuer
- Como expedir de forma sencilla un certificado
En líneas generales ha sido un proceso simple, ¿verdad? Es más, cuando sabes cómo funciona es muy fácil replicar este setup en cualquier clúster en cuestión de unos pocos minutos.
Cert-manager se encargará de la renovación de tus certificados. También puedes crear otros Issuers o ClusterIssuers que soporten otros CA o usar otros métodos de validación (DNS), pero eso es un tema algo más avanzado que dejaremos para más adelante.
Espero que hayas disfrutado con este how-to y que haya resultado útil. Recuerda que si necesitas cualquier cosa estaremos encantados de escucharte. ¡También puedes revisar nuestro blog para encontrar otras publicaciones útiles como ésta!