apache/beam · error · IllegalArgumentException

Failed to parse DirectedReadOptions from string: + directedR

Error message

Failed to parse DirectedReadOptions from string: + directedReadOptions

What it means

SpannerConfig.parseDirectedReadOptions() converts a JSON string into a protobuf DirectedReadOptions using JsonFormat.parser().merge(). If the string is not valid JSON for the DirectedReadOptions protobuf schema, it wraps the InvalidProtocolBufferException in an IllegalArgumentException, so users get a clear message about the offending string.

Source

Thrown at sdks/java/io/google-cloud-platform/src/main/java/org/apache/beam/sdk/io/gcp/spanner/SpannerConfig.java:379

  /** Specifies the Cloud Spanner directed read options from a string representation. */
  public SpannerConfig withDirectedReadOptions(String directedReadOptions) {
    if (directedReadOptions == null || directedReadOptions.isEmpty()) {
      return this;
    }
    return withDirectedReadOptions(parseDirectedReadOptions(directedReadOptions));
  }

  @VisibleForTesting
  static DirectedReadOptions parseDirectedReadOptions(String directedReadOptions) {
    if (directedReadOptions == null || directedReadOptions.isEmpty()) {
      return DirectedReadOptions.getDefaultInstance();
    }
    DirectedReadOptions.Builder builder = DirectedReadOptions.newBuilder();
    try {
      JsonFormat.parser().merge(directedReadOptions, builder);
      return builder.build();
    } catch (InvalidProtocolBufferException e) {
      throw new IllegalArgumentException(
          "Failed to parse DirectedReadOptions from string: " + directedReadOptions, e);
    }
  }

  /** Specifies if the pipeline has to be run on the independent compute resource. */
  public SpannerConfig withDataBoostEnabled(ValueProvider<Boolean> dataBoostEnabled) {
    return toBuilder().setDataBoostEnabled(dataBoostEnabled).build();
  }

  /** Specifies the PartitionQuery timeout. */
  public SpannerConfig withPartitionQueryTimeout(Duration partitionQueryTimeout) {
    return withPartitionQueryTimeout(ValueProvider.StaticValueProvider.of(partitionQueryTimeout));
  }

  /** Specifies the PartitionQuery timeout. */
  public SpannerConfig withPartitionQueryTimeout(ValueProvider<Duration> partitionQueryTimeout) {
    return toBuilder().setPartitionQueryTimeout(partitionQueryTimeout).build();
  }

View on GitHub (pinned to 12126d8942)

Solutions

  1. Validate the string is JSON conforming to google.spanner.v1.DirectedReadOptions (use JsonFormat.printer on a builder to see the expected shape)
  2. Test parse locally with DirectedReadOptions.newBuilder() + JsonFormat.parser().merge before deploying
  3. Check for unknown/misspelled field names — JsonFormat rejects unrecognized fields by default
  4. Ensure CLI quoting preserves the JSON intact

Example fix

// before
config.withDirectedReadOptions("{replica_selection: {}}");
// after
config.withDirectedReadOptions("{\"replicaSelection\": {\"autoFailoverDisabled\": false}}");
Defensive patterns

Strategy: validation

Validate before calling

DirectedReadOptions.Builder probe = DirectedReadOptions.newBuilder();
JsonFormat.parser().merge(directedReadOptionsJson, probe); // throws before pipeline build if invalid

Try / catch

try { config = config.withDirectedReadOptions(json); } catch (IllegalArgumentException e) { throw new IllegalStateException("Bad DirectedReadOptions JSON: " + e.getMessage(), e); }

Prevention

When it happens

Trigger: Passing a malformed string to SpannerConfig.withDirectedReadOptions(String) — e.g. wrong field names (unknown fields), missing braces, non-JSON syntax, or fields not present in the DirectedReadOptions proto.

Common situations: Hand-writing the JSON in pipeline options; copying a YAML or proto-text representation instead of JSON; typos in fields like replicaSelection or includeReplicas; quoting/escaping issues when passing via CLI.

Understand the failure class

Background: "cannot parse invalid wire-format data", "cannot unmarshal", "failed unmarshalling": protobuf unmarshal errors explained — this error's family across 10 libraries.

Related errors


AI-assisted analysis of apache/beam@12126d8942 (2026-09-13). Data as JSON: /api/errors/d140952aa15d140c. Report an issue: GitHub.