# CLAUDE.md This file provides guidance to Claude Code (claude.ai/code) when working with code in this repository. ## Repository Purpose Home Kubernetes lab infrastructure-as-code. Manages VM provisioning (Terraform/KVM), Kubernetes cluster configuration, and application deployments via Flux GitOps — all pointing at a self-hosted Gitea instance. ## Common Commands ### Terraform (kubernetes-kvm-terraform/) ```bash cd kubernetes-kvm-terraform tofu init tofu plan tofu apply tofu destroy ``` ### Flux GitOps ```bash # Check reconciliation status kubectl get kustomizations -A kubectl get helmreleases -A # Force reconcile flux reconcile kustomization flux-system --with-source flux reconcile helmrelease -n # Watch logs flux logs --follow # Check source sync flux get sources git ``` ### kubectl — common ops ```bash export KUBECONFIG=kubernetes-kvm-terraform/kubeconfig kubectl get nodes kubectl get pods -A kubectl get secrets -A ``` ### Docker Compose (docker-30/ services) ```bash # These run on 192.168.0.30 (docker-30), accessed via SSH ssh novakj@192.168.0.30 cd /path/to/service && docker compose up -d docker compose logs -f ``` ## Architecture ### Infrastructure Layer - **Hypervisors**: homer (192.168.0.7) and beelink (192.168.0.6) run KVM/libvirt - **Terraform provider**: primary `qemu+ssh://novakj@192.168.0.7/system`, secondary alias `kvm-beelink` for 192.168.0.6 - **Kubernetes master**: kube-master-31 @ 192.168.0.31:6443, bootstrapped via kubeadm - **OS**: Ubuntu 24.04 Noble cloud images, network bridge `br0`, subnet 192.168.0.0/24 ### GitOps Layer (`gitops/home-kubernetes/`) Flux syncs from Gitea (`https://gitea.home.hrajfrisbee.cz`, main branch, every 10 minutes). The reconciliation order is enforced via `dependsOn` in `flux-system/extra-kustomizations.yaml`: ``` 00-crds → 00-rbac → cilium → cert-manager → external-secrets → everything else ``` Each application lives in its own subdirectory under `gitops/home-kubernetes/` and is referenced as a Flux `Kustomization` resource. Prune is enabled — removing a manifest from git removes it from the cluster. ### Secrets Flow Vault (docker-30) → External-Secrets controller (in-cluster) → Kubernetes `Secret` objects. Applications reference `ExternalSecret` CRs that pull from Vault paths. Do not put real secrets in git. ### Networking - **CNI**: Cilium 1.19.x with Gateway API and Hubble UI enabled - **L2 LB**: Cilium `CiliumL2AnnouncementPolicy` + `CiliumLoadBalancerIPPool` for bare-metal load-balancer IPs (defined in `gitops/home-kubernetes/cilium/`) - **Ingress**: ingress-nginx for HTTP(S) workloads; Gateway API for newer apps - **TLS**: cert-manager issues wildcard cert (`*.home.hrajfrisbee.cz`) referenced by apps ### Storage - **democratic-CSI**: iSCSI volumes backed by FreeNAS at 192.168.0.40 - **Longhorn**: configured but disabled in Flux (directory present, not in `extra-kustomizations.yaml`) ### Supporting Services on docker-30 (192.168.0.30) All managed with Docker Compose: - **Gitea** — Git server + act_runner (GitHub Actions-compatible CI) - **Vault** — secrets backend for External Secrets - **Zot** — private OCI/container registry - **Kanidm** — identity management / OIDC provider - **nginx** — reverse proxy for docker-30 services ## Key Conventions - **New application**: create a directory under `gitops/home-kubernetes//`, add a `Kustomization` entry in `flux-system/extra-kustomizations.yaml` with appropriate `dependsOn`. - **Helm apps**: use a `HelmRepository` + `HelmRelease` pair; pin chart versions explicitly. - **Secrets**: add an `ExternalSecret` CR pointing to the Vault path; never commit actual secret values. - **Terraform state**: `kubernetes-kvm-terraform/terraform.tfstate*` is gitignored/sensitive; treat it carefully. - **kubeconfig**: `kubernetes-kvm-terraform/kubeconfig` is gitignored; obtain it from the master node after provisioning. ## Plans When Claude Code's plan mode is used, save the plan file inside the repo at `docs/plans/YYYY-MM-DD-HHMM-.md` instead of the default `~/.claude/plans/` location. Get the timestamp with `date "+%Y-%m-%d-%H%M"` (matches the changelog convention). The `` should be a short kebab-case summary of the plan's topic.