The Afrotomation cluster runs 70+ apps on a bare-metal k3s setup, fully managed via ArgoCD and a single GitLab repository. Every deploy is a git commit. Every secret is SOPS-encrypted. Every cert is auto-renewed.
GitLab is the source of truth. ArgoCD pulls changes into k3s. cert-manager, external-dns, and ingress-nginx handle TLS and routing. Cloudflare sits in front of everything.
A single-node k3s control plane runs on a Contabo VPS 50 (8 vCPU, 30 GB RAM). An Oracle Ampere ARM64 node (4 OCPU, 24 GB RAM) joins as a worker for lightweight workloads. ArgoCD manages every namespace declaratively; the only manual step is bootstrapping a new namespace secret once per workload.
All production images are built via GitLab CI and pushed to the in-house
registry at registry.afrotomation.com. The argocd-image-updater
watches for new digests and writes back to the GitLab repository, triggering
a self-healing sync loop. SOPS + age encrypts every secret committed to the
repo; the sops-secrets-operator decrypts at runtime.
Each workload defines its own GitLab CI job gated on changes to its subdirectory. Semantic-release manages the infra changelog and version tagging. Mirror-to-GitHub ensures a public read-only copy stays in sync on github.com/afrotomation/afrotomationinfra.
A selection of open-source services self-hosted on the cluster, all served over HTTPS via Cloudflare + ingress-nginx + cert-manager.
Self-hosted scheduling and calendar-link platform, replacing Calendly.
Self-hosted collaborative whiteboard for diagrams, architecture sketches, and brainstorming sessions.
Self-hosted knowledge graph and note-taking app for team documentation and personal wikis.
Self-hosted file storage, sharing, and collaboration suite — a Dropbox/Google-Drive alternative.
Self-hosted monitoring and status page for every public service on the cluster.
Privacy-first web analytics platform — a self-hosted alternative to Google Analytics.
Cluster observability dashboards: metrics, logs, and resource usage for every workload.
Last 10 releases — managed by semantic-release from the GitLab repository.
Full changelog on GitLab →