kubernetes/kops · error
error reading actual policy document: %v
Error message
error reading actual policy document: %v
What it means
During RenderAWS of an IAMRolePolicy, when the task has changes to apply, kOps re-reads the current inline policy from IAM via policyDocumentString() to compare with the desired policy before diffing/updating. This error wraps any failure of that read — most commonly the resource rendering of PolicyDocument or the local 10240-byte size guard inside policyDocumentString(). It aborts the apply for this task without modifying the IAM role policy.
Source
Thrown at upup/pkg/fi/cloudup/awstasks/iamrolepolicy.go:257
return nil
}
return fmt.Errorf("error deleting IAMRolePolicy: %v", err)
}
return nil
}
doPut := false
if a == nil {
klog.V(2).Infof("Creating IAMRolePolicy")
doPut = true
} else if changes != nil {
if changes.PolicyDocument != nil {
klog.V(2).Infof("Applying changed role policy to %q:", *e.Name)
actualPolicy, err := a.policyDocumentString()
if err != nil {
return fmt.Errorf("error reading actual policy document: %v", err)
}
if actualPolicy == policy {
klog.Warning("Policies were actually the same")
} else {
d := diff.FormatDiff(actualPolicy, policy)
klog.V(2).Infof("diff: %s", d)
}
doPut = true
}
}
if doPut {
request := &iam.PutRolePolicyInput{}
request.PolicyDocument = aws.String(policy)
request.RoleName = e.Role.Name
request.PolicyName = e.NameView on GitHub (pinned to 4c8573c808)
Solutions
- Check the wrapped inner error (%v) — if it reports policy size, trim statements or move permissions to a managed policy.
- Validate the PolicyDocument JSON is well-formed and readable before running kops update.
- Re-run kops update with --v=2 to see which role policy failed and inspect the cluster spec's additionalPolicies.
- Split the policy into a separately managed IAM managed policy and attach it by ARN.
Example fix
// before: one huge inline policy in cluster spec additionalPolicies: [ <11KB JSON> ] // after: trim or attach a managed policy additionalPolicies: [ <condensed JSON with combined actions, wildcard resources where safe> ]
Defensive patterns
Strategy: validation
Validate before calling
policy, err := fi.ResourceAsString(task.PolicyDocument)
if err != nil { return err }
if len(strings.Join(strings.Fields(policy), "")) > 10240 { return fmt.Errorf("policy too large: %d bytes", len(policy)) } Try / catch
// kops CLI: wrap the update call
if err := applyCluster(ctx, cluster); err != nil {
if strings.Contains(err.Error(), "error reading actual policy document") {
klog.Errorf("IAM role policy unreadable/oversized: %v", err)
}
return err
} Prevention
- Keep inline role policies well under 10240 bytes; use managed policies for large permission sets.
- Validate policy JSON with `jq empty` before committing it to the cluster spec.
- Run `kops update --target=terraform` as a dry-run to catch policy problems before applying.
- Lint IAM policies with access-analyzer or cfn-policy-validator.
When it happens
Trigger: Apply with changes to an IAMRolePolicy where fi.ResourceAsString(e.PolicyDocument) fails (unreadable/nil PolicyDocument resource), or the serialized policy exceeds 10240 bytes (the size guard inside policyDocumentString returns its own error which is wrapped here).
Common situations: Oversized inline role policies after adding many permissions; a PolicyDocument resource whose backing file/asset cannot be read at apply time; corrupted or empty policy resource after a partial build.
Related errors
- error creating/updating IAMRolePolicy: %v
- IP version is incorrect
- provider ID cannot be empty
- provider ID number cannot be empty
- error listing hosted zones: %w
AI-assisted analysis of kubernetes/kops@4c8573c808 (2026-09-05).
Data as JSON: /api/errors/1d7d1252ed5b2fe4.
Report an issue: GitHub.