apache/beam · error · IllegalArgumentException

%s requires an input Schema. Note that only Row or user clas

Error message

%s requires an input Schema. Note that only Row or user classes are supported. Consider using TextIO or FileIO directly when writing primitive types

What it means

JsonIO.Write.expand() requires the input PCollection to have a schema (via Beam's schema inference); only Row-backed or schema-annotated user classes are supported. If hasSchema() is false, it throws this IllegalArgumentException suggesting TextIO/FileIO for primitive types. JsonIO writes JSON via schema-derived serialization, so untyped PCollections cannot be handled.

Source

Thrown at sdks/java/io/json/src/main/java/org/apache/beam/sdk/io/json/JsonIO.java:267

    @AutoValue.Builder
    abstract static class Builder<T> {

      /**
       * The underlying {@link FileIO.Write} that writes converted input to JSON formatted output.
       */
      abstract Builder<T> setTextIOWrite(TextIO.Write value);

      abstract Write<T> autoBuild();

      final Write<T> build() {
        return autoBuild();
      }
    }

    @Override
    public WriteFilesResult<String> expand(PCollection<T> input) {
      if (!input.hasSchema()) {
        throw new IllegalArgumentException(
            String.format(
                "%s requires an input Schema. Note that only Row or user classes are supported. Consider using TextIO or FileIO directly when writing primitive types",
                Write.class.getName()));
      }

      Schema schema = input.getSchema();

      RowCoder rowCoder = RowCoder.of(schema);

      PCollection<Row> rows =
          input
              .apply("To Rows", MapElements.into(rows()).via(input.getToRowFunction()))
              .setCoder(rowCoder);

      SerializableFunction<Row, String> toJsonFn =
          JsonUtils.getRowToJsonStringsFunction(input.getSchema());

      PCollection<String> json = rows.apply("To JSON", MapElements.into(strings()).via(toJsonFn));

View on GitHub (pinned to 12126d8942)

Solutions

  1. Use TextIO.write() for PCollection<String> of raw JSON text instead of JsonIO.
  2. Annotate your POJO with @DefaultSchema and register it via SchemaRegistry, or convert to Row via setSchema.
  3. Apply a schema-providing transform (e.g. withTypeDescriptor/setRowSchema) before JsonIO.write.

Example fix

// before
pc.apply("write", JsonIO.write().to(path)); // pc is PCollection<String>
// after
pc.apply("write", TextIO.write().to(path));
// or give the PCollection a schema:
pc.setSchema(schema); pc.apply(JsonIO.write().to(path));
Defensive patterns

Strategy: type-guard

Validate before calling

if (input == null || !input.hasSchema()) {
  // use TextIO.write() for raw strings, or set a schema first
}

Type guard

boolean isSchemaBacked(PCollection<?> pc) {
  return pc != null && pc.hasSchema();
}

Try / catch

try { pc.apply(JsonIO.write().to(out)); }
catch (IllegalArgumentException e) {
  if (e.getMessage().contains("requires an input Schema")) { /* switch to TextIO or add schema */ }
  throw e;
}

Prevention

When it happens

Trigger: Calling JsonIO.write() on a PCollection<String>, PCollection<Map<...>>, or other primitive/untyped collection without a registered schema or TypeDescriptor.

Common situations: Applying JsonIO.write directly to raw JSON strings read from TextIO; using POJOs without @DefaultSchema/GetSchema annotations; passing primitive types that Beam cannot infer schemas for.

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/1538e9e3af5bcb4a. Report an issue: GitHub.