[FLINK-40488][table] Support UUID as a comparison, ordering key - #29128
Open
raminqaf wants to merge 3 commits into
Open
[FLINK-40488][table] Support UUID as a comparison, ordering key#29128raminqaf wants to merge 3 commits into
raminqaf wants to merge 3 commits into
Conversation
twalthr
reviewed
Sep 8, 2026
| && !isVariantType(type) | ||
| && !isBitmapType(type) | ||
| && !isUuidType(type); | ||
| && !isBitmapType(type); |
Contributor
There was a problem hiding this comment.
Why did you remove it here?
Contributor
Author
There was a problem hiding this comment.
Removed because the method isComparable returns true if the type is comparable. Before this PR UUID was not yet comparable.
raminqaf
force-pushed
the
FLINK-40488-uuid-comparison
branch
from
September 8, 2026 14:28
261b275 to
8aee200
Compare
raminqaf
force-pushed
the
FLINK-40488-uuid-comparison
branch
from
September 8, 2026 14:58
8aee200 to
283078f
Compare
twalthr
reviewed
Sep 8, 2026
| } else if (value instanceof RoaringBitmapData) { | ||
| convertedDataType = DataTypes.BITMAP(); | ||
| } else if (value instanceof UUID) { | ||
| convertedDataType = DataTypes.UUID(); |
Contributor
There was a problem hiding this comment.
Something is off here. All 3 cases (Variant, Bitmap, UUID) actually belong to ClassDataTypeConverter.
Contributor
Author
There was a problem hiding this comment.
That is true... The definition here is redundant. If we don't define the branch it should fall back to the else and get the defaultDataType from CalssDataTypeConverter.
raminqaf
force-pushed
the
FLINK-40488-uuid-comparison
branch
2 times, most recently
from
September 9, 2026 12:55
0a6fec0 to
3249efc
Compare
Allow a UUID to be used as a value literal in the expression layer. ValueDataTypeConverter now derives DataTypes.UUID() from a java.util.UUID value (so Expressions.lit(uuid) works), and ExpressionConverter builds the literal RexNode via RexBuilder.makeUuidLiteral, since RexBuilder.makeLiteral has no generic UUID support. This also lets filter push-down round-trip a UUID predicate back into a RexNode, and lets a UUID literal be serialized as UUID '...'.
Enable UUID as an ordering, grouping and join key. UUID is stored as its 16-byte big-endian encoding and orders by the same unsigned byte-wise comparison as binary strings, so it is routed through the existing binary compare paths (SortUtil.compareBinary for sorting and SqlFunctionUtils.byteArrayCompare for predicates) at the code-generation sites that previously threw: the comparability gate, comparison and sort code generation, and the normalized-key computer (a fixed 16-byte, fully determining key consistent with the DataStream UuidComparator).
raminqaf
force-pushed
the
FLINK-40488-uuid-comparison
branch
from
September 9, 2026 13:00
3249efc to
cac1123
Compare
twalthr
reviewed
Sep 9, 2026
…istent BITMAP and VARIANT are sealed built-in binary types with a single canonical internal representation, RoaringBitmapData and BinaryVariant. Their handling had diverged across the type system, and the canonical-form invariant was enforced in several overlapping places for BITMAP but only in the serializer for VARIANT. This change makes the two types follow the same paths and enforces the canonical form once per type, in the serializer: - BitmapType and VariantType use Class.isAssignableFrom in supportsInputConversion and supportsOutputConversion, dropping the static whitelist sets. - ClassDataTypeConverter and ValueDataTypeConverter resolve both types to their interface conversion class uniformly. - DataStructureConverters returns a shared stateless IdentityConverter.INSTANCE for both types, removing the bespoke BitmapBitmapConverter and the redundant switch guard. - DataFormatConverters.BitmapConverter becomes a plain identity converter, matching VariantConverter. - BitmapSerializer.serialize enforces the canonical form via RoaringBitmapData.toRoaringBitmapData, matching VariantSerializer. There is no user-facing change for the supported implementations. A non-canonical conversion class is now rejected at the serialization boundary instead of by a plan-time whitelist.
raminqaf
force-pushed
the
FLINK-40488-uuid-comparison
branch
from
September 9, 2026 15:53
cac1123 to
a5ce72e
Compare
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
What is the purpose of the change
The main purpose is to make the
UUIDtype usable as a key and as a value literal in Table API and SQL. This is a subtask of FLIP-604 (FLINK-40488).UUIDis stored internally as its 16-byte big-endian encoding, and the type defines ordering as the unsigned big-endian byte comparison of that encoding. This is the same ordering Flink's binary compare helpers already implement (SortUtil.compareBinary,SqlFunctionUtils.byteArrayCompare), and it matches the DataStreamUuidComparatorand how PostgreSQL orders UUIDs. The change routesUUIDthrough those existing paths rather than adding new comparison logic.COUNT(DISTINCT uuid)is intentionally left out, consistent withBINARY/VARBINARY, and is deferred to a follow-up.The PR also contains a related cleanup (FLINK-40616): it makes the sibling sealed built-in binary types,
VARIANTandBITMAP, handle conversions consistently and removes redundant checks. It is kept as a separate commit.Brief change log
UUID value literals (FLINK-40488):
ValueDataTypeConverter/ExpressionConverter/ValueLiteralExpression:UUIDvalue literals andUUID '...'serialization.UUID comparison and ordering (FLINK-40488):
TypeCheckUtils#isComparable:UUIDis comparable.GenerateUtils#generateCompareandScalarOperatorGens#generateComparison:UUIDuses the unsigned binary comparison.SortCodeGenerator:UUIDgets a fixed 16-byte normalized key.BITMAP/VARIANT consistency (FLINK-40616):
BitmapType/VariantType:supports{Input,Output}ConversionuseClass.isAssignableFrom, dropping the per-type whitelist sets.ClassDataTypeConverter/ValueDataTypeConverter: both types resolve to their interface conversion class uniformly.DataStructureConverters: both return a shared, statelessIdentityConverter.INSTANCE;BitmapBitmapConverteris removed.DataFormatConverters.BitmapConverter: plain identity converter, matchingVariantConverter.BitmapSerializer.serialize: enforces the canonical form viaRoaringBitmapData.toRoaringBitmapData, matchingVariantSerializer.Verifying this change
UUID (FLINK-40488):
SortCodeGeneratorTest: addsUUIDto the randomized sort harness with0x00…/0x80…/0xff…boundary values that make unsigned and signed byte orders disagree.UuidSemanticTest(streaming and batch): equality, column comparison, a> UUID '...'literal filter,ORDER BY(as a bounded Top-N),GROUP BY, and a join on aUUIDkey.ExpressionTest,ValueDataTypeConverterTest:UUIDvalue-literal extraction and value-based type derivation.CastFunctionITCase:UUIDcasts driven throughlit(uuid)andUUIDinput fields.BITMAP/VARIANT (FLINK-40616):
ClassDataTypeConverterTest,ValueDataTypeConverterTest,TypeInferenceExtractorTest,DataStructureConvertersTest,ExternalSerializerTest,DataFormatConvertersTest,BitmapSerializerTest,VariantSerializerTest.Does this pull request potentially affect one of the following parts:
@Public(Evolving):ValueLiteralExpressionis@PublicEvolving;UUIDhandling is additive within existing methods, with no signature or contract change.BitmapTypeandVariantTypeare@PublicEvolving;supports{Input,Output}Conversionnow accept any subtype of the respective interface viaisAssignableFrominstead ognature change.BitmapSerializer.serializenow routes throughRoaringBitmapData.toRoaringBitmapData; the wire format isunchanged (byte-identical for
RoaringBitmapData), o is added, consistent withVariantSerializer. Nostate-compatibility impact. NoUUIDserializer change.BITMAPconversion drops a redundant per-record guard, and both binary types share a single statelessidentity converter. No other type's path changes.
Documentation
UUIDtype is tracked separately under FLINK-40494. The FLINK-40616 change is an internal consistency refactor with no usWas generative AI tooling used to co-author thi
Generated-by: Claude Code (Opus 4.8)