Deliver Rancher with Cloud-init and Terraform

In my previous posts, I already showed how with a simple vanilla template and cloud-init template it’s possible to create a fully customized workload without “manual” interventions respecting the declarative methods where possible and in the same time injecting scripts able to prepare the virtual machine for the real purpose of the workload. In this post, I’ll show how to deliver a production-ready Rancher cluster following the same declarative method.

You can find the fully-function project on my GitHub repo here: https://github.com/linoproject/terraform/tree/master/rancher-lab

The single docker host method could be an easy way to test Rancher service, but it lacks resiliency and in some enterprise contexts it could result inefficient. For this reason following the official Rancher 2.x documentation, the best way to deliver Rancher is by the creation of a single-node K8S cluster using RKE (Rancher Kubernetes engine) and the Rancher installation as Helm deployment.

After docker, kubectl, and Helm and RKE (Rancher Kubernetes engine), the installation workflow is composed by:

  1. RKE up the first cluster
  2. Cert-manager installation
  3. Rancher installation by a Helm chart

After these steps rancher is ready to be configured with admin credentials, connections, templates,… and the first cluster. Let’s dive into the first step: the init

The init steps

The installation process is quite long and depending on your resources could result in a little bit hard to handle using a single cloud-init step. For this reason, the idea is to keep the VM preparation inside the cloud-init process and proceed using a remote-exec to inject the installation step as a flow of some imperative commands.

Checking the user-data file located under nodes/rancher/cloudinit the init steps are two:

  • The file creations: the first single node cluster and the installation script could be delivered using the write_file statement, which is served before the runcmd statement.
  • The environment setup commands which are running in runcmd statement and includes the first steps

At the end of the init-process the VM is prepared for the real installation. With the benefits of the template handling with Terraform, it’s possible to prepare and customize the cluster init like IP, hostname, and domain name.

Before proceeding, in order to speed up the process, I prepared the “default template” starting from another bunch of Terraform files and a single cloud-init file that contains the kick-off system (local-user and VMware vSphere cloud-init implementation like described here). After the VM creation with a simple cloud-to-template the template is ready for the real deployment. (You can check the example on my GitHub here: https://github.com/linoproject/terraform/tree/master/template-prep-adv ). This intermediate template will include:

  • cloud-init VMware integration
  • Kubectl, Helm, and RKE
  • User ubuntu directly involved in the installation process.

Rancher installation steps

Finally, the real installation process starts with:

  1. RKE up based on rancher-cluster.yml config
  2. Cert-manager installation using Helm
  3. Rancher installation

During the cert-manager installation, it’s necessary to wait for the complete rollout before going ahead with the installation. Then after Rancher Helm installation, a loop is checking for the readiness of the cluster and the ability to connect with your browser to https://<hostname.domainname>.

I suggest using Firefox because it is one of the browsers that still bypass the restriction of the unverified certificate which is used in this installation. An enterprise installation should implement a real certificate issued by a real CA.

After setting the admin password it is possible to start deploying the first cluster like as seen here.

A final note

In the “main.tf” file, I introduced also a workaround way to set DNS record A with the rancher machine. It simply injects a PowerShell script able to test and add or modify the DNS record. Depending on your installation, you could skip this process by simply commenting out the null_resorce called “dnsrecord” or introducing your own automation step to correctly handle the DNS registration.

If you have any suggestions on how to improve this code, feel free to reach me via the contact form.

   Send article as PDF