kubernetes/kops · error

expected exactly one subnet for InstanceGroup %q; subnets wa

Error message

expected exactly one subnet for InstanceGroup %q; subnets was %s

What it means

During Azure VM ScaleSet model building, kops resolves the subnets of an InstanceGroup via GatherSubnets and requires exactly one, because an Azure VM ScaleSet can only be placed in a single subnet. If the instance group's spec lists zero or multiple subnets, buildVMScaleSetTask refuses to continue with this error.

Source

Thrown at pkg/model/azuremodel/vmscaleset.go:156

	}

	if n := len(b.SSHPublicKeys); n > 0 {
		if n > 1 {
			return nil, fmt.Errorf("expected at most one SSH public key; found %d keys", n)
		}
		t.SSHPublicKey = new(string(b.SSHPublicKeys[0]))
	}

	if t.UserData, err = b.BootstrapScriptBuilder.ResourceNodeUp(c, ig); err != nil {
		return nil, err
	}

	subnets, err := b.GatherSubnets(ig)
	if err != nil {
		return nil, err
	}
	if len(subnets) != 1 {
		return nil, fmt.Errorf("expected exactly one subnet for InstanceGroup %q; subnets was %s", ig.Name, ig.Spec.Subnets)
	}
	subnet := subnets[0]
	t.Subnet = b.LinkToAzureSubnet(subnet)

	switch subnet.Type {
	case kops.SubnetTypePublic, kops.SubnetTypeUtility:
		t.RequirePublicIP = new(true)
		if ig.Spec.AssociatePublicIP != nil {
			t.RequirePublicIP = ig.Spec.AssociatePublicIP
		}
	case kops.SubnetTypeDualStack, kops.SubnetTypePrivate:
		t.RequirePublicIP = new(false)
	default:
		return nil, fmt.Errorf("unexpected subnet type: for InstanceGroup %q; type was %s", ig.Name, subnet.Type)
	}

	if ig.Spec.Role.HasControlPlane() && b.Cluster.Spec.API.LoadBalancer != nil {
		t.LoadBalancer = &azuretasks.LoadBalancer{

View on GitHub (pinned to 4c8573c808)

Solutions

  1. Edit the InstanceGroup so spec.subnets contains exactly one subnet name, then run `kops update cluster --yes`.
  2. If multi-AZ is desired on Azure, create one InstanceGroup per subnet/zone instead of listing multiple subnets in one group.
  3. Verify the referenced subnet names exist in the cluster spec (spec.subnets) and match the cluster's topology.

Example fix

// before (instancegroup nodes)
subnets:
- subnet-a
- subnet-b
// after
subnets:
- subnet-a
Defensive patterns

Strategy: validation

Validate before calling

ig := cluster.InstanceGroup("nodes")
if ig != nil && len(ig.Spec.Subnets) != 1 {
  return fmt.Errorf("azure instance group %q must list exactly one subnet, got %d", ig.Name, len(ig.Spec.Subnets))
}

Prevention

When it happens

Trigger: Running `kops update cluster` (or building the Azure model) with an InstanceGroup whose spec.subnets contains 0 or more than 1 subnet names on an Azure cluster.

Common situations: Copying an AWS instance group config (which supports multiple subnets) to Azure; forgetting to define subnets; typos duplicated in the subnets list; multi-AZ configs pasted from AWS/GCP examples.

Related errors


AI-assisted analysis of kubernetes/kops@4c8573c808 (2026-09-05). Data as JSON: /api/errors/f45dfb3882e7f5b8. Report an issue: GitHub.