kubernetes/kops · error

Subnet ID not set

Error message

Subnet ID not set

What it means

In RenderAWS, when the task specifies TagOnSubnet (deprecated mechanism to tag the associated subnet so the EIP can be rediscovered), kOps requires that subnet's ID to be resolved. If e.TagOnSubnet.ID is still nil at render time it throws 'Subnet ID not set' rather than tagging an undefined resource.

Source

Thrown at upup/pkg/fi/cloudup/awstasks/elastic_ip.go:258

			return fmt.Errorf("error creating ElasticIP: %v", err)
		}

		e.ID = response.AllocationId
		e.PublicIP = response.PublicIp
		publicIp = e.PublicIP
		eipId = response.AllocationId
	} else {
		publicIp = a.PublicIP
		eipId = a.ID
		if err := t.AddAWSTags(*e.ID, e.Tags); err != nil {
			return err
		}
	}

	// Tag the associated subnet
	if e.TagOnSubnet != nil {
		if e.TagOnSubnet.ID == nil {
			return fmt.Errorf("Subnet ID not set")
		}
		tags := make(map[string]string)
		tags["AssociatedElasticIp"] = *publicIp
		tags["AssociatedElasticIpAllocationId"] = *eipId // Leaving this in for reference, even though we don't use it
		err := t.AddAWSTags(*e.TagOnSubnet.ID, tags)
		if err != nil {
			return fmt.Errorf("Unable to tag subnet %v", err)
		}
	} else {
		// TODO: Figure out what we can do.  We're sort of stuck between wanting to have one code-path with
		// terraform, and having a bigger "window of loss" here before we create the NATGateway
		klog.V(2).Infof("ElasticIP %q not tagged on subnet; risk of leaking", fi.ValueOf(publicIp))
	}

	return nil
}

type terraformElasticIP struct {

View on GitHub (pinned to 4c8573c808)

Solutions

  1. Fix the spec so TagOnSubnet references a real subnet of the cluster (verify with `kops get cluster -oyaml` / kops edit cluster)
  2. Remove TagOnSubnet if not needed — modern kOps discovers NAT-gateway EIPs via AssociatedNatGatewayRouteTable instead
  3. Ensure the referenced Subnet task renders successfully (no earlier errors) so its ID is populated before RenderAWS
  4. Migrate to the AssociatedNatGatewayRouteTable pattern for NAT EIP discovery

Example fix

// before
tagOnSubnet: legacy-subnet-name // task ID unresolved
// after: use route-table association or a valid subnet
associatedNatGatewayRouteTable: private-us-east-1a
Defensive patterns

Strategy: validation

Validate before calling

if e.TagOnSubnet != nil && e.TagOnSubnet.ID == nil {
    return errors.New("TagOnSubnet must reference a resolved subnet with an ID")
}

Try / catch

if err != nil && strings.Contains(err.Error(), "Subnet ID not set") {
    // fix spec: point TagOnSubnet at a real subnet or drop the field
}

Prevention

When it happens

Trigger: An ElasticIP task defines TagOnSubnet as a Subnet task reference whose ID was never resolved — e.g. the subnet task hasn't been created/looked up yet, or the spec references a subnet by name that doesn't exist in the cluster so no ID was populated during Find.

Common situations: Hand-edited cluster specs referencing a nonexistent subnet for TagOnSubnet; NAT gateway EIP definitions where the subnet task failed earlier in the run; legacy cluster configs using the deprecated TagOnSubnet field after subnet IDs changed.

Related errors


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