apache/iceberg · error · UnsupportedOperationException

Expected value to be date or timestamp

Error message

Expected value to be date or timestamp: ${valueType.catalogString()}

What it means

Iceberg's days() transform function binds its single argument at planning time. Only DATE, TIMESTAMP, and TIMESTAMP_NTZ columns have a defined day-granularity transform; any other type is rejected with UnsupportedOperationException that includes the offending type's catalog string.

Solutions

  1. Cast the column to TIMESTAMP or DATE first: days(cast(ts_str AS TIMESTAMP)).
  2. For epoch-seconds BIGINT, convert: days(timestamp_seconds(epoch_col)).
  3. Use to_date() on the string column before applying days(): days(to_date(ts_str)).

Example fix

// before
SELECT iceberg.days(ts_string) FROM t;
// after
SELECT iceberg.days(CAST(ts_string AS TIMESTAMP)) FROM t;
Defensive patterns

Strategy: type-guard

Validate before calling

require(Seq(DateType, TimestampType, TimestampNTZType).exists(_.acceptsType(col.dataType)),
  s"days() requires date/timestamp, got ${col.dataType}")

Type guard

def isTemporalForDays(t: DataType): Boolean =
  t == DateType || t == TimestampType || t == TimestampNTZType

Prevention

When it happens

Trigger: Calling iceberg.days(col) where col is STRING, INT, BIGINT, or any non-temporal type — e.g. days(event_time_str) where event_time_str is a string timestamp.

Common situations: Passing a string-formatted timestamp stored as VARCHAR; passing a unix epoch BIGINT column assuming it works like Spark's to_date; calling days() on a date string column from an external source.

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


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

Appendix: source

Thrown at spark/v4.0/spark/src/main/java/org/apache/iceberg/spark/functions/DaysFunction.java:48

import org.apache.spark.sql.types.TimestampType;

/**
 * A Spark function implementation for the Iceberg day transform.
 *
 * <p>Example usage: {@code SELECT system.days('source_col')}.
 */
public class DaysFunction extends UnaryUnboundFunction {

  @Override
  protected BoundFunction doBind(DataType valueType) {
    if (valueType instanceof DateType) {
      return new DateToDaysFunction();
    } else if (valueType instanceof TimestampType) {
      return new TimestampToDaysFunction();
    } else if (valueType instanceof TimestampNTZType) {
      return new TimestampNtzToDaysFunction();
    } else {
      throw new UnsupportedOperationException(
          "Expected value to be date or timestamp: " + valueType.catalogString());
    }
  }

  @Override
  public String description() {
    return name()
        + "(col) - Call Iceberg's day transform\n"
        + "  col :: source column (must be date or timestamp)";
  }

  @Override
  public String name() {
    return "days";
  }

  protected abstract static class BaseToDaysFunction extends BaseScalarFunction<Integer>
      implements ReducibleFunction<Integer, Integer> {

View on GitHub (pinned to 86d9c8fc54)