Kubernetes su Hetzner con Talos: Parte 1 - Bootstrap dei Nodi Control Plane
Panoramica
Questo è il primo articolo della serie su come configurare un cluster Kubernetes su Hetzner Cloud utilizzando Talos. In questo articolo, ci concentreremo sul bootstrap di 3 nodi control plane che possono anche eseguire workload.
Il motivi che mi hanno spinto ad addentrarmi in questo viaggio sono i seguenti:
- Apprendimento - Imparare Kubernetes costruendo un cluster da zero
- Self-hosting - Avere un cluster dove eseguire le app che uso quotidianamente (come Navidrome per la musica)
- Progetti personali - Un cluster dove effettuare il deployment dei miei progetti e sperimentare.
Se non hai requisiti simili, questa serie probabilmente non fa per te. Ma se sei un hobbista che vuole imparare e hostare i propri servizi a basso costo, continua a leggere. Tieni inoltre presente che non amministro cluster Kubernetes per lavoro - questo è un progetto per hobby. Se stai cercando una guida enterprise-level da un professionale amministratore Kubernetes, questa potrebbe non essere la serie giusta per te. Potresti anche voler leggere l’eccellente serie di Mathias Pius che ho consultato frequentemente quando rimanevo bloccato, così come il tutorial ufficiale di Talos per Hetzner.
Perché Talos + Hetzner?
Talos OS è una distribuzione Linux minimale e hardenizzata progettata specificamente per Kubernetes. Combinata con l’infrastruttura cloud economica di Hetzner, ottieni un cluster sicuro e gestibile a una frazione del costo dei principali provider cloud. Per mantenere i costi ulteriormente bassi, useremo una configurazione a tre nodi, dove ogni nodo esegue sia il control plane che i workload effettivi. Il compromesso è una leggermente minore isolazione tra control plane e workload, ma per molti casi d’uso, questo è perfettamente accettabile. Il costo totale stimato e’ meno di 20 euro al mese.
Prerequisiti
- Account Hetzner Cloud e token API con permessi di lettura/scrittura. Imposta la variabile d’ambiente
HCLOUD_TOKENcon il token API. Inoltre, assicurati di avere installato lo strumento hcloud di Hetzner - talosctl installato
- Comprensione di base dei concetti di Kubernetes. Per principianti assoluti puoi comunque seguire, ma suggerisco di integrare questo tutorial con l’eccellente libro Kubernetes Up & Running
- packer per creare lo snapshot iniziale dell’immagine.
Passo 1: Creare l’Immagine Talos con Packer
Per prima cosa, abbiamo bisogno di un’immagine Talos utilizzabile in seguito da Hetzner. Useremo Packer per buildare e caricare questa immagine.
1packer {
2 required_plugins {
3 hcloud = {
4 source = "github.com/hetznercloud/hcloud"
5 version = "~> 1"
6 }
7 }
8 }
9
10 variable "talos_version" {
11 type = string
12 default = "v1.11.3"
13 }
14
15 variable "arch" {
16 type = string
17 default = "amd64"
18 }
19
20 variable "server_type" {
21 type = string
22 default = "cx23"
23 }
24
25 variable "server_location" {
26 type = string
27 default = "nbg1"
28 }
29
30 locals {
31 image = "https://factory.talos.dev/image/376567988ad370138ad8b2698212367b8edcb69b5fd68c80be1f2ec7d603b4ba/${var.talos_version}/hcloud-${var.arch}.raw.xz"
32 }
33
34 source "hcloud" "talos" {
35 rescue = "linux64"
36 image = "debian-11"
37 location = "${var.server_location}"
38 server_type = "${var.server_type}"
39 ssh_username = "root"
40
41 snapshot_name = "talos system disk - ${var.arch} - ${var.talos_version}"
42 snapshot_labels = {
43 type = "infra",
44 os = "talos",
45 version = "${var.talos_version}",
46 arch = "${var.arch}",
47 }
48 }
49
50 build {
51 sources = ["source.hcloud.talos"]
52
53 provisioner "shell" {
54 inline = [
55 "apt-get install -y wget",
56 "wget -O /tmp/talos.raw.xz ${local.image}",
57 "xz -d -c /tmp/talos.raw.xz | dd of=/dev/sda && sync",
58 ]
59 }
60 }
Builda l’immagine:
1# Naviga nella tua directory infrastructure (adatta il percorso secondo necessità)
2cd infrastructure
3packer build hcloud.pkr.hcl
Questo comando farà alcune cose:
- Avvia un server Debian su Hetzner
- Abilita la modalità rescue e riavvia il server
- Scarica l’immagine Talos dalla factory Talos per sovrascrivere l’immagine Debian
- Spegne il server e crea lo snapshot
- Carica lo snapshot su Hetzner
L’intero processo mi ha richiesto 7 minuti, quindi sentiti libero di fare una pausa mentre l’automazione compie il suo dovere. Una volta terminato, tieni traccia dell’ID dello snapshot dall’output di Packer - lo useremo nei passaggi seguenti.
1export SNAPSHOT_ID=<id dello snapshot>
Passo 2: Configurare il Load Balancer
Useremo un load balancer per l’endpoint dell’API Kubernetes, così come per l’ingress. Questo non è strettamente necessario all’inizio e potresti risparmiare $5 al mese non usandolo, ma ho deciso di usarlo dato che mi servirà comunque per i miei progetti personali.
1# Crea load balancer
2hcloud load-balancer create \
3 --name talos-control-plane \
4 --network-zone eu-central \
5 --type lb11 \
6 --label 'type=controlplane'
7
8# Aggiungi servizio per Kubernetes API
9hcloud load-balancer add-service \
10 --name talos-control-plane \
11 --protocol tcp \
12 --listen-port 6443 \
13 --destination-port 6443
14
15# Aggiungi target usando label
16hcloud load-balancer add-target talos-control-plane --label-selector 'type=controlplane'
Prima creiamo il load balancer. Dopodiché esponiamo la porta 6443 e usiamo la stessa porta come destinazione. Creiamo un target group usando il selettore di label, così che ogni volta che avviamo un nuovo nodo con quella label, verrà automaticamente aggiunto al gruppo.
Ora possiamo trovare l’IP del nostro load balancer appena creato con il seguente comando
1hcloud loadbalancer list
Aggiungiamolo a una variabile d’ambiente, ci servirà nei passaggi seguenti
1export LB_IP=<ip del tuo load balancer>
Passo 3: Generare la Configurazione Talos
Ora siamo pronti per generare la configurazione talos, che useremo per connetterci al cluster e per avviare nuovi nodi.
1# Genera configurazione cluster
2talosctl gen config talos-k8s-hcloud-tutorial https://$LB_IP:6443 \
3 --with-examples=false \
4 --with-docs=false
Questo crea diversi file, inclusi controlplane.yaml, worker.yaml, e talosconfig.
Passo 4: Patch della Configurazione per l’Integrazione con Hetzner
Applicheremo alcune modifiche alla configurazione. Per farlo, useremo delle patch. Creiamo una cartella patches dove possiamo tenere traccia di tutte le patch. Inizieremo patchando il cluster per permettere externalCloudProviders. Questo sarà richiesto per usare l’hetzner cloud controller manager.
1# patches/external_cloud_providers.yaml
2cluster:
3 externalCloudProvider:
4 enabled: true
Successivamente, creeremo una patch per permettere ai workload di essere schedulati sui nodi control plane. Questo impedirà ai nodi di essere taintati, che fermerebbe lo scheduling dei workload.
1# patches/allow_controlplane_workloads.yaml
2cluster:
3 allowSchedulingOnControlPlanes: true
Applica la patch:
1talosctl machineconfig patch controlplane.yaml --patch @patches/allow_controlplane_workloads.yaml --patch @patches/external_cloud_providers.yaml -o controlplane.yaml
Passo 5: Deploy dei Nodi Control Plane
Ora creiamo i nostri 3 nodi control plane usando la configurazione patchata:
1# Crea tre nodi control plane
2for i in 1 2 3; do
3 hcloud server create \
4 --name talos-control-plane-$i \
5 --image $SNAPSHOT_ID \
6 --type cx23 \
7 --location nbg1 \
8 --label 'type=controlplane' \
9 --user-data-from-file controlplane.yaml
10done
Per il mio cluster sto usando le istanze più piccole disponibili dato che sono più che sufficienti per le mie necessità.
Passo 6: Bootstrap del Cluster
Troviamo l’IP del primo nodo usando hcloud server list | grep talos-control-plane ed esportiamolo come variabile d’ambiente:
1export FIRST_NODE_IP=<ip del tuo nodo control-plane>
Ora configuriamo il client Talos per connettersi a questo nodo impostando sia l’endpoint che il nodo:
1talosctl --talosconfig talosconfig config endpoint $FIRST_NODE_IP
2talosctl --talosconfig talosconfig config node $FIRST_NODE_IP
Siamo pronti per fare il bootstrap di etcd sul nostro primo nodo control plane
1talosctl --talosconfig talosconfig bootstrap
Dovresti quindi essere in grado di vedere tutti e tre i nodi con il seguente comando:
1talosctl --talosconfig talosconfig get members
Possiamo quindi recuperare il kubeconfig e usarlo con kubectl
1talosctl --talosconfig talosconfig kubeconfig .
2export KUBECONFIG=./kubeconfig
3kubectl get nodes -o wide
Verifica che tutto funzioni:
1# Controlla stato nodi
2kubectl get nodes -o wide
Possiamo dare un’occhiata alla salute del cluster usando il comando talosctl dashboard
1talosctl --talosconfig talosconfig dashboard
Passo 7: Hetzner Cloud Controller Manager
Configurare l’Hetzner cloud controller manager è stato abbastanza semplice, ho appena seguito il suo quickstart.md ufficiale.
Crea un secret contenente il tuo token API Hetzner:
1kubectl -n kube-system create secret generic hcloud --from-literal=token=<hcloud API token>
Aggiungi il repository helm
1helm repo add hcloud https://charts.hetzner.cloud
2helm repo update hcloud
Installa il chart
1helm install hccm hcloud/hcloud-cloud-controller-manager -n kube-system
Dovresti essere in grado di vedere hcloud-cloud-controller-manager nei deployments
1kubectl get deployments -n kube-system
Prossimi passi?
Nelle prossime parti di questa serie, tratteremo:
- Configurare ArgoCD (Parte 2)
- Configurare lo storage con Longhorn
- Deploy di Navidrome per lo streaming musicale
Riepilogo
Abbiamo bootstrapato con successo un cluster Kubernetes a 3 nodi usando Talos su Hetzner Cloud. I nostri nodi control plane possono anche eseguire workload, ottenendo una configurazione economica e altamente disponibile.