kubernetes/kops · error

unable to convert %T to unstructured: %w

Error message

unable to convert %T to unstructured: %w

What it means

FromRuntimeObject converts a typed Kubernetes runtime.Object into an unstructured map via runtime.DefaultUnstructuredConverter.ToUnstructured. If the object cannot be represented as a generic map (unsupported fields, nil pointer, or a type registered without proper JSON tags / conversion reflection issues), this error wraps the underlying failure.

Source

Thrown at pkg/kubemanifest/manifest.go:57

func NewObject(data map[string]interface{}) *Object {
	return &Object{data: data}
}

// ToUnstructured converts the object to an unstructured.Unstructured
func (o *Object) ToUnstructured() *unstructured.Unstructured {
	return &unstructured.Unstructured{Object: o.data}
}

// GroupVersionKind returns the group/version/kind information for the object
func (o *Object) GroupVersionKind() schema.GroupVersionKind {
	return o.ToUnstructured().GroupVersionKind()
}

// FromRuntimeObject converts from a runtime.Object.
func FromRuntimeObject(obj runtime.Object) (*Object, error) {
	data, err := runtime.DefaultUnstructuredConverter.ToUnstructured(obj)
	if err != nil {
		return nil, fmt.Errorf("unable to convert %T to unstructured: %w", obj, err)
	}
	return NewObject(data), nil
}

// ObjectList describes a list of objects, allowing us to add bulk-methods
type ObjectList []*Object

// LoadObjectsFrom parses multiple objects from a yaml file
func LoadObjectsFrom(contents []byte) (ObjectList, error) {
	var objects []*Object

	sections := text.SplitContentToSections(contents)

	for _, section := range sections {
		// We need this so we don't error on a section that is empty / commented out
		if !hasYAMLContent(section) {
			continue
		}

View on GitHub (pinned to 4c8573c808)

Solutions

  1. Check the object is non-nil before calling FromRuntimeObject
  2. Add proper `json:"..."` struct tags to custom Go types used as runtime.Objects
  3. Use unstructured.Unstructured directly if the type cannot round-trip through the converter
  4. Inspect the wrapped error message for the specific field causing conversion failure

Example fix

// before
var obj *v1.Pod // nil
o, err := kubemanifest.FromRuntimeObject(obj) // error
// after
if obj == nil { return fmt.Errorf("object is nil") }
o, err := kubemanifest.FromRuntimeObject(obj)
Defensive patterns

Strategy: validation

Validate before calling

func safeFromRuntimeObject(obj runtime.Object) (*kubemanifest.Object, error) {
	if obj == nil || reflect.ValueOf(obj).IsNil() {
		return nil, fmt.Errorf("runtime.Object is nil")
	}
	return kubemanifest.FromRuntimeObject(obj)
}

Type guard

func isNilObject(obj runtime.Object) bool {
	return obj == nil || reflect.ValueOf(obj).Kind() == reflect.Ptr && reflect.ValueOf(obj).IsNil()
}

Try / catch

o, err := kubemanifest.FromRuntimeObject(obj)
if err != nil {
	return fmt.Errorf("cannot serialize %T: %w", obj, err)
}

Prevention

When it happens

Trigger: Passing a runtime.Object that is nil, a typed object whose Go struct fields are incompatible with unstructured conversion, or an unregistered/custom type to FromRuntimeObject.

Common situations: Programmatically constructing addon/manifest objects from typed structs in kOps tooling; passing a pointer that is nil; using custom CRD Go types without json tags.

Related errors


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