apache/iceberg · error · java.lang.UnsupportedOperationException

Transform is not supported

Error message

Transform is not supported: <transform>

What it means

Spark3Util.toIcebergTerm converts Spark sort/cluster expression transforms into Iceberg expressions. The default case of the transform switch throws UnsupportedOperationException when the Spark transform (e.g. an unsupported bucket/year variant or other function transform) has no Iceberg equivalent.

Solutions

  1. Restrict to supported transforms: identity, bucket, truncate, year/month/day/hour (and supported sort orders)
  2. Rewrite the query to use an Iceberg-supported transform expression
  3. Check the Iceberg version's supported transform list before using a transform in DDL

Example fix

// before
CLUSTER BY (sha2(col, 32));
// after
CLUSTER BY (bucket(16, col));
Defensive patterns

Strategy: validation

Validate before calling

java.util.Set<String> supported = java.util.Set.of(
    "identity","bucket","truncate","years","months","days","hours");
for (Transform<?, ?> t : transforms) {
  if (!supported.contains(t.name())) throw new IllegalArgumentException("Unsupported transform: " + t.name());
}

Try / catch

try {
  Spark3Util.toIcebergTerm(expr);
} catch (UnsupportedOperationException e) {
  // rewrite the transform to a supported one and retry
}

Prevention

When it happens

Trigger: Cluster/sort DDL using a Spark transform that the switch does not cover (unsupported named transform such as certain time units or functions) passed to toIcebergTerm.

Common situations: Using Spark SQL transform functions in CLUSTER BY / SORTED BY that Iceberg partitioning/sorting does not define; version drift between Spark transforms and Iceberg support matrix.

Understand the failure class

Background: UnsupportedOperationException and "is not supported" errors: when a library deliberately refuses a call — this error's family across 30 libraries.

Related errors


AI-assisted analysis of apache/iceberg@86d9c8fc54 (2026-09-12). Data as JSON: /api/errors/ebd68c58d443bb4a. Report an issue: GitHub.

Appendix: source

Thrown at spark/v4.2/spark/src/main/java/org/apache/iceberg/spark/Spark3Util.java:413

        case "hour":
        case "hours":
          return org.apache.iceberg.expressions.Expressions.hour(colName);
        case "truncate":
          return org.apache.iceberg.expressions.Expressions.truncate(colName, findWidth(transform));
        case "zorder":
          return new Zorder(
              Stream.of(transform.references())
                  .map(ref -> DOT.join(ref.fieldNames()))
                  .map(org.apache.iceberg.expressions.Expressions::ref)
                  .collect(Collectors.toList()));
        case "hilbert":
          return new Hilbert(
              Stream.of(transform.references())
                  .map(ref -> DOT.join(ref.fieldNames()))
                  .map(org.apache.iceberg.expressions.Expressions::ref)
                  .collect(Collectors.toList()));
        default:
          throw new UnsupportedOperationException("Transform is not supported: " + transform);
      }

    } else if (expr instanceof NamedReference) {
      NamedReference ref = (NamedReference) expr;
      return org.apache.iceberg.expressions.Expressions.ref(DOT.join(ref.fieldNames()));

    } else {
      throw new UnsupportedOperationException("Cannot convert unknown expression: " + expr);
    }
  }

  /**
   * Converts Spark transforms into a {@link PartitionSpec}.
   *
   * @param schema the table schema
   * @param partitioning Spark Transforms
   * @return a PartitionSpec
   */

View on GitHub (pinned to 86d9c8fc54)