apache/iceberg · error · IllegalArgumentException
Unsupported primitive type for decimal: <type>
Error message
Unsupported primitive type for decimal: <type>
What it means
Thrown by ParquetConversions.convertValue when converting a Parquet value to an Iceberg DECIMAL value and the Parquet column's primitive type is neither INT32, INT64, FIXED_LEN_BYTE_ARRAY nor BINARY. Decimal values in Parquet must be stored in one of those physical types, so any other primitive reaching this converter is invalid.
Source
Thrown at parquet/src/main/java/org/apache/iceberg/parquet/ParquetConversions.java:67
case STRING:
return (T) ((Binary) value).toStringUsingUTF8();
case UUID:
return (T) UUIDUtil.convert(((Binary) value).toByteBuffer());
case FIXED:
case BINARY:
return (T) ((Binary) value).toByteBuffer();
case DECIMAL:
int scale =
((DecimalLogicalTypeAnnotation) parquetType.getLogicalTypeAnnotation()).getScale();
switch (parquetType.getPrimitiveTypeName()) {
case INT32:
case INT64:
return (T) BigDecimal.valueOf(((Number) value).longValue(), scale);
case FIXED_LEN_BYTE_ARRAY:
case BINARY:
return (T) new BigDecimal(new BigInteger(((Binary) value).getBytes()), scale);
default:
throw new IllegalArgumentException(
"Unsupported primitive type for decimal: " + parquetType.getPrimitiveTypeName());
}
default:
throw new IllegalArgumentException("Unsupported primitive type: " + type);
}
}
static Function<Object, Object> converterFromParquet(
PrimitiveType parquetType, Type icebergType) {
Function<Object, Object> fromParquet = converterFromParquet(parquetType);
if (icebergType != null) {
if (icebergType.typeId() == Type.TypeID.LONG
&& parquetType.getPrimitiveTypeName() == PrimitiveType.PrimitiveTypeName.INT32) {
return value -> ((Integer) fromParquet.apply(value)).longValue();
} else if (icebergType.typeId() == Type.TypeID.DOUBLE
&& parquetType.getPrimitiveTypeName() == PrimitiveType.PrimitiveTypeName.FLOAT) {
return value -> ((Float) fromParquet.apply(value)).doubleValue();
} else if (icebergType.typeId() == Type.TypeID.UUID) {View on GitHub (pinned to 86d9c8fc54)
Solutions
- Rewrite/re-encode the Parquet file so the decimal column uses INT32/INT64/FIXED_LEN_BYTE_ARRAY/BINARY as appropriate for precision.
- Fix the Parquet schema at write time to declare the correct physical type for the decimal logical type.
- If you control the read path, use converterFromParquet only with compatible primitive types and guard the type beforehand.
Example fix
// before Types.DecimalType.of(38, 10) backed by a FLOAT Parquet column // after declare the column in Parquet as BINARY (DECIMAL logical type) or INT64 and re-encode the data
Defensive patterns
Strategy: validation
Validate before calling
org.apache.parquet.schema.PrimitiveType pt = parquetType.asPrimitiveType();
switch (pt.getPrimitiveTypeName()) {
case INT32: case INT64: case FIXED_LEN_BYTE_ARRAY: case BINARY: break;
default: throw new IllegalStateException("Decimal column has invalid physical type: " + pt.getPrimitiveTypeName());
} Type guard
boolean isDecimalSafe(PrimitiveType pt) {
return pt.getPrimitiveTypeName() == PrimitiveType.PrimitiveTypeName.INT32
|| pt.getPrimitiveTypeName() == PrimitiveType.PrimitiveTypeName.INT64
|| pt.getPrimitiveTypeName() == PrimitiveType.PrimitiveTypeName.FIXED_LEN_BYTE_ARRAY
|| pt.getPrimitiveTypeName() == PrimitiveType.PrimitiveTypeName.BINARY;
} Try / catch
try {
Object v = ParquetConversions.convertValue(parquetType, icebergType, ...);
} catch (IllegalArgumentException e) {
throw new SchemaParseException("Parquet decimal column has incompatible physical type", e);
} Prevention
- Validate Parquet schemas at ingest time against the Iceberg schema before reading.
- Standardize decimal physical types (INT32/INT64/FIXED_LEN_BYTE_ARRAY) in all writers.
- Reject non-conforming files at scan planning rather than mid-read.
When it happens
Trigger: Reading data whose Parquet schema declares a decimal logical type on an unexpected physical primitive (e.g. a corrupted or handcrafted schema), calling convertValue directly with a mismatched parquetType.
Common situations: Hand-written or third-party Parquet files with nonstandard decimal encodings; schema mismatch between the writer and reader; buggy custom writer libraries.
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
- Unsupported base type for decimal: " + primitive.getPrimitiv
- Unsupported base type for decimal:
- Buffer size of %d is larger than requested size of %d
- Cannot parse default as a %s value: %s
- Invalid primitive type for decimal:
AI-assisted analysis of apache/iceberg@86d9c8fc54 (2026-09-12).
Data as JSON: /api/errors/5ec0c2a089cd0fca.
Report an issue: GitHub.