apache/iceberg · error · IllegalStateException

Unknown type for long field. Type name: ${className}

Error message

Unknown type for long field. Type name: ${className}

What it means

StructRowData.getLong(pos) converts an internal value into a Flink long (epoch-based). It supports Integer, Long, LocalDate, LocalTime, LocalDateTime; anything else raises IllegalStateException 'Unknown type for long field'. This getter backs long/bigint/time/timestamp-millis fields.

Source

Thrown at flink/v1.20/flink/src/main/java/org/apache/iceberg/flink/data/StructRowData.java:151

  @Override
  public long getLong(int pos) {
    Object longVal = struct.get(pos, Object.class);

    if (longVal instanceof Long) {
      return (long) longVal;
    } else if (longVal instanceof OffsetDateTime) {
      return Duration.between(Instant.EPOCH, (OffsetDateTime) longVal).toNanos() / 1000;
    } else if (longVal instanceof LocalDate) {
      return ((LocalDate) longVal).toEpochDay();
    } else if (longVal instanceof LocalTime) {
      return ((LocalTime) longVal).toNanoOfDay();
    } else if (longVal instanceof LocalDateTime) {
      return Duration.between(Instant.EPOCH, ((LocalDateTime) longVal).atOffset(ZoneOffset.UTC))
              .toNanos()
          / 1000;
    } else {
      throw new IllegalStateException(
          "Unknown type for long field. Type name: " + longVal.getClass().getName());
    }
  }

  @Override
  public float getFloat(int pos) {
    return struct.get(pos, Float.class);
  }

  @Override
  public double getDouble(int pos) {
    return struct.get(pos, Double.class);
  }

  @Override
  public StringData getString(int pos) {
    return isNullAt(pos) ? null : getStringDataInternal(pos);
  }

View on GitHub (pinned to 86d9c8fc54)

Solutions

  1. Check the message's class name and align the field's declared Flink type with the actual value class (e.g. use TIMESTAMP(6) not BIGINT for LocalDateTime-backed fields).
  2. Ensure the value reader (FlinkValueReaders/Avro reader) produces supported classes (Integer, Long, LocalDate, LocalTime, LocalDateTime).
  3. Fix the Iceberg schema so the field type matches the data (e.g. Types.LongType for a long field).
  4. Convert the value before it reaches StructRowData, e.g. in a custom projection or reader.

Example fix

// before: reader stores OffsetDateTime, Flink field is BIGINT
rowType = ROW<ts BIGINT> // getInt->getLong sees OffsetDateTime, throws
// after: declare the Flink field as TIMESTAMP(6) or convert value to epoch micros Long before projection
Defensive patterns

Strategy: type-guard

Validate before calling

if (!(v instanceof Integer || v instanceof Long || v instanceof LocalDate || v instanceof LocalTime || v instanceof LocalDateTime)) {
  throw new IllegalArgumentException("value not long-compatible: " + v.getClass());
}

Type guard

boolean isLongCompatible(Object v) {
  return v instanceof Integer || v instanceof Long || v instanceof LocalDate
      || v instanceof LocalTime || v instanceof LocalDateTime;
}

Try / catch

try {
  long l = structRow.getLong(pos);
} catch (IllegalStateException e) {
  if (e.getMessage().startsWith("Unknown type for long field")) {
    // convert value to epoch-based Long or fix the declared field type
  }
}

Prevention

When it happens

Trigger: A field projected as BIGINT/TIME/TIMESTAMP whose underlying Iceberg value is an unexpected class (e.g. String, TimestampData, OffsetDateTime) - usually from a schema/read-schema mismatch or a custom value reader emitting a different representation.

Common situations: Timestamp field conversions where the reader returned OffsetDateTime but StructRowData expects Long/LocalDateTime; partition values or statistics columns with different classes; reading tables written by other Iceberg versions with different time representations.

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