apache/iceberg · error
Cannot determine comparator for type: + type
Error message
Cannot determine comparator for type: + type
What it means
Comparators.forType() builds a java.util.Comparator for a given Iceberg primitive type. Types not covered by its if/else chain (e.g. non-primitive/nested types passed directly) have no comparator defined, so the library throws UnsupportedOperationException. Comparators are only defined for primitive types; nested types must go through the comparator builder.
Solutions
- Pass a primitive type (use field.type().asPrimitiveType()) to forType
- Use Comparators.comparator(schema) builder for nested struct/list/map types instead of forType
- Upgrade Iceberg if the type is a newer spec type supported by a newer version
Example fix
// before Comparator<T> c = Comparators.forType(structType); // after Comparator<T> c = Comparators.forType(field.type().asPrimitiveType());
Defensive patterns
Strategy: type-guard
Validate before calling
if (!type.isPrimitiveType()) throw new IllegalArgumentException("forType requires a primitive type: " + type); Type guard
boolean hasComparator(Type t) { return t.isPrimitiveType(); } Try / catch
try { cmp = Comparators.forType(type); } catch (UnsupportedOperationException e) { cmp = null; /* handle non-comparable type */ } Prevention
- Use the Comparators.comparator(schema) builder for nested types
- Pass asPrimitiveType() rather than raw field types
- Check for newer spec types before comparing
When it happens
Trigger: Calling Comparators.forType(Types.NestedField.type()) or forType with a StructType/ListType/MapType instead of a primitive type; passing an unknown or UNKNOWN type.
Common situations: Passing the whole field type instead of field.type().typeId()'s primitive; sorting/merging code hitting a newly added spec type (e.g. geometry/geography) on an older client version.
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
- Backup table name cannot be specified
- Batch reading is not supported in non-vectorized reader
- Bucket transform is not supported
- Can't modify an empty struct
- Can't retrieve values from an empty struct
AI-assisted analysis of apache/iceberg@86d9c8fc54 (2026-09-12).
Data as JSON: /api/errors/32ae20261849e0a6.
Report an issue: GitHub.
Appendix: source
Thrown at api/src/main/java/org/apache/iceberg/types/Comparators.java:77
return new ListComparator<>(list);
}
public static <K, V> Comparator<Map<K, V>> forType(Types.MapType mapType) {
return new MapComparator<>(mapType);
}
@SuppressWarnings("unchecked")
public static <T> Comparator<T> forType(Type.PrimitiveType type) {
Comparator<?> cmp = COMPARATORS.get(type);
if (cmp != null) {
return (Comparator<T>) cmp;
} else if (type instanceof Types.FixedType) {
return (Comparator<T>) Comparators.unsignedBytes();
} else if (type instanceof Types.DecimalType) {
return (Comparator<T>) Comparator.naturalOrder();
}
throw new UnsupportedOperationException("Cannot determine comparator for type: " + type);
}
@SuppressWarnings("unchecked")
private static <T> Comparator<T> internal(Type type) {
if (type.isPrimitiveType()) {
return forType(type.asPrimitiveType());
} else if (type.isStructType()) {
return (Comparator<T>) forType(type.asStructType());
} else if (type.isListType()) {
return (Comparator<T>) forType(type.asListType());
} else if (type.isMapType()) {
return (Comparator<T>) forType(type.asMapType());
}
throw new UnsupportedOperationException("Cannot determine comparator for type: " + type);
}
private static class StructLikeComparator implements Comparator<StructLike> {View on GitHub (pinned to 86d9c8fc54)