
By default, Kubernetes requires you to manage some portions of your application by hand, such as DNS records and TLS certificates. But wouldn't it be better to define your desired DNS and TLS alongside the application manifests?
The good news is that you can use two open-source Kubernetes plugins to automate the process. This guide explains how to install and configure ExternalDNS for DNS management in your manifests and cert-manager to handle certificate management.
To follow this guide, you'll need:
You should also know how to:
Log in to the registrar where you purchased your domain and set the nameserver (NS) records to Vultr's name servers: * ns1.vultr.com * ns2.vultr.com
Use vultr-cli to create a new DNS zone at Vultr.
Verify the zone with vultr-cli.
Cert-manager, at a high level, is a custom Kubernetes resource that allows for certificate management natively within Kubernetes.
Cert-manager can:
Vultr offers custom cert-manager webhooks so users can issue certificates as YAML manifests. In the specific use case for this guide, you'll use the Vultr cert-manager-webhook plugin, which handles TLS certificates for your domains.
In this step, you'll install the base cert-manager and the Vultr-specific cert-manager-webhook.
First, install the base cert-manager with kubectl apply as described in the cert-manager documentation.
After applying the YAML, uou can inspect the related resources in the cert-manager namespace.
Next, create a secret that contains your Vultr API key. Cert-manager uses this secret to create the DNS entries required for domain validation.
Now install the Vultr-specific cert-manager-webhook with Helm.
Verify that the Vultr webhook is running by inspecting the cert-manager namespace.
To issue certificates, you must create YAML definitions for a ClusterIssuer and grant permissions to the service account.
A ClusterIssuer represents the Certificate Authority (CA) used to create the signed certificates.
This example uses the LetsEncrypt staging environment. For production, use
https://acme-v02.api.letsencrypt.org/directory.
You must grant permissions to the service account for it to grab the secret. Deploy Role-based access control (RBAC), like this:
Apply the YAML. After you deploy the ClusterIssuer and RBAC, you can request TLS certificates from LetsEncrypt for domains hosted on Vultr.
The Certificate resource is the human-readable certificate request definition that is honored by an issuer and kept up-to-date. Here's an example:
Here's a description of the key fields:
Kubernetes create a few more resources after creating the Certificate kind. They are:
order for a signed TLS certificate.challenge, which must be completed for an authorization for a single DNS name.Here is an example kubectl output:
See the Concepts section of the cert-manager documentation to learn more about these resources.
The validation of the certificate takes a few minutes. You can check the status with Kubectl:
Check the Ready state of the certificate. When it returns True, your valid TLS certificate from LetsEncrypt is stored in the secret name you defined in the certificate YAML.
Remember that this example ClusterIssuer points to the LetsEncrypt staging environment. For production, please use https://acme-v02.api.letsencrypt.org/directory.
You have automated TLS for your domain on Kubernetes!
Next, you'll set up ExternalDNS to automatically create DNS entries and relate them to the service IP addresses for the ingress or loadbalancer services in Kubernetes.
The ExternalDNS installation at Vultr is straightforward. You can install ExternalDNS with the following YAML manifest.
Here's a description of the key fields in the Deployment Spec args section:
ingress, or pair ExternalDNS with a regular loadbalancer service.txt to create a TXT record that accompanies each record created by external-dns.Apply the external-dns YAML and verify it's running correctly by inspecting the pod.
After ExternalDNS is running, you can add annotations to your service manifests for DNS entries.
External-dns and Cert-manager ensure you always have valid TLS certificates. To test this, deploy a simple application and expose it to the public internet on HTTPS. For example, this is a single replica deployment of Nginx and a clusterIP service that routes to the deployment.
To expose the Nginx deployment to the internet, use ingress-nginx, or a loadbalancer service type instead of an ingress. If you use loadbalancer, change the type from ingress to service in your external DNS YAML.
To use Kubernetes Nginx ingress, apply the prepared manifests from the ingress controller quick start guide.
This creates a new namespace, ingress-nginx, for the ingress resources. Here's an example ingress entry that exposes and Nginx app.
external-dns.alpha.kubernetes.io/hostname: www.example.com annotation defines what entry ExternalDNS should create. In this case, it creates an A record for www that points to the load balancer deployed by the ingress.tls.hosts section defines which domain the ingress should treat as HTTPS.secretName has the issued TLS certificates.rules.host section defines what URL should route to which service. In this example, www.example.com/ should go to this Nginx service deployment.After you deploy the ingress, inspect it with Kubectl.
Kubernetes and the DNS system will take a few minutes to propagate the requests and domain records, and then you should have a domain backed with HTTPS.
To recap what you've accomplished:
With these three tools at your disposal, you can define your application's entire state in YAML manifests and let Kubernetes handle the rest.
For more information, see these useful resources:
0 Comments
Be the first to comment and share your perspective with the community.