apache/iceberg · error · IllegalArgumentException
Unexpected object type for TIMESTAMP logical type. Received:
Error message
Unexpected object type for TIMESTAMP logical type. Received:
What it means
convertToTimestamp throws IllegalArgumentException when the Avro reader produces an object for a TIMESTAMP logical type that is neither java.time.LocalDateTime nor a Joda-time convertible object (and no Joda converter is available).
Source
Thrown at flink/v2.3/flink/src/main/java/org/apache/iceberg/flink/formats/avro/AvroToRowDataConverters.java:251
return TimestampData.fromEpochMillis(timeLong);
} else if (precision <= 6) {
return TimestampData.fromEpochMillis(
Math.floorDiv(timeLong, 1000L), (int) Math.floorMod(timeLong, 1000L) * 1000);
} else {
// Iceberg: Added support for nanoseconds precision (FLINK-39251)
return TimestampData.fromEpochMillis(
Math.floorDiv(timeLong, 1_000_000L), (int) Math.floorMod(timeLong, 1_000_000L));
}
} else if (object instanceof Instant) {
return TimestampData.fromInstant((Instant) object);
} else if (object instanceof LocalDateTime) {
return TimestampData.fromLocalDateTime((LocalDateTime) object);
} else {
JodaConverter jodaConverter = JodaConverter.getConverter();
if (jodaConverter != null) {
return TimestampData.fromEpochMillis(jodaConverter.convertTimestamp(object));
} else {
throw new IllegalArgumentException(
"Unexpected object type for TIMESTAMP logical type. Received: " + object);
}
}
}
private static int convertToDate(Object object) {
if (object instanceof Integer) {
return (Integer) object;
} else if (object instanceof LocalDate) {
return (int) ((LocalDate) object).toEpochDay();
} else {
JodaConverter jodaConverter = JodaConverter.getConverter();
if (jodaConverter != null) {
return (int) jodaConverter.convertDate(object);
} else {
throw new IllegalArgumentException(
"Unexpected object type for DATE logical type. Received: " + object);
}View on GitHub (pinned to 86d9c8fc54)
Solutions
- Ensure the Avro reader returns java.time.LocalDateTime for timestamp fields (use a matching Avro datum reader version)
- Add org.joda:joda-time to the classpath if reading data produced by old Avro writers
- Normalize upstream Avro writing to the ISO/LocalDateTime encoding this converter expects
Example fix
// before
Object object = record.get("ts"); // java.util.Date — throws
// after
LocalDateTime object = ((Instant) record.get("ts")).atZone(ZoneOffset.UTC).toLocalDateTime(); Defensive patterns
Strategy: type-guard
Validate before calling
if (!(object instanceof LocalDateTime) && !isJodaDateTime(object)) { throw new IllegalArgumentException("Expected LocalDateTime for TIMESTAMP field, got " + object.getClass()); } Type guard
boolean isTimestampDatum(Object o) { return o instanceof LocalDateTime || o instanceof org.joda.time.LocalDateTime; } Try / catch
try { return convertToTimestamp(object); } catch (IllegalArgumentException e) { throw new IllegalStateException("Avro writer produced unexpected timestamp encoding: " + e.getMessage(), e); } Prevention
- Confirm joda-time is on the classpath if reading legacy Avro data
- Pin Avro reader versions that emit java.time types
- Test against real files from each producer version
When it happens
Trigger: Avro datum is e.g. a java.util.Date, Long, or Instant while the converter expects LocalDateTime or a Joda class; Joda-Time not on classpath so legacy objects cannot be converted.
Common situations: Mixed Avro writer versions: newer writers emit java.time types, older writers emit Joda or millis-Long; missing joda-time dependency in the Flink job.
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
- Unexpected object type for TIMESTAMP logical type. Received:
- Unexpected object type for TIMESTAMP logical type. Received:
- Unexpected object type for TIMESTAMP logical type. Received:
- Unexpected object type for DATE logical type. Received:
- Unexpected object type for TIME logical type. Received:
AI-assisted analysis of apache/iceberg@86d9c8fc54 (2026-09-12).
Data as JSON: /api/errors/48d8904a3b4ba2c5.
Report an issue: GitHub.