apache/beam · error
non-UTF8 compliant string found
Error message
non-UTF8 compliant string found: %q
What it means
This error is raised by the Beam Go pipeline vet checker when a string field inside a struct element in the pipeline graph is not valid UTF-8. Beam requires all string data in PCollections to be UTF-8 compliant, and checkStructFieldsUTF8 walks struct fields via reflection to catch violations before the pipeline runs.
Solutions
- Fix the data source so strings are valid UTF-8 (decode with a charset converter such as golang.org/x/text/encoding before inserting into the pipeline)
- Validate input data with utf8.ValidString before adding elements and handle invalid records explicitly
- Replace invalid bytes with utf8.RuneError using a repair pass (e.g. strings.ToValidUTF8)
- Store binary data as []byte instead of string fields
Example fix
// before s := string(rawLatin1Bytes) // after s := strings.ToValidUTF8(string(rawLatin1Bytes), string(utf8.RuneError))
Defensive patterns
Strategy: validation
Validate before calling
if !utf8.ValidString(s) { return fmt.Errorf("invalid UTF-8 in %q", s) } // run before adding elements to the pipeline Type guard
func isValidUTF8(s string) bool { return utf8.ValidString(s) } Prevention
- Decode legacy encodings (Latin-1 etc.) to UTF-8 at ingestion
- Run utf8.ValidString checks on external data before pipeline insertion
- Use strings.ToValidUTF8 as a sanitization pass
- Prefer []byte for binary data instead of string
When it happens
Trigger: Passing a struct to a beam.Create or similar transform whose string field bytes are invalid UTF-8 (e.g. raw binary data, Latin-1 encoded bytes, or truncated multi-byte sequences) stored in a reflect.String field.
Common situations: Reading legacy-encoded text files (ISO-8859-1/Windows-1252), decoding binary protocols into strings without conversion, or data corruption from byte slicing that splits a multi-byte UTF-8 character.
Understand the failure class
Background: Schema validation failed / invalid input schema: payload rejected because its shape doesn't match the expected schema — this error's family across 28 libraries.
Related errors
AI-assisted analysis of apache/beam@12126d8942 (2026-09-13).
Data as JSON: /api/errors/6ab24387a6ba9677.
Report an issue: GitHub.
Appendix: source
Thrown at sdks/go/pkg/beam/runners/vet/vet.go:555
for i := 0; i < v.Len(); i++ {
if err := e.checkStructFieldsUTF8(v.Index(i), seen); err != nil {
return err
}
}
case reflect.Map:
iter := v.MapRange()
for iter.Next() {
if err := e.checkStructFieldsUTF8(iter.Key(), seen); err != nil {
return err
}
if err := e.checkStructFieldsUTF8(iter.Value(), seen); err != nil {
return err
}
}
case reflect.String:
str := v.String()
if !utf8.ValidString(str) {
return fmt.Errorf("non-UTF8 compliant string found: %q", str)
}
}
return nil
}
// We need to take graph.Fns (which can be created from any from graph.NewFn)
// and convert them to all needed function caller signatures,
// and emitters.
//
// The type assertion shim Funcs need to be registered with reflectx.RegisterFunc
// Emitters need to be registered with exec.RegisterEmitter
// Iterators with exec.RegisterInput
// The types need to be registered with beam.RegisterType
// The user functions need to be registered with beam.RegisterFunction
//
// Registrations are all on the concrete element type, rather than the
// pointer type.
View on GitHub (pinned to 12126d8942)