apache/beam · error
Nested FullValues must be nested as pointers.
Error message
Nested FullValues must be nested as pointers.
What it means
When encoding composite types, convertIfNeeded wraps values for FullValue-based coders. A nested FullValue must be passed as *FullValue (a pointer); passing a FullValue by value cannot be handled (the function needs a stable, possibly overwritable slot), so it panics. This indicates the value was constructed/typed incorrectly upstream.
Source
Thrown at sdks/go/pkg/beam/core/runtime/exec/coder.go:638
// the contents of the first element, but returning the FullValue unchanged
// if it has two elements.
//
// Technically drops window and timestamp info, so only use when those are
// expected to be empty.
func elideSingleElmFV(fv *FullValue) any {
if fv.Elm2 == nil {
return fv.Elm
}
return fv
}
// convertIfNeeded reuses Wrapped KVs if needed, but accepts pointer
// to a pre-allocated non-nil *FullValue for overwriting and use.
func convertIfNeeded(v any, allocated *FullValue) *FullValue {
if fv, ok := v.(*FullValue); ok {
return fv
} else if _, ok := v.(FullValue); ok {
panic("Nested FullValues must be nested as pointers.")
}
*allocated = FullValue{Elm: v}
return allocated
}
type nullableEncoder struct {
inner ElementEncoder
be boolEncoder
}
func (n *nullableEncoder) Encode(value *FullValue, writer io.Writer) error {
if value.Elm == nil {
if err := n.be.Encode(&FullValue{Elm: false}, writer); err != nil {
return err
}
return nil
}
if err := n.be.Encode(&FullValue{Elm: true}, writer); err != nil {View on GitHub (pinned to 12126d8942)
Solutions
- Change the nested value to a *FullValue pointer (&fv) before encoding.
- If you only need to wrap a plain value, pass the raw value — convertIfNeeded wraps non-FullValue values automatically.
- Fix the producer code that constructs the nested element to use pointers for nested FullValues.
Example fix
// before
elm := exec.FullValue{Elm: x}
Encode(c, elm, w) // panics: value-typed nested FullValue
// after
elm := &exec.FullValue{Elm: x}
Encode(c, elm, w) Defensive patterns
Strategy: type-guard
Validate before calling
if fv, ok := v.(exec.FullValue); ok {
v = &fv // convert value-typed FullValue to pointer before encoding
} Type guard
func isValueFullValue(v any) bool {
_, ok := v.(exec.FullValue)
return ok
} Try / catch
// recover at pipeline-construction boundary
defer func() {
if r := recover(); r != nil {
err = fmt.Errorf("coder error: %v", r)
}
}() Prevention
- Always store nested FullValues as *FullValue in composite elements.
- Let convertIfNeeded wrap plain values; only pre-wrap when necessary, and use pointers.
- After Beam upgrades, re-test custom coders against exec package expectations.
When it happens
Trigger: Encoding an element where a nested field was stored as a FullValue value (not pointer) inside a KV/struct being encoded via exec.Encode or ProcessElement.
Common situations: Custom coders or user DoFns that build FullValue structs manually and forget to take the address; changes in the exec package's expectations when upgrading Beam versions.
Understand the failure class
Background: Type mismatch errors: IllegalArgumentException, TypeError and type guards across 150 open-source libraries — this error's family across 150 libraries.
Related errors
- %v
- received unknown value type: want a number:, got %T
- KV coder with more than 2 components: %s
- WindowedValue coder with more than 2 components: %s
- ShardedKey coder must have only 1 component: %s
AI-assisted analysis of apache/beam@12126d8942 (2026-09-13).
Data as JSON: /api/errors/d0c1a2c2bd08cc19.
Report an issue: GitHub.