Skip to main content
Two layers — most RL users only care about the first.

Inside a forked cluster (your GRPO scenario)

This is the k3s that lives inside the VMs you fork (cluster mode). The fork engine is N-node (tree_create_cluster(vm_count) / adopt any live set) — there is no hard-coded 3. Two guests prove the rows below. The minimal CI guest fixture is a 3-node control plane with flannel + kube-proxy and a real in-cluster Deployment; its default profile keeps stock k3s add-ons off so the lean path stays lean, and each add-on is an opt-in profile with its own proving test. The Ubuntu node runs stock Ubuntu 24.04 with k3s’ own containerd and takes Cilium, Tetragon, Longhorn, and the ML operators. Every ✅ is an integration test that brings the feature up, warm-forks the cluster, and checks source and fork keep working, then diverge independently. Need CoreDNS + Ingress on one CI-guest cluster? Flip the profile flags — the switchboard is configuration, not a redesign. Same for a larger fixture: wiring 20 nodes is configuration + RAM, not a new fork feature. Per-row fork latencies: Benchmarks.

Host RuntimeClass (pods as k7d VMs)

This is the outer layer: kubectl on the host schedules pods into k7d microVMs via runtimeClassName: k7. Relevant if you also want single-VM sandboxes, not only whole-cluster forks.