Arquitectura
Homelab de seis equipos heterogéneos en casa: x86 reciclados, mini-PCs y una Raspberry Pi. Juntos forman un clúster k3s con el control-plane en alta disponibilidad. Sirve de laboratorio de DevOps, observabilidad y seguridad, y aloja algunos servicios de uso diario (DNS con Pi-hole, n8n, Jira y Confluence).
Vista general
flowchart TB
internet((Internet)) -. sin rutas .-> cf[Cloudflare<br/>*.example.com]
cf -. túnel .-> cfd[cloudflared<br/>master-3]
lan((LAN 192.0.2.0/24)) --> vip
lan --> lb
subgraph cp[Control-plane HA · etcd 3 miembros]
direction LR
master-1[master-1<br/>.112 · MASTER VIP]
master-2[master-2<br/>.139]
g2[master-3<br/>.129]
end
vip[VIP 192.0.2.250:6443<br/>keepalived + haproxy] --> cp
subgraph wk[Workers]
direction LR
sz[worker-2 .164]
nuc[worker-1 .128]
worker-3[worker-3 .197]
end
cp --- wk
cfd -.-> traefik
lb[MetalLB L2<br/>192.0.2.240-245] --> traefik[Traefik .240<br/>Ingress]
lb --> pihole[Pi-hole DNS .241]
traefik --> apps[Jira · Confluence · n8n ⏸]
Capas
| Capa | Tecnología | Detalle |
|---|---|---|
| Sistema | Ubuntu 26.04 (Debian 13 en worker-3) | nodes/README.md |
| Distribución Kubernetes | k3s v1.34.6 | Embebe containerd, flannel, CoreDNS, Traefik, metrics-server y local-path |
| Control-plane | 3 masters con etcd embebido | Tolera la caída de un master |
| Endpoint de la API | VIP 192.0.2.250 con keepalived (VRRP) y haproxy (TCP) |
red.md |
| Red de pods | flannel VXLAN (por defecto en k3s) | --flannel-iface fijado por nodo |
LoadBalancer |
MetalLB en modo L2, pool 192.0.2.240-245 |
ServiceLB/Klipper desactivado |
| Ingress | Traefik (el de k3s) en 192.0.2.240 |
|
| Publicación a Internet | Cloudflare Tunnel (cloudflared en master-3) |
Sin puertos abiertos en el router. Desde el 2026-11-01 sin rutas: no hay nada publicado (se vuelve a publicar con Cloudflare Access delante) |
| Almacenamiento | Longhorn (replicado) y local-path (disco del nodo) | almacenamiento.md |
| GitOps | Argo CD contra el repo example-org/GitOps |
4 aplicaciones (filebeat-routing-job, jenkins-lab, vector-kafka-elastic y homepage); el resto se instala con Helm a mano (R3) |
| Observabilidad | kube-prometheus-stack, ECK (Elasticsearch y Kibana), Kafka, Flink y Vector | aplicaciones.md |
| Seguridad | Kyverno, Falco, Trivy Operator, Policy Reporter | seguridad.md |
Decisiones de diseño
- k3s en lugar de kubeadm: un solo binario, consume poco y encaja con hardware modesto y mezcla de arquitecturas (amd64 y arm64).
- etcd embebido con 3 masters: permite hacer drain y reiniciar un master sin perder la API. Se migró desde SQLite el 2026-07-03.
- La VIP en una interfaz
dummy0con/32: si la VIP va como IP secundaria de la interfaz real, flannel la elige como IP pública del nodo y rompe la red overlay. Con/24en lugar de/32se secuestra la ruta de toda la subred. Las dos cosas pasaron; ver incidentes.md. - MetalLB en lugar de ServiceLB: IPs estables y dedicadas por servicio (Pi-hole necesita una IP fija para DNS).
- Cloudflare Tunnel: publicaba servicios sin abrir puertos ni exponer la IP de casa. Desde el 2026-11-01 no tiene rutas (nada en Internet); lo que se vuelva a publicar irá con Cloudflare Access delante.
- Masters que también ejecutan cargas: master-2 y master-3 no tienen taint de control-plane, para aprovechar el hardware. A cambio, una carga con mucho I/O en un master afecta a etcd. Ya ha pasado con filebeat y trivy (ver incidentes.md).