Skip to content

afonsoc12/homelab

Repository files navigation

homelab

CI Docs

GitOps-driven homelab. Self-hosted. Automated. Encrypted.

Documentation


📖 About

This repository is the single source of truth for my homelab — a fully GitOps-driven setup where every change is version-controlled and automatically applied:

  • Kubernetes workloads — managed by ArgoCD via GitOps
  • Node provisioning — handled by Ansible
  • External infrastructure — Cloudflare DNS, tunnels, and more via Terraform
  • Secrets — encrypted with SOPS, never committed in plaintext

🗂️ Repository Layout

Ansible

Ansible handles node provisioning and cluster lifecycle management — k3s installation and upgrades, OS configuration, Tailscale enrollment, and ongoing maintenance across all nodes. Uses uv for dependency management.

uv sync --all-groups
uv run ansible-playbook ansible/playbooks/k3s-cluster.yml

Terraform

Terraform manages external infrastructure-as-code (IaC). The cloudflare module covers DNS records, Cloudflare Tunnel, WAF rules, and zone settings across two domains.

cd terraform/cloudflare
terraform init -backend-config=../.decrypted~backend.sops.tfbackend
terraform plan
terraform apply -auto-aprove

k8s Apps

All apps are declared as ArgoCD Application manifests under kubernetes/apps/addons/argocd-apps/templates/. Pushing to master is enough — ArgoCD detects drift and syncs automatically. To add a new app, drop a values file and an Application manifest, then push.

Helm Charts

Ad-hoc Kubernetes resources that don't belong to a specific app (CRDs, cluster-wide config) live as Helm charts under kubernetes/charts/.

helmfile (bootstrap)

A fresh cluster is bootstrapped with Helmfile via the bootstrap Ansible tag. Helmfile installs the SOPS GPG key secret, the GitHub deploy key, ArgoCD, and the root argocd-apps Application — in dependency order. After that, ArgoCD self-manages via the App of Apps pattern.

uv run ansible-playbook ansible/playbooks/k3s-cluster.yml --tags bootstrap

See the bootstrap runbook for the full procedure.

🔐 Secrets (SOPS)

All secrets are SOPS-encrypted (.sops.yaml) and never committed in plaintext. Ansible, Terraform, and ArgoCD each decrypt on the fly at runtime — no manual steps required.

Tool Secrets location
Ansible ansible/inventory/hosts_secrets.sops.yaml
Terraform secrets.sops.yaml per module
Kubernetes values.sops.yaml alongside plain values.yaml

License

Copyright © 2026 Afonso Costa

Licensed under the MIT License. See the LICENSE file for details.

About

GitOps-driven homelab. Self-hosted. Automated. Encrypted.

Topics

Resources

License

Stars

Watchers

Forks

Packages

 
 
 

Contributors