Configuration Reference
- AADApplication
- ACMECredentials
- ACMEDNS01Config
- AMIConfig
- APIServerConfig
- AWSAutoScalableNodeGroup
- AWSConfig
- AWSControlPlane
- AWSCredentials
- ArgoCDConfig
- AutoScalableNodeGroup
- AzureAutoScalableNodeGroup
- AzureConfig
- AzureControlPlane
- AzureCredentials
- BareMetalConfig
- BareMetalControlPlane
- BareMetalControlPlaneEndpoint
- BareMetalHost
- BareMetalKubeletConfig
- BareMetalNodeGroup
- BareMetalSSHConfig
- CanonicalUbuntuImage
- CloudConfig
- ClusterConfig
- DeployKeysConfig
- DisasterRecoveryConfig
- FileConfig
- FirewallConfig
- FirewallPort
- ForksConfig
- GeneralConfig
- GitConfig
- HCloudAutoScalableNodeGroup
- HCloudConfig
- HCloudControlPlane
- HCloudControlPlaneLoadBalancer
- HCloudVPNClusterConfig
- HetznerBareMetalConfig
- HetznerBareMetalControlPlane
- HetznerBareMetalControlPlaneEndpoint
- HetznerBareMetalHost
- HetznerBareMetalNodeGroup
- HetznerConfig
- HetznerControlPlane
- HetznerCredentials
- HetznerNetworkConfig
- HetznerNodeGroups
- HetznerRobotCredentials
- HetznerSSHKeyPair
- HostPathMountConfig
- InstallImageConfig
- KeycloakConfig
- KeycloakCredentials
- KubeAidForkConfig
- KubePrometheusConfig
- KubeaidConfigForkConfig
- KubeaidStoragectlConfig
- LocalConfig
- NetBirdClusterProxyConfig
- NetBirdClusterProxyRBACConfig
- NetBirdConfig
- NetBirdCredentials
- NodeGroup
- ObmondoConfig
- OpenIDProviderSSHKeyPairConfig
- SSHKeyPairConfig
- SecretsConfig
- UserConfig
- VG0Config
- VSwitchConfig
- WorkloadIdentity
- ZFSConfig
AADApplication
| Field | Type | Default | Description |
|---|---|---|---|
| principalID | string |
ACMECredentials
ACMECredentials carries the DNS-provider secrets the cert-manager ClusterIssuer's DNS-01 solver authenticates with. Only needed when cluster.acmeDNS01 is set.
| Field | Type | Default | Description |
|---|---|---|---|
| cloudflareApiToken | string | CloudflareAPIToken is a Cloudflare API token with Zone:Read + DNS:Edit on the zones the solver manages (the TXT challenge records). Sealed into the cert-manager/cloudflare-api-token Secret the ClusterIssuer references. |
ACMEDNS01Config
ACMEDNS01Config selects and scopes the ClusterIssuer's DNS-01 solver. Only Cloudflare is wired today (the chart's solver list also knows route53; extend Provider's oneof when kubeaid-cli grows the matching credential plumbing).
| Field | Type | Default | Description |
|---|---|---|---|
| provider | string | cloudflare | |
| dnsZones | []string | DNSZones limits which zones this solver answers challenges for (cert-manager's selector.dnsZones). Empty matches every DNS-01 order — fine when this is the only solver. |
AMIConfig
| Field | Type | Default | Description |
|---|---|---|---|
| id | string |
APIServerConfig
REFER : https://github.com/kubernetes-sigs/cluster-api/blob/main/controlplane/kubeadm/config/crd/bases/controlplane.cluster.x-k8s.io_kubeadmcontrolplanes.yaml.
NOTE : Generally, refer to the KubeadmControlPlane CRD instead of the corresponding GoLang source types linked below. There are some configuration options which appear in the corresponding GoLang source type, but not in the CRD. If you set those fields, then they get removed by the Kubeadm control-plane provider. This causes the capi-cluster ArgoCD App to always be in an OutOfSync state, resulting to KubeAid CLI not making any progress!
| Field | Type | Default | Description |
|---|---|---|---|
| extraArgs | map[string]string | {} | |
| extraVolumes | []HostPathMountConfig | [] | |
| files | []FileConfig | [] |
AWSAutoScalableNodeGroup
| Field | Type | Default | Description |
|---|---|---|---|
| ami | AMIConfig | ||
| instanceType | string | ||
| rootVolumeSize | uint32 | ||
| sshKeyName | string | ||
| name | string | Nodegroup name. | |
| labels | map[string]string | [] | Labels that you want to be propagated to each node in the nodegroup. Each label should meet one of the following criterias to propagate to each of the nodes : 1. Has node-role.kubernetes.io as prefix. 2. Belongs to node-restriction.kubernetes.io domain. 3. Belongs to node.cluster.x-k8s.io domain. REFER : https://cluster-api.sigs.k8s.io/developer/architecture/controllers/metadata-propagation#machine. |
| taints | []k8s.io/api/core/v1.Taint | [] | Taints that you want to be propagated to each node in the nodegroup. |
| minSize | uint | Minimum number of replicas in the nodegroup. | |
| maxSize | uint | Maximum number of replicas in the nodegroup. |
AWSConfig
| Field | Type | Default | Description |
|---|---|---|---|
| region | string | ||
| sshKeyName | string | ||
| vpcID | string | ||
| bastionEnabled | bool | True | |
| controlPlane | AWSControlPlane | ||
| nodeGroups | []AWSAutoScalableNodeGroup |
AWSControlPlane
| Field | Type | Default | Description |
|---|---|---|---|
| loadBalancerScheme | string | internet-facing | |
| replicas | uint32 | ||
| instanceType | string | ||
| ami | AMIConfig |
AWSCredentials
| Field | Type | Default | Description |
|---|---|---|---|
| accessKeyID | string | ||
| secretAccessKey | string | ||
| sessionToken | string |
ArgoCDConfig
| Field | Type | Default | Description |
|---|---|---|---|
| deployKeys | DeployKeysConfig |
AutoScalableNodeGroup
| Field | Type | Default | Description |
|---|---|---|---|
| minSize | uint | Minimum number of replicas in the nodegroup. | |
| maxSize | uint | Maximum number of replicas in the nodegroup. | |
| name | string | Nodegroup name. | |
| labels | map[string]string | [] | Labels that you want to be propagated to each node in the nodegroup. Each label should meet one of the following criterias to propagate to each of the nodes : 1. Has node-role.kubernetes.io as prefix. 2. Belongs to node-restriction.kubernetes.io domain. 3. Belongs to node.cluster.x-k8s.io domain. REFER : https://cluster-api.sigs.k8s.io/developer/architecture/controllers/metadata-propagation#machine. |
| taints | []k8s.io/api/core/v1.Taint | [] | Taints that you want to be propagated to each node in the nodegroup. |
AzureAutoScalableNodeGroup
| Field | Type | Default | Description |
|---|---|---|---|
| vmSize | string | ||
| diskSizeGB | uint32 | ||
| minSize | uint | Minimum number of replicas in the nodegroup. | |
| maxSize | uint | Maximum number of replicas in the nodegroup. | |
| name | string | Nodegroup name. | |
| labels | map[string]string | [] | Labels that you want to be propagated to each node in the nodegroup. Each label should meet one of the following criterias to propagate to each of the nodes : 1. Has node-role.kubernetes.io as prefix. 2. Belongs to node-restriction.kubernetes.io domain. 3. Belongs to node.cluster.x-k8s.io domain. REFER : https://cluster-api.sigs.k8s.io/developer/architecture/controllers/metadata-propagation#machine. |
| taints | []k8s.io/api/core/v1.Taint | [] | Taints that you want to be propagated to each node in the nodegroup. |
AzureConfig
| Field | Type | Default | Description |
|---|---|---|---|
| tenantID | string | ||
| subscriptionID | string | ||
| aadApplication | AADApplication | ||
| location | string | ||
| storageAccount | string | ||
| workloadIdentity | WorkloadIdentity | ||
| sshPublicKey | string | ||
| canonicalUbuntuImage | CanonicalUbuntuImage | ||
| controlPlane | AzureControlPlane | ||
| nodeGroups | []AzureAutoScalableNodeGroup |
AzureControlPlane
| Field | Type | Default | Description |
|---|---|---|---|
| loadBalancerType | string | Public | |
| diskSizeGB | uint32 | ||
| vmSize | string | ||
| replicas | uint32 |
AzureCredentials
| Field | Type | Default | Description |
|---|---|---|---|
| clientID | string | ||
| clientSecret | string |
BareMetalConfig
| Field | Type | Default | Description |
|---|---|---|---|
| ssh | BareMetalSSHConfig | ||
| kubelet | BareMetalKubeletConfig | Kubelet tuning applied to every host (control-plane and workers). | |
| controlPlane | BareMetalControlPlane | ||
| nodeGroups | []BareMetalNodeGroup |
BareMetalControlPlane
| Field | Type | Default | Description |
|---|---|---|---|
| endpoint | BareMetalControlPlaneEndpoint | ||
| hosts | []BareMetalHost |
BareMetalControlPlaneEndpoint
| Field | Type | Default | Description |
|---|---|---|---|
| host | string | ||
| port | uint | 6443 |
BareMetalHost
| Field | Type | Default | Description |
|---|---|---|---|
| publicAddress | string | ||
| privateAddress | string | ||
| ssh | BareMetalSSHConfig |
BareMetalKubeletConfig
BareMetalKubeletConfig mirrors KubeOne's per-host KubeletConfig. REFER : https://docs.kubermatic.com/kubeone/v1.13/references/kubeone-cluster-v1beta2/#kubeletconfig
| Field | Type | Default | Description |
|---|---|---|---|
| systemReserved,omitempty | map[string]string | ||
| kubeReserved,omitempty | map[string]string | ||
| evictionHard,omitempty | map[string]string | ||
| maxPods,omitempty | int32 |
BareMetalNodeGroup
| Field | Type | Default | Description |
|---|---|---|---|
| hosts | []BareMetalHost | ||
| name | string | Nodegroup name. | |
| labels | map[string]string | [] | Labels that you want to be propagated to each node in the nodegroup. Each label should meet one of the following criterias to propagate to each of the nodes : 1. Has node-role.kubernetes.io as prefix. 2. Belongs to node-restriction.kubernetes.io domain. 3. Belongs to node.cluster.x-k8s.io domain. REFER : https://cluster-api.sigs.k8s.io/developer/architecture/controllers/metadata-propagation#machine. |
| taints | []k8s.io/api/core/v1.Taint | [] | Taints that you want to be propagated to each node in the nodegroup. |
BareMetalSSHConfig
| Field | Type | Default | Description |
|---|---|---|---|
| port | uint | 22 | |
| privateKeyFilePath | string | PrivateKeyFilePath is the on-disk SSH private key kubeaid-cli reads to derive PublicKey + Fingerprint and (for cloud-side SSH connections like the Hetzner NAT gateway setup) to authenticate the SSH session. Required when UseSSHAgent is false; ignored when UseSSHAgent is true (the agent owns the private key — yubikey case — so there's nothing on disk to point at). Cross-field validation in pkg/config/parser/validate.go enforces "exactly one is set". | |
| useSSHAgent | bool | UseSSHAgent flips the SSH key sourcing from "read a file from PrivateKeyFilePath" to "dial $SSH_AUTH_SOCK and ask the agent for its loaded identities". The first identity supplies PublicKey + Fingerprint; the SSH client (kubeone) signs through the agent socket so yubikey-resident private keys never need to be exported. |
CanonicalUbuntuImage
| Field | Type | Default | Description |
|---|---|---|---|
| offer | string | ||
| sku | string |
CloudConfig
| Field | Type | Default | Description |
|---|---|---|---|
| aws | AWSConfig | ||
| azure | AzureConfig | ||
| hetzner | HetznerConfig | ||
| bare-metal | BareMetalConfig | ||
| local | LocalConfig | ||
| disasterRecovery | DisasterRecoveryConfig |
ClusterConfig
| Field | Type | Default | Description |
|---|---|---|---|
| type | string | workload | |
| name | string | Name of the Kubernetes cluster. We don't allow using dots in the cluster name, since it can cause issues with tools like ClusterAPI and Cilium : which use the cluster name to generate other configurations. | |
| k8sVersion | string | Kubernetes version (>= 1.30.0). | |
| enableAuditLogging | bool | True | Whether you would like to enable Kubernetes Audit Logging out of the box. Suitable Kubernetes API configurations will be done for you automatically. And they can be changed using the apiSever struct field. |
| acmeEmail | string | ACMEEmail is the contact email used to register with the ACME CA (Let's Encrypt) when cert-manager's ClusterIssuer is rendered. Required when cluster.keycloak.mode=managed (the keycloakx and netbird-mgmt Ingresses both need TLS certs); optional otherwise. Used as Issuer.spec.acme.email. | |
| acmeDNS01 | ACMEDNS01Config | ACMEDNS01 switches the rendered ClusterIssuer's solver from the HTTP-01 default to DNS-01. Required for the split-horizon mesh pattern: NetBird-exposed services use real public DNS names (e.g. argocd.staging.acme.com) that only resolve inside the mesh — Let's Encrypt can never reach them over HTTP, but proves ownership via a TXT record on the public zone instead. Requires cluster.acmeEmail plus the provider credential in secrets.yaml (acme.cloudflareApiToken). | |
| apiServer | APIServerConfig | Configuration options for the Kubernetes API server. | |
| lockdown | bool | Lockdown pre-answers the end-of-bootstrap Host Firewall (CCNP) step. nil = ask interactively (legacy behavior); true = apply without prompting (CI-safe); false = skip the step. | |
| keycloak | KeycloakConfig | Keycloak declares the Keycloak instance a VPN cluster hosts as NetBird's SSO IdP. Required on cluster.type=vpn (mode=managed → kubeaid-cli installs it; mode=external → operator runs it elsewhere). Not supported on workload clusters — access there is via the NetBird mesh (cluster.netbird.dns), so a keycloak block on a workload cluster is rejected. | |
| netbird | NetBirdConfig | NetBird declares the NetBird Management instance this VPN cluster hosts. Only meaningful when cluster.type=vpn AND cluster.keycloak.mode=managed. NetBird Mgmt's OIDC client is created in the same Keycloak realm; its public DNS is used for the redirect URI and audience claim. | |
| additionalUsers | []UserConfig | Other than the root user, addtional users that you would like to be created in each node. NOTE : Currently, we can't register additional SSH key-pairs against the root user. | |
| argoCD | ArgoCDConfig | ArgoCD specific details. |
DeployKeysConfig
| Field | Type | Default | Description |
|---|---|---|---|
| kubeaid | SSHKeyPairConfig | ||
| kubeaidConfig | SSHKeyPairConfig |
DisasterRecoveryConfig
| Field | Type | Default | Description |
|---|---|---|---|
| veleroBackupsBucketName | string | ||
| sealedSecretsBackupsBucketName | string |
FileConfig
REFER : "sigs.k8s.io/cluster-api/bootstrap/kubeadm/api/v1beta1".File.
| Field | Type | Default | Description |
|---|---|---|---|
| path | string | ||
| content | string |
FirewallConfig
FirewallConfig drives the Cilium host-firewall policy rendered by kubeaid-cli for Hetzner bare-metal clusters. The resulting CiliumClusterwideNetworkPolicy selects every node and locks down the public NIC via eBPF host-endpoint rules. See docs/hetzner-bare-metal-network-surface.md.
| Field | Type | Default | Description |
|---|---|---|---|
| enabled | bool | Enabled gates whether kubeaid-cli renders the Cilium host-firewall CiliumClusterwideNetworkPolicy at all. Defaults to true; set false to opt out — e.g. a separate upstream L3 firewall appliance already fronts the cluster. A pointer so an explicit "enabled: false" is distinguishable from unset and honoured. | |
| allowSshFrom | []string | AllowSSHFrom restricts inbound SSH (22/tcp) on every bare-metal node to these sources. Rendered as a fromCIDR rule in the CCNP. Empty (the default) allows SSH from anywhere — matching the bare-metal posture where nodes are not NetBird peers and have no mesh fallback path. Each entry is an IPv4 address or CIDR (e.g. "203.0.113.4" or "203.0.113.0/24"); a bare address is treated as /32. | |
| allowPublic | []FirewallPort | AllowPublic is a legacy field from the (removed) Hetzner Robot firewall. It is parsed and validated but NOT rendered into the Cilium host-firewall policy — parser.validateHetznerConfig only logs a warning when it is set. The policy's world-facing ports come from hostNetworkPolicy.publicPorts (chart default [80, 443]); 6443 is never world-public — it is a separate rule restricted to hostNetworkPolicy.apiserverSourceCIDRs (the node IPs). To open extra ports to the world, add them to hostNetworkPolicy.publicPorts in the cilium chart values overlay, not here. |
FirewallPort
FirewallPort is one {port, protocol} entry in FirewallConfig.AllowPublic.
| Field | Type | Default | Description |
|---|---|---|---|
| port | string | Port is a single port ("25") or an inclusive range ("30000-32767"). | |
| protocol | string | Protocol is "tcp", "udp", or omitted for any protocol. |
ForksConfig
KubeAid and KubeAid Config repository specific details. We require the KubeAid and KubeAid Config repositories to be hosted in the same Git server.
| Field | Type | Default | Description |
|---|---|---|---|
| kubeaid | KubeAidForkConfig | KubeAid repository specific details. | |
| kubeaidConfig | KubeaidConfigForkConfig | KubeAid Config repository specific details. |
GeneralConfig
Non secret configuration options.
| Field | Type | Default | Description |
|---|---|---|---|
| git | GitConfig | Git server specific details. | |
| forkURLs | ForksConfig | KubeAid and KubeAid Config repository specific details. The KubeAid and KubeAid Config repositories must be hosted in the same Git server. | |
| cluster | ClusterConfig | Kubernetes specific details. | |
| cloud | CloudConfig | Cloud provider specific details. | |
| kubePrometheus | KubePrometheusConfig | Kube Prometheus installation specific details. | |
| kubeaidStoragectl | KubeaidStoragectlConfig | KubeaidStoragectl pins the kubeaid-storagectl release tag used by the bare-metal preKubeadm script when carving the ZFS pool and Ceph partition. Leave nil (block omitted) to fall back to the kubeaid-cli binary's own release version, which is the right default for most operators — every node downloads the storagectl that ships with the kubeaid-cli release that bootstrapped it. Set explicitly to override: - to pin against a tag newer/older than kubeaid-cli for testing a fix or rolling back, or - to point at an unreleased dev build when running a go run ./cmd/kubeaid-cli development bootstrap (theCLI's KubeaidCLIVersion is empty there and the chart would otherwise fall through to latest, which 404s ifno release has been published yet). | |
| obmondo | ObmondoConfig | Obmondo customer specific details. |
GitConfig
Git specific details, used by KubeAid CLI, to clone repositories from and push changes to the Git server. We enforce the user to use SSH, for authenticating to the Git server.
| Field | Type | Default | Description |
|---|---|---|---|
| caBundlePath | string | ||
| sshUsername | string | git | SSH username. |
| knownHosts | []string | Additional SSH known hosts. Merged with known hosts of common Git repo hosting providers (like Azure DevOps, GitLab etc.) | |
| privateKeyFilePath | string | PrivateKeyFilePath is the on-disk SSH private key kubeaid-cli reads to derive PublicKey + Fingerprint and (for cloud-side SSH connections like the Hetzner NAT gateway setup) to authenticate the SSH session. Required when UseSSHAgent is false; ignored when UseSSHAgent is true (the agent owns the private key — yubikey case — so there's nothing on disk to point at). Cross-field validation in pkg/config/parser/validate.go enforces "exactly one is set". | |
| useSSHAgent | bool | UseSSHAgent flips the SSH key sourcing from "read a file from PrivateKeyFilePath" to "dial $SSH_AUTH_SOCK and ask the agent for its loaded identities". The first identity supplies PublicKey + Fingerprint; the SSH client (kubeone) signs through the agent socket so yubikey-resident private keys never need to be exported. |
HCloudAutoScalableNodeGroup
Details about (autoscalable) node-groups in HCloud.
| Field | Type | Default | Description |
|---|---|---|---|
| machineType | string | HCloud machine type. You can browse all available HCloud machine types here : https://hetzner.com/cloud. | |
| minSize | uint | Minimum number of replicas in the nodegroup. | |
| maxSize | uint | Maximum number of replicas in the nodegroup. | |
| name | string | Nodegroup name. | |
| labels | map[string]string | [] | Labels that you want to be propagated to each node in the nodegroup. Each label should meet one of the following criterias to propagate to each of the nodes : 1. Has node-role.kubernetes.io as prefix. 2. Belongs to node-restriction.kubernetes.io domain. 3. Belongs to node.cluster.x-k8s.io domain. REFER : https://cluster-api.sigs.k8s.io/developer/architecture/controllers/metadata-propagation#machine. |
| taints | []k8s.io/api/core/v1.Taint | [] | Taints that you want to be propagated to each node in the nodegroup. |
HCloudConfig
| Field | Type | Default | Description |
|---|---|---|---|
| zone | string | ||
| imageName | string | ubuntu-26.04 | |
| natGatewayServerType | string | cpx22 | NATGatewayServerType is the HCloud server type for the NAT gateway that fronts the private network during bootstrap. cpx22 is a small, cost-optimised x86 box — ample for NAT. Override it if cpx22 is out of stock / not offered in your locations, or you need more throughput ( hcloud server-type list shows what's available). |
| hetznerNetwork | HetznerNetworkConfig | Hetzner Network specific details. |
HCloudControlPlane
| Field | Type | Default | Description |
|---|---|---|---|
| machineType | string | ||
| replicas | uint | ||
| loadBalancer | HCloudControlPlaneLoadBalancer |
HCloudControlPlaneLoadBalancer
| Field | Type | Default | Description |
|---|---|---|---|
| enabled | bool | ||
| region | string | ||
| endpoint | string | Endpoint is the FQDN clients use to reach kube-apiserver (CAPI's controlPlaneEndpoint.host, kubeadm cert SAN, kubeconfig server URL). Optional: when omitted, the LB private IP is used as the control-plane endpoint directly (no public interface, no DNS wait). When set, the LB gets a public interface during bootstrap and kubeaid-cli waits for the operator's DNS A-record to land before continuing. DNS resolution is the operator's responsibility. |
HCloudVPNClusterConfig
| Field | Type | Default | Description |
|---|---|---|---|
| name | string |
HetznerBareMetalConfig
| Field | Type | Default | Description |
|---|---|---|---|
| wipeDisks | bool | false | |
| installImage | InstallImageConfig | ||
| firewall | FirewallConfig | Firewall configures the Cilium host-firewall policy (CiliumClusterwideNetworkPolicy) that locks down each bare-metal node's public NIC. Enabled controls whether kubeaid-cli renders the policy at all; AllowSSHFrom feeds the per-CIDR SSH ingress rule. See docs/hetzner-bare-metal-network-surface.md. | |
| zfs | ZFSConfig | ZFS specific configuration. Every node runs a ZFS pool, named primary. We carve out storage for container images, pod logs and pod ephemeral volumes from that ZFS pool, as required. The ZFS pool has RAIDZ-1 enabled, which means it can survive single disk failure. | |
| vSwitch | VSwitchConfig | Details about the VSwitch which'll be used to connect the Hetzner Bare Metal servers with the Hetzner Network. |
HetznerBareMetalControlPlane
| Field | Type | Default | Description |
|---|---|---|---|
| endpoint | HetznerBareMetalControlPlaneEndpoint | ||
| bareMetalHosts | []HetznerBareMetalHost | ||
| zfs | ZFSConfig | ZFS pool size on each control-plane node. See ZFSConfig.Size for sizing rules. |
HetznerBareMetalControlPlaneEndpoint
| Field | Type | Default | Description |
|---|---|---|---|
| isFailoverIP | bool | ||
| host | string |
HetznerBareMetalHost
| Field | Type | Default | Description |
|---|---|---|---|
| serverID | string | ||
| privateIP | string |
HetznerBareMetalNodeGroup
| Field | Type | Default | Description |
|---|---|---|---|
| bareMetalHosts | []HetznerBareMetalHost | ||
| zfs | ZFSConfig | ZFS specific configuration. Every node runs a ZFS pool, named primary. We carve out storage for container images, pod logs and pod ephemeral volumes from that ZFS pool, as required. The ZFS pool has RAIDZ-1 enabled, which means it can survive single disk failure. | |
| name | string | Nodegroup name. | |
| labels | map[string]string | [] | Labels that you want to be propagated to each node in the nodegroup. Each label should meet one of the following criterias to propagate to each of the nodes : 1. Has node-role.kubernetes.io as prefix. 2. Belongs to node-restriction.kubernetes.io domain. 3. Belongs to node.cluster.x-k8s.io domain. REFER : https://cluster-api.sigs.k8s.io/developer/architecture/controllers/metadata-propagation#machine. |
| taints | []k8s.io/api/core/v1.Taint | [] | Taints that you want to be propagated to each node in the nodegroup. |
HetznerConfig
| Field | Type | Default | Description |
|---|---|---|---|
| mode | string | hcloud | The Hetzner mode to use : (1) hcloud : Both the control-plane and the nodegroups will be in HCloud. (2) bare-metal : Both the control-plane and the nodegroups will be in Hetzner Bare Metal. (3) hybrid : The control-plane will be in HCloud, and each node-group can be either in HCloud or Hetzner Bare Metal. |
| hcloudVPNCluster | HCloudVPNClusterConfig | Details about the VPN cluster you have in HCloud. | |
| sshKeyPair | HetznerSSHKeyPair | Details about the SSH keypair which will be used to SSH into the HCloud or / and Hetzner Bare Metal server. KubeAid CLI will create the corresponding HCloud or / and Hetzner Bare Metal SSH keypairs, if it / they doesn't already exist. | |
| hcloud | HCloudConfig | HCloud specific details. | |
| bareMetal | HetznerBareMetalConfig | Hetzner bare-metal specific details. | |
| controlPlane | HetznerControlPlane | Control-plane specific details. | |
| nodeGroups | HetznerNodeGroups | Details about the node-groups. |
HetznerControlPlane
| Field | Type | Default | Description |
|---|---|---|---|
| hcloud | HCloudControlPlane | ||
| bareMetal | HetznerBareMetalControlPlane | ||
| regions | []string | Regions is the list of Hetzner regions (lower-case IDs: "fsn1", "hel1", "ash", ...) the CAPH chart constrains control-plane placement to. At least one is required. | |
| extraCertSANs,omitempty | []string | ExtraCertSANs are additional DNS names added to the apiserver's TLS cert SAN list, on every Hetzner mode (hcloud, bare-metal, hybrid). The chart merges these with endpoint.host into kubeadm's apiServer.certSANs. Use for any additional hostnames clients reach the apiserver under. |
HetznerCredentials
| Field | Type | Default | Description |
|---|---|---|---|
| apiToken | string | APIToken is the HCloud Cloud-API token. Required for every Hetzner mode. | |
| robot | HetznerRobotCredentials |
HetznerNetworkConfig
| Field | Type | Default | Description |
|---|---|---|---|
| cidr | string | ||
| hcloudServersSubnetCIDR | string |
HetznerNodeGroups
Details about node-groups in Hetzner.
| Field | Type | Default | Description |
|---|---|---|---|
| hcloud | []HCloudAutoScalableNodeGroup | Details about node-groups in HCloud. | |
| bareMetal | []HetznerBareMetalNodeGroup | Details about node-groups in Hetzner Bare Metal. |
HetznerRobotCredentials
| Field | Type | Default | Description |
|---|---|---|---|
| user | string | ||
| password | string |
HetznerSSHKeyPair
| Field | Type | Default | Description |
|---|---|---|---|
| name | string | ||
| privateKeyFilePath | string | PrivateKeyFilePath is the on-disk SSH private key kubeaid-cli reads to derive PublicKey + Fingerprint and (for cloud-side SSH connections like the Hetzner NAT gateway setup) to authenticate the SSH session. Required when UseSSHAgent is false; ignored when UseSSHAgent is true (the agent owns the private key — yubikey case — so there's nothing on disk to point at). Cross-field validation in pkg/config/parser/validate.go enforces "exactly one is set". | |
| useSSHAgent | bool | UseSSHAgent flips the SSH key sourcing from "read a file from PrivateKeyFilePath" to "dial $SSH_AUTH_SOCK and ask the agent for its loaded identities". The first identity supplies PublicKey + Fingerprint; the SSH client (kubeone) signs through the agent socket so yubikey-resident private keys never need to be exported. |
HostPathMountConfig
REFER : "sigs.k8s.io/cluster-api/bootstrap/kubeadm/api/v1beta1".HostPathMount
| Field | Type | Default | Description |
|---|---|---|---|
| name | string | ||
| hostPath | string | ||
| mountPath | string | ||
| pathType | k8s.io/api/core/v1.HostPathType | ||
| readOnly | bool | true | Whether the mount should be read-only. |
InstallImageConfig
| Field | Type | Default | Description |
|---|---|---|---|
| imagePath | string | /root/.oldroot/nfs/images/Ubuntu-2604-resolute-amd64-base.tar.zst | |
| vg0 | VG0Config |
KeycloakConfig
KeycloakConfig declares the Keycloak instance a VPN cluster hosts as NetBird's SSO IdP. The parser derives the Realm from DNS when unset and validates the combination against cluster.type. The admin password is generated by kubeaid-cli at bootstrap and never lives in this struct or in secrets.yaml; only Mode/DNS/Realm are user-facing.
| Field | Type | Default | Description |
|---|---|---|---|
| mode | string | Mode is "managed" (kubeaid-cli installs Keycloak via the keycloakx Helm chart on this cluster — VPN clusters only) or "external" (Keycloak is already running elsewhere; supply DNS only). Workload clusters must use external. | |
| dns | string | DNS is the public hostname Keycloak is reachable at, e.g. "keycloak.vpn.acme.com". Required. Used to derive the OIDC issuer URL the apiserver and kubelogin trust, and (when Realm is unset) to default the realm name. | |
| realm | string | Realm is the Keycloak realm name. Optional — when empty, kubeaid-cli derives it from DNS via golang.org/x/net/publicsuffix.EffectiveTLDPlusOne and thefirst dot-separated segment of the result. Examples: keycloak.vpn.acme.com → "acme" keycloak.foo.co.uk → "foo" Set this explicitly to override the derivation. |
KeycloakCredentials
KeycloakCredentials carries Keycloak-related secrets — admin credentials and OIDC client secrets the operator either supplies (external mode) or kubeaid-cli auto-generates and persists into secrets.yaml (managed mode, via FillMissingSecrets).
All fields are persisted in secrets.yaml so SealedSecret renders are byte-stable across re-runs — the alternative (read-or-generate from the in-cluster Secret) caused the re-encryption noise that produced spurious PRs on every run.
| Field | Type | Default | Description |
|---|---|---|---|
| adminPassword | string | AdminPassword is templated into the keycloak-admin SealedSecret's KEYCLOAK_PASSWORD key. Required when cluster.keycloak.mode is "managed"; ignored otherwise. FillMissingSecrets generates a value here on first run if the field is empty. | |
| netBirdBackendClientSecret | string | NetBirdBackendClientSecret is the confidential-client secret for the netbird-backend OIDC client. In external mode the operator creates the client in their Keycloak and supplies the resulting secret here. In managed mode FillMissingSecrets generates it, the realm reconciler creates the Keycloak client with this exact value, and the netbird SealedSecret is templated with the same value — single source of truth either way. |
KubeAidForkConfig
KubeAid repository specific details.
| Field | Type | Default | Description |
|---|---|---|---|
| url | string | KubeAid repository SSH URL. | |
| version | string | KubeAid git ref (tag / branch / commit). |
KubePrometheusConfig
| Field | Type | Default | Description |
|---|---|---|---|
| version | string | ||
| grafanaURL | string |
KubeaidConfigForkConfig
KubeAid Config repository specific details.
| Field | Type | Default | Description |
|---|---|---|---|
| url | string | KubeAid Config repository SSH URL. | |
| directory | string | Name of the directory inside your KubeAid Config repository's k8s folder, where the KubeAid Config files for this cluster will be contained. When not specified, the directory name will default to the cluster name. So, suppose your cluster name is 'staging'. Then, the directory name will default to 'staging'. Or you can customize it to something like 'staging.qa'. |
KubeaidStoragectlConfig
KubeaidStoragectlConfig pins the kubeaid-storagectl release. See GeneralConfig.KubeaidStoragectl for when to set it.
| Field | Type | Default | Description |
|---|---|---|---|
| version | string | Version is the GitHub release tag of kubeaid-storagectl — rendered into the chart as global.kubeaidStoragectl.versionand used to build the releases/download/<version>/ URL thenode's preKubeadm wget hits. Empty string is treated as "not set" and falls back to kubeaid-cli's own version, same as omitting the parent block. |
LocalConfig
Local specific.
| Field | Type | Default | Description |
|---|
NetBirdClusterProxyConfig
NetBirdClusterProxyConfig configures the netbird-operator kube-apiserver
proxy (netbird-operator.clusterProxy in the chart values). The proxy
registers under cluster.name (netbird kubernetes write-kubeconfig
| Field | Type | Default | Description |
|---|---|---|---|
| enabled | bool | Enabled toggles the cluster proxy. | |
| rbac | []NetBirdClusterProxyRBACConfig | RBAC binds NetBird groups to cluster roles via the proxy's identity impersonation. |
NetBirdClusterProxyRBACConfig
NetBirdClusterProxyRBACConfig binds one NetBird group to one ClusterRole through the cluster proxy.
| Field | Type | Default | Description |
|---|---|---|---|
| group | string | ||
| clusterRole | string |
NetBirdConfig
NetBirdConfig describes this cluster's relationship to the NetBird mesh. It is valid for both cluster.type=vpn (which hosts NetBird Mgmt) and cluster.type=workload (which only joins the mesh): dns/stun/turn are meaningful only on the VPN host, while dnsZone applies to any cluster on the mesh. cluster.type is the gate.
| Field | Type | Default | Description |
|---|---|---|---|
| dns | string | DNS is the public hostname NetBird Management is reachable at, e.g. "netbird.vpn.acme.com". Required only for cluster.type=vpn (enforced in parser/keycloak.go); unused on workload clusters. | |
| dnsZone | string | DNSZone is the mesh DNS domain peers resolve under — NetBird Mgmt's --dns-domain, e.g. "mesh.acme.com". Operator-supplied, no default. Required for cluster.type=vpn and for workload clusters that join a mesh; absent on workload clusters that don't. Used to create the DNS zone on NetBird, to drive --dns-domain on VPN clusters, and to add the kubernetes. | |
| stunDNS | string | StunDNS is the public hostname Coturn answers STUN queries on, e.g. "stun.vpn.acme.com". Optional: kubeaid-cli derives it as "stun." where base is DNS with the leading "netbird." stripped (so netbird.vpn.acme.com → stun.vpn.acme.com). Override only when STUN is exposed on a non-standard FQDN. | |
| turnDNS | string | TurnDNS is the public hostname Coturn answers TURN queries on, e.g. "turn.vpn.acme.com". Optional: derived as "turn." by the same logic as StunDNS. | |
| turnUser | string | netbird | TurnUser is the static username Coturn / NetBird Mgmt agree on for TURN authentication. The matching password is generated and persisted in the Secret. Optional, defaults to "netbird". |
| clusterProxy | NetBirdClusterProxyConfig | ClusterProxy configures the netbird-operator's kube-apiserver proxy (operator >= 0.7.0): a mesh peer that proxies kubectl to the in-cluster apiserver, impersonating the caller's NetBird identity. Omit the block to leave it disabled. | |
| groups | []string | Groups are extra NetBird groups this cluster OWNS (chart: groups), beyond the derived k8s- cluster only — a duplicate wedges that operator on HTTP 409. |
NetBirdCredentials
NetBirdCredentials carries the random secrets NetBird's in-cluster components need at startup. All fields are auto-generated by FillMissingSecrets when blank. Persisted in secrets.yaml for re-run stability — same rationale as KeycloakCredentials.
| Field | Type | Default | Description |
|---|---|---|---|
| datastoreEncryptionKey | string | DatastoreEncryptionKey is the AES key NetBird Mgmt uses to encrypt its data store. base64(32 random bytes); the chart base64-decodes it back to 32 raw bytes for AES-256. | |
| relayPassword | string | RelayPassword is the shared secret between NetBird Mgmt and the in-cluster Relay deployment. Alphanumeric so it flows cleanly through Helm values + envFrom. | |
| turnPassword | string | TurnPassword is the credential the NetBird agents use to authenticate with Coturn (TURN server). Same value is templated into both the netbird Secret (Mgmt-side) and the netbird-turn-credentials Secret (Coturn-side) — the two MUST match or relayed TURN auth fails. | |
| apiKey | string | APIKey is a NetBird Management service-user access token (nbp_…) the netbird-operator authenticates to the Mgmt API with — minting setup keys for routing peers, managing groups / networks / policies. Created manually in the NetBird dashboard: Team → Service Users → create → generate access token (a service user, not a personal PAT, so it survives offboarding). NOT auto-generated by FillMissingSecrets — only the Mgmt dashboard can mint it. Rendered into the netbird/netbird-mgmt-api-key SealedSecret whose NB_API_KEY the operator Deployment reads (the chart's default secret ref). When blank, the SealedSecret is skipped and bootstrap pauses at netbird.AwaitOperatorToken with instructions instead. |
NodeGroup
| Field | Type | Default | Description |
|---|---|---|---|
| name | string | Nodegroup name. | |
| labels | map[string]string | [] | Labels that you want to be propagated to each node in the nodegroup. Each label should meet one of the following criterias to propagate to each of the nodes : 1. Has node-role.kubernetes.io as prefix. 2. Belongs to node-restriction.kubernetes.io domain. 3. Belongs to node.cluster.x-k8s.io domain. REFER : https://cluster-api.sigs.k8s.io/developer/architecture/controllers/metadata-propagation#machine. |
| taints | []k8s.io/api/core/v1.Taint | [] | Taints that you want to be propagated to each node in the nodegroup. |
ObmondoConfig
| Field | Type | Default | Description |
|---|---|---|---|
| customerID | string | ||
| monitoring | bool | ||
| certPath | string | Path to the mTLS client cert issued by Obmondo. Required when Monitoring is true — kubeaid-agent uses it to authenticate to the Obmondo API, and kube-prometheus's Alertmanager uses it to push alerts to Obmondo's alert-receiver endpoint. | |
| keyPath | string | Path to the private key paired with CertPath. Required when Monitoring is true. |
OpenIDProviderSSHKeyPairConfig
| Field | Type | Default | Description |
|---|---|---|---|
| publicKeyFilePath | string | ||
| privateKeyFilePath | string | PrivateKeyFilePath is the on-disk SSH private key kubeaid-cli reads to derive PublicKey + Fingerprint and (for cloud-side SSH connections like the Hetzner NAT gateway setup) to authenticate the SSH session. Required when UseSSHAgent is false; ignored when UseSSHAgent is true (the agent owns the private key — yubikey case — so there's nothing on disk to point at). Cross-field validation in pkg/config/parser/validate.go enforces "exactly one is set". | |
| useSSHAgent | bool | UseSSHAgent flips the SSH key sourcing from "read a file from PrivateKeyFilePath" to "dial $SSH_AUTH_SOCK and ask the agent for its loaded identities". The first identity supplies PublicKey + Fingerprint; the SSH client (kubeone) signs through the agent socket so yubikey-resident private keys never need to be exported. |
SSHKeyPairConfig
| Field | Type | Default | Description |
|---|---|---|---|
| privateKeyFilePath | string | PrivateKeyFilePath is the on-disk SSH private key kubeaid-cli reads to derive PublicKey + Fingerprint and (for cloud-side SSH connections like the Hetzner NAT gateway setup) to authenticate the SSH session. Required when UseSSHAgent is false; ignored when UseSSHAgent is true (the agent owns the private key — yubikey case — so there's nothing on disk to point at). Cross-field validation in pkg/config/parser/validate.go enforces "exactly one is set". | |
| useSSHAgent | bool | UseSSHAgent flips the SSH key sourcing from "read a file from PrivateKeyFilePath" to "dial $SSH_AUTH_SOCK and ask the agent for its loaded identities". The first identity supplies PublicKey + Fingerprint; the SSH client (kubeone) signs through the agent socket so yubikey-resident private keys never need to be exported. |
SecretsConfig
| Field | Type | Default | Description |
|---|---|---|---|
| aws | AWSCredentials | ||
| azure | AzureCredentials | ||
| hetzner | HetznerCredentials | ||
| keycloak | KeycloakCredentials | ||
| netbird | NetBirdCredentials | ||
| acme | ACMECredentials |
UserConfig
| Field | Type | Default | Description |
|---|---|---|---|
| name | string | ||
| sshPublicKey | string |
VG0Config
| Field | Type | Default | Description |
|---|---|---|---|
| size | int | 80 | |
| rootVolumeSize | int | 50 |
VSwitchConfig
| Field | Type | Default | Description |
|---|---|---|---|
| vlanID | int | VLANID is the Hetzner vSwitch VLAN ID. Hetzner's webservice only accepts 4000-4091 (inclusive) — matches pkg/config/validate.{Min,Max}HetznerVLANID, enforced again here (not just at prompt time) so a config from outside the prompt (hand-written, or rendered by the Obmondo API) still fails fast instead of erroring against Hetzner's API mid-bootstrap. | |
| name | string | ||
| subnetCIDRBlock | string | SubnetCIDRBlock is the vSwitch subnet attached to the Hetzner Network. The IP written here doubles as the subnet's gateway (net.ParseCIDR's first return), so "10.0.1.0/24" yields gateway 10.0.1.0 — write the IP you want as the gateway, not just any address in the range. |
WorkloadIdentity
| Field | Type | Default | Description |
|---|---|---|---|
| openIDProviderSSHKeyPair | OpenIDProviderSSHKeyPairConfig |
ZFSConfig
| Field | Type | Default | Description |
|---|---|---|---|
| size | int | 220 | ZFS pool size (in GB), on each node in the corresponding node-group. Must be >= 200 GB : reserving 100 GB for container images, 50 GB for pod logs and 50 GB for pod ephemeral volumes. On top of that, if you want x GB of node-local storage for your workloads (like Redis), the ZFS pool size will be (200 + 2x) GB, keeping in mind that RAIDZ-1 is enabled. |