kubernetes/kops · error
error reading local-hostname from AWS metadata: %v
Error message
error reading local-hostname from AWS metadata: %v
What it means
When useIPBasedNodeNames is enabled on AWS, nodeup reads 'metadata://aws/meta-data/local-hostname' to verify the instance has an IP-based (DHCP-set) hostname. A read failure is wrapped with this message, since nodeup cannot decide whether the node name would be valid.
Source
Thrown at upup/pkg/fi/nodeup/command.go:503
return "", fmt.Errorf("error reading instance-id from AWS metadata: %v", err)
}
instanceID := string(instanceIDBytes)
if !useIPBasedNodeNames {
return instanceID, nil
}
// The node name is the DNS name that EC2 generates for IP-named instances, built from the
// primary private IPv4 address. kops-controller derives it with the same formula when
// issuing certificates, so the two always agree. IMDS local-hostname is not usable for
// this: with a custom DHCP domain it differs from the generated name.
//
// An instance launched with a resource-based hostname keeps a resource-based name (it can
// only change while the instance is stopped), so an IP-based node name would not match its
// EC2 hostname; fail rather than join a misconfigured instance.
hostnameBytes, err := vfs.Context.ReadFile("metadata://aws/meta-data/local-hostname")
if err != nil {
return "", fmt.Errorf("error reading local-hostname from AWS metadata: %v", err)
}
if strings.HasPrefix(string(hostnameBytes), instanceID) {
return "", fmt.Errorf("instance %s was launched with a resource-based hostname; useIPBasedNodeNames requires subnets that assign IP-based hostnames", instanceID)
}
localIPv4Bytes, err := vfs.Context.ReadFile("metadata://aws/meta-data/local-ipv4")
if err != nil {
return "", fmt.Errorf("error reading local-ipv4 from AWS metadata: %v", err)
}
localIPv4 := string(localIPv4Bytes)
if net.ParseIP(localIPv4).To4() == nil {
return "", fmt.Errorf("local-ipv4 from AWS metadata is not a valid IPv4 address: %q", localIPv4)
}
return awsbootstrap.PrivateDNSName(localIPv4, region), nil
case api.CloudProviderGCE:
// This lets us tolerate broken hostnames (i.e. systemd)View on GitHub (pinned to 4c8573c808)
Solutions
- Restore IMDS connectivity (test with curl against /latest/meta-data/local-hostname).
- Re-enable the metadata endpoint if disabled: aws ec2 modify-instance-metadata-options --http-endpoint enabled.
- Set hop limit >=2 for containerized nodeup.
- If IP-based names are not required, disable useIPBasedNodeNames in the cluster spec.
Defensive patterns
Strategy: validation
Validate before calling
H=$(curl -sf http://169.254.169.254/latest/meta-data/local-hostname) || { echo 'local-hostname metadata unavailable'; exit 1; }
echo "local-hostname=$H" Try / catch
override, err := evaluateHostnameOverride(provider, true /*useIPBasedNodeNames*/, region)
if err != nil && strings.Contains(err.Error(), "error reading local-hostname") {
return fmt.Errorf("useIPBasedNodeNames requires readable local-hostname metadata: %w", err)
} Prevention
- Validate metadata reachability before enabling useIPBasedNodeNames.
- Keep the metadata endpoint enabled and hop-limit >=2.
- Test node naming on one instance before rolling the setting cluster-wide.
- Fall back to instance-id node names if IP-based naming is not a hard requirement.
When it happens
Trigger: vfs.Context.ReadFile("metadata://aws/meta-data/local-hostname") errors while evaluateHostnameOverride runs with useIPBasedNodeNames=true: IMDS unreachable, metadata endpoint disabled, or hop-limit/token issues for IMDSv2.
Common situations: Cluster spec sets useIPBasedNodeNames but the node's metadata access is broken (network policy blocking link-local); nodeup running in a containerized context with hop limit 1; instance launched with metadata HttpEndpoint disabled.
Related errors
- failed to load AWS config: %w
- failed to get local-ipv4 address from ec2 metadata: %w
- error reading instance-id from AWS metadata: %v
- failed to get machine type: %w
- error reading local-ipv4 from AWS metadata: %v
AI-assisted analysis of kubernetes/kops@4c8573c808 (2026-09-05).
Data as JSON: /api/errors/470c6b1366ed8cbe.
Report an issue: GitHub.