Kubernetes Cluster using RKE2 HA and Rancher
I will show how to install kubernetes cluster with High Availibility using RKE2 and install Rancher to manage the cluster under ubuntu. To simplify access to the application deployed in the cluster, I set up nginx as load balancer to forward domain name request to the application. Here, I use simple ansible script to install the cluster.
Server Architecture
Ansible host configuration
[allnode:children] rke2-firstnode rke2-nextnode [rke2-firstnode] rke2-node1 ansible_host=192.168.1.11 [rke2-nextnode] rke2-node2 ansible_host=192.168.1.12 rke2-node3 ansible_host=192.168.1.13
--- - hosts: allnode become: true tasks: - name: Copy Proxy Config copy: src: proxy dest: /etc/default/proxy mode: '0644' tags: [ 'envproxy', 'proxy' ] - name: Copy APT Proxy Config copy: src: proxy.conf dest: /etc/apt/apt.conf.d/proxy.conf mode: '0644' tags: [ 'aptproxy', 'proxy' ] - name: Insert Proxy Env lineinfile: path: /etc/environment line: '{{ item }}' with_items: - 'HTTP_PROXY="http://192.168.1.1:3128"' - 'HTTPS_PROXY="http://192.168.1.1:3128"' - 'NO_PROXY="127.0.0.0/8,10.0.0.0/8,192.168.1.0/16,*.mydomain.com"' tags: [ 'envproxy', 'proxy' ] - hosts: rke2-firstnode become: true tasks: - name: create directory with parent directories file: path: /etc/rancher/rke2 state: directory recurse: yes tags: [ 'rke-config'] - name: create directory with parent directories file: path: /var/lib/rancher/rke2/server/manifests state: directory recurse: yes tags: [ 'rke-config'] - name: Copy Master Config copy: src: config-master.yaml dest: /etc/rancher/rke2/config.yaml mode: '0644' tags: [ 'master','rke-config'] - name: Run RKE2 script shell: cmd: curl -sfL https://get.rke2.io | sh - warn: False tags: [ 'download'] - name: Add proxy in rke init script lineinfile: path: /usr/local/lib/systemd/system/rke2-server.service insertbefore: 'EnvironmentFile=-/etc/default/%N' line: EnvironmentFile=/etc/default/proxy - name: Copy Nginx Config copy: src: rke2-ingress-nginx-custom.yaml dest: /var/lib/rancher/rke2/server/manifests/rke2-ingress-nginx-custom.yaml mode: '0644' tags: [ 'master','rke-config'] - name: Enable RKE2 script shell: cmd: systemctl enable rke2-server.service warn: False - name: Reload systemd shell: cmd: systemctl daemon-reload warn: False - name: Start RKE2 script shell: cmd: systemctl start rke2-server.service warn: False - hosts: rke2-nextnode become: true tasks: - name: create directory with parent directories file: path: /etc/rancher/rke2 state: directory recurse: yes - name: create directory with parent directories file: path: /var/lib/rancher/rke2/server/manifests state: directory recurse: yes tags: [ 'rke-config'] - name: Copy Slave Config copy: src: config-slave.yaml dest: /etc/rancher/rke2/config.yaml mode: '0644' tags: [ 'slave','rke-config'] - name: Run RKE2 script shell: cmd: curl -sfL https://get.rke2.io | sh - warn: False tags: [ 'download'] - name: Add proxy in rke init script lineinfile: path: /usr/local/lib/systemd/system/rke2-server.service insertbefore: 'EnvironmentFile=-/etc/default/%N' line: EnvironmentFile=/etc/default/proxy - name: Copy Nginx Config copy: src: rke2-ingress-nginx-custom.yaml dest: /var/lib/rancher/rke2/server/manifests/rke2-ingress-nginx-custom.yaml mode: '0644' tags: [ 'master','rke-config'] - name: Enable RKE2 script shell: cmd: systemctl enable rke2-server.service warn: False - name: Reload systemd shell: cmd: systemctl daemon-reload warn: False - name: Start RKE2 script shell: cmd: systemctl start rke2-server.service warn: False
- proxy
- proxy.conf
- config-master.yaml
- rke2-ingress-nginx-custom.yaml
HTTP_PROXY=http://192.168.1.1:3128 HTTPS_PROXY=http://192.168.1.1:3128 NO_PROXY=127.0.0.0/8,10.0.0.0/8,192.168.1.0/16,*.mydomain.com
Acquire::http::Proxy "http://192.168.1.1:3128/"; Acquire::https::Proxy "https://192.168.1.1:3128/";
tls-san: - "mydomain.com" - "192.168.1.11" - "192.168.1.12" - "192.168.1.13"
apiVersion: helm.cattle.io/v1 kind: HelmChartConfig metadata: name: rke2-ingress-nginx namespace: kube-system spec: valuesContent: |- controller: kind: DaemonSet daemonset: useHostPort: true
Install the First Node
ansible-playbook rke2-ha.yml -i rke2-hosts -l rke2-node1
server: https://master.mydomain.com:9345 token: [token from /var/lib/rancher/rke2/server/node-token] tls-san: - "mydomain.com" - "192.168.1.11" - "192.168.1.12" - "192.168.1.13"
Install the rest of Node
ansible-playbook rke2-ha.yml -i rke2-hosts -l rke2-nextnode
/var/lib/rancher/rke2/bin/kubectl \ --kubeconfig /etc/rancher/rke2/rke2.yaml get nodes NAME STATUS ROLES AGE VERSION rke2-node1 Ready control-plane,etcd,master 1m v1.21.4+rke2r2 rke2-node2 Ready control-plane,etcd,master 1m v1.21.4+rke2r2 rke2-node3 Ready control-plane,etcd,master 1m v1.21.4+rke2r2
Installing Rancher (Kubernetes Dashboard Management)
After your cluster is up, you can already manage and deploy application using kubectl tools, but it'll be much more easy to manage the cluster from web interface. We use Rancher for that. To install rancher, you must do the following step from any rke2 nodes
Install helm
To install helm you can download the script from their website:
curl -fsSL -o get_helm.sh https://raw.githubusercontent.com/helm/helm/master/scripts/get-helm-3 chmod 700 get_helm.sh ./get_helm.sh
Add Latest Helm Repo
helm repo add rancher-latest https://releases.rancher.com/server-charts/latest
Create a Namespace for Rancher
kubectl create namespace cattle-system
Install cert-manager
I use Rancher Generated Certificates, so the command will be:
# If you have installed the CRDs manually instead of with the `--set installCRDs=true` option added to your Helm install command, you should upgrade your CRD resources before upgrading the Helm chart: kubectl apply -f https://github.com/jetstack/cert-manager/releases/download/v1.5.1/cert-manager.crds.yaml # Add the Jetstack Helm repository helm repo add jetstack https://charts.jetstack.io # Update your local Helm chart repository cache helm repo update # Install the cert-manager Helm chart helm install cert-manager jetstack/cert-manager \ --namespace cert-manager \ --create-namespace \ --version v1.5.1
Wait until the cert-manager installed successfully and check using this command:
kubectl get pods --namespace cert-manager NAME READY STATUS RESTARTS AGE cert-manager-5c6866597-zw7kh 1/1 Running 0 2m cert-manager-cainjector-577f6d9fd7-tr77l 1/1 Running 0 2m cert-manager-webhook-787858fcdb-nlzsq 1/1 Running 0 2m
Install Rancher using helm
helm install rancher rancher-latest/rancher \ --namespace cattle-system \ --set hostname=rancher.mydomain.com \ --set replicas=3 \ --set proxy="http://192.168.1.1:3128/" \ --set noProxy=".mydomain.com\,127.0.0.0/8\,192.168.1.0/16\,10.0.0.0/8"
Wait until deployment is finish, check the deployment status
kubectl -n cattle-system get deploy rancher NAME DESIRED CURRENT UP-TO-DATE AVAILABLE AGE rancher 3 3 3 3 3m
To access rancher, you must configure your DNS and Nginx because it uses domain to resolve the application
Configure DNS
Add this following entry into your DNS configuration
*.mydomain.com. IN A 192.168.1.1
Configure Nginx
Below is Nginx configuration that can be used to forward the request to the RKE2 cluster, put this config inside http section:
upstream kube { server 192.168.1.11:80; server 192.168.1.12:80; server 192.168.1.13:80; } server { listen 443 ssl; error_log /var/log/nginx/kubes-error.log; ssl_certificate /etc/ssl/private/kube.crt; ssl_certificate_key /etc/ssl/private/kube.key; # Support for wildcard domains server_name *.mydomain.com; location / { access_log off; proxy_pass http://kube; proxy_set_header Host $host; proxy_set_header X-Real-IP $remote_addr; proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; } } server { listen 80; error_log /var/log/nginx/kubes-error.log; # Support for wildcard domains server_name *.mydomain.com; return 301 https://$host$request_uri; }
Inside Main section:
stream { map $ssl_preread_server_name $name { rancher.mydomain.com rancher_servers_https; } upstream rancher_servers_https { least_conn; server 192.168.1.11:443 max_fails=3 fail_timeout=5s; server 192.168.1.12:443 max_fails=3 fail_timeout=5s; server 192.168.1.13:443 max_fails=3 fail_timeout=5s; } server { listen 8443; proxy_pass $name; ssl_preread on; } }
Please remember to pointing the ip to the agent node, not master node if you add more agent node. If everything are fine, you can access rancher in this url https://rancher.mydomain.com:8443
Using rancher you can deploy application using marketplace or using custom yaml, you can assign domain to application for example: grafana.mydomain.com without needed to configure DNS again, because all domain using mydomain.com will be forwarded to rke2 cluster.
Comments