kubernetes/kops · error
failed to parse objects: %w
Error message
failed to parse objects: %w
What it means
ClientApplier.Apply parses the raw YAML manifest into typed Kubernetes objects via kubemanifest.LoadObjectsFrom before applying them. If the manifest is not valid YAML or an object is malformed, parsing fails and the underlying error is wrapped with this message. Nothing is sent to the cluster.
Source
Thrown at channels/pkg/channels/clientapplier.go:39
"fmt"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
"k8s.io/client-go/dynamic"
"k8s.io/client-go/restmapper"
"k8s.io/kops/pkg/applylib/applyset"
"k8s.io/kops/pkg/kubemanifest"
)
type ClientApplier struct {
Client dynamic.Interface
RESTMapper *restmapper.DeferredDiscoveryRESTMapper
}
// Apply applies the manifest to the cluster.
func (p *ClientApplier) Apply(ctx context.Context, manifest []byte) error {
objects, err := kubemanifest.LoadObjectsFrom(manifest)
if err != nil {
return fmt.Errorf("failed to parse objects: %w", err)
}
// TODO: Cache applyset for more efficient applying
patchOptions := metav1.PatchOptions{
FieldManager: "kops",
}
// We force to overcome errors like: Apply failed with 1 conflict: conflict with "kubectl-client-side-apply" using apps/v1: .spec.template.spec.containers[name="foo"].image
// TODO: How to handle this better? In a controller we don't have a choice and have to force eventually.
// But we could do something like try first without forcing, log the conflict if there is one, and then force.
// This would mean that if there was a loop we could log/detect it.
// We could even do things like back-off on the force apply.
force := true
patchOptions.Force = &force
s, err := applyset.New(applyset.Options{
RESTMapper: p.RESTMapper,
Client: p.Client,View on GitHub (pinned to 4c8573c808)
Solutions
- Validate the manifest locally: kubectl apply --dry-run=client -f manifest.yaml or yamllint.
- Check for unresolved template placeholders and render templates before calling Apply.
- Confirm the fetched data is the actual YAML (not an HTML error page).
- Fix YAML indentation/syntax at the position given in the wrapped error.
- Regenerate the manifest from the upstream addon source.
Example fix
// before
err := applier.Apply(ctx, manifestBytes) // manifestBytes contains templated {{ .Foo }}
// after
rendered, err := renderTemplate(tmpl, data)
if err != nil { return err }
if err := yaml.Unmarshal(rendered, &struct{}{}); err != nil { return fmt.Errorf("invalid manifest: %w", err) }
err = applier.Apply(ctx, rendered) Defensive patterns
Strategy: validation
Validate before calling
var raw []map[string]any
if err := yaml.Unmarshal(manifest, &raw); err != nil {
return fmt.Errorf("manifest is not valid YAML: %w", err)
}
for i, o := range raw {
if o["apiVersion"] == nil || o["kind"] == nil {
return fmt.Errorf("object %d missing apiVersion/kind", i)
}
} Type guard
func isParseFailure(err error) bool {
return strings.Contains(err.Error(), "failed to parse objects")
} Try / catch
if err := applier.Apply(ctx, manifest); err != nil {
if isParseFailure(err) {
return fmt.Errorf("fix manifest before applying: %w", err)
}
return err
} Prevention
- Render all templates before passing bytes to Apply.
- Run kubectl apply --dry-run=client -f as a pre-check.
- Lint YAML with yamllint/kubeconform in CI.
- Ensure fetched URLs return YAML, not HTML error pages.
When it happens
Trigger: Calling Apply with a manifest containing YAML syntax errors, invalid Kubernetes object structure, unknown/malformed kinds, or non-UTF8 bytes.
Common situations: Hand-edited addon manifests; templating left unresolved placeholders (e.g. {{ }}) in the YAML; wrong file loaded (HTML error page from a failed fetch); schema drift after Kubernetes API changes.
Understand the failure class
- Parsing and encoding errors: unexpected token, malformed input — why parsers reject input and how to find the real culprit.
Related errors
- error parsing addons or manifest: %v
- failed to parse objects: %w
- parsing yaml: %w
- error parsing addon %q: %v
- error parsing yaml: %v
AI-assisted analysis of kubernetes/kops@4c8573c808 (2026-09-05).
Data as JSON: /api/errors/9bb48ff8dc7c88b5.
Report an issue: GitHub.