From cef9e94db022f14cb8e9bbcc93789073aeb74b51 Mon Sep 17 00:00:00 2001 From: Kanthi Subramanian Date: Thu, 6 Nov 2025 20:01:15 -0600 Subject: [PATCH] cover mapping for INT8/INT16 and isSigned(INT32) to Integer and Unsigned to Long. --- .../iceberg/parquet/MessageTypeToType.java | 16 +++++++++++++--- 1 file changed, 13 insertions(+), 3 deletions(-) diff --git a/ice/src/main/java/org/apache/iceberg/parquet/MessageTypeToType.java b/ice/src/main/java/org/apache/iceberg/parquet/MessageTypeToType.java index 72b19f0..c351a59 100644 --- a/ice/src/main/java/org/apache/iceberg/parquet/MessageTypeToType.java +++ b/ice/src/main/java/org/apache/iceberg/parquet/MessageTypeToType.java @@ -226,11 +226,21 @@ public Optional visit(LogicalTypeAnnotation.IntLogicalTypeAnnotation intTy intType.isSigned() || intType.getBitWidth() < 64, "Cannot use uint64: not a supported Java type"); */ - if (intType.getBitWidth() < 32) { - return Optional.of(Types.IntegerType.get()); - } else if (intType.getBitWidth() == 32 && intType.isSigned()) { + + // Preserve logical type information by choosing appropriate Iceberg types + // that can represent the full range of the original type + int bitWidth = intType.getBitWidth(); + boolean isSigned = intType.isSigned(); + + // Determine the appropriate Iceberg type based on bit width and signedness + if (bitWidth <= 16) { + // INT8/INT16, UINT8/UINT16 all fit in INT32 return Optional.of(Types.IntegerType.get()); + } else if (bitWidth <= 32) { + // INT32 fits in INT32, UINT32 needs INT64 to avoid overflow + return Optional.of(isSigned ? Types.IntegerType.get() : Types.LongType.get()); } else { + // INT64 needs INT64, UINT64 - best effort with INT64, may have range issues return Optional.of(Types.LongType.get()); } }