Skip to content

Build K3s Cluster from Scratch

Use this guide to provision a bare-metal Kubernetes cluster on Ubuntu 26.04 using Ansible and K3s with this repo as the single source of truth. One command takes a machine from base OS to a running GitOps-managed cluster.

Review the host target in ansible/inventory/hosts.yaml and cluster settings in ansible/group_vars/all.yaml. Ensure SSH access and sudo privileges are active on the target machine.

all:
children:
k3s_cluster:
children:
k3s_servers:
hosts:
legion:
ansible_host: 100.66.139.118
ansible_user: sudhanva
ansible_ssh_common_args: "-o StrictHostKeyChecking=accept-new"
k3s_node_ip: "100.66.139.118"
k3s_external_ip: "100.66.139.118"

Run the automated provisioning script from the repository root:

Terminal window
./scripts/provision.sh

The script executes the Ansible playbook ansible/site.yaml which handles:

  • Host prerequisites: Kernel modules (overlay, br_netfilter), sysctls, and storage path creation on the dedicated SSD (/home/k3s-storage).
  • NVIDIA integration: Installs NVIDIA Container Toolkit, generates CDI specifications, and configures containerd GPU runtime.
  • Tailscale: Verifies Tailscale is running and disables Tailscale DNS on the node so the host resolves through its upstream network resolvers.
  • K3s Server: Installs K3s, disables Traefik and ServiceLB, uses the Tailscale IP as the node IP, reserves CPU and memory for the system, orders K3s after tailscaled, and starts the systemd service.
  • Kubeconfig: Fetches the cluster credentials and configures the Tailscale endpoint.
  • GitOps bootstrap: Deploys ArgoCD with server-side apply and applies the root Application (bootstrap/root.yaml).

Confirm the node is ready and pods are running:

Terminal window
export KUBECONFIG="./k3s.kubeconfig"
kubectl get nodes -o wide
kubectl get pods -A
kubectl get apps -n argocd

Step 4: Configure Vault and External Secrets

Section titled “Step 4: Configure Vault and External Secrets”

Follow Vault to initialize Vault and sync the required secrets for ExternalDNS, cert-manager, and the Tailscale operator.