Skip to content

Commit bad6717

Browse files
authored
Interpret full-supported UUID type correctly in JDBC server (#3515)
This PR (1) adds the missing support in `DataType` and gRPC-related classes for the future UUID type. This is needed to maintain compatibility in mixed-mode testing with the future full-support version. It is relatively difficult to test this on the `main` as we cannot bring in the support in the current PR. However, here is the PR for re-introducing the full support: #3510 (2). I have tested that (2) is backward compatible with fixes in (1). Hence, if (1) releases first, and then we bring in (2) we will maintain compatibility to "older" version JDBC servers.
1 parent 80d5e7c commit bad6717

File tree

3 files changed

+90
-0
lines changed
  • fdb-relational-api/src/main/java/com/apple/foundationdb/relational/api/metadata
  • fdb-relational-core/src/main/java/com/apple/foundationdb/relational/recordlayer/metadata
  • fdb-relational-grpc/src/main/java/com/apple/foundationdb/relational/jdbc

3 files changed

+90
-0
lines changed

fdb-relational-api/src/main/java/com/apple/foundationdb/relational/api/metadata/DataType.java

Lines changed: 77 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -68,6 +68,7 @@ public abstract class DataType {
6868
typeCodeJdbcTypeMap.put(Code.DOUBLE, Types.DOUBLE);
6969
typeCodeJdbcTypeMap.put(Code.STRING, Types.VARCHAR);
7070
typeCodeJdbcTypeMap.put(Code.ENUM, Types.OTHER);
71+
typeCodeJdbcTypeMap.put(Code.UUID, Types.OTHER);
7172
typeCodeJdbcTypeMap.put(Code.BYTES, Types.BINARY);
7273
typeCodeJdbcTypeMap.put(Code.VERSION, Types.BINARY);
7374
typeCodeJdbcTypeMap.put(Code.STRUCT, Types.STRUCT);
@@ -801,6 +802,79 @@ public String toString() {
801802
}
802803
}
803804

805+
public static final class UuidType extends DataType {
806+
@Nonnull
807+
private static final UuidType NOT_NULLABLE_INSTANCE = new UuidType(false);
808+
809+
@Nonnull
810+
private static final UuidType NULLABLE_INSTANCE = new UuidType(true);
811+
812+
@Nonnull
813+
private final Supplier<Integer> hashCodeSupplier = Suppliers.memoize(this::computeHashCode);
814+
815+
private UuidType(boolean isNullable) {
816+
super(isNullable, true, Code.UUID);
817+
}
818+
819+
@Override
820+
@Nonnull
821+
public DataType withNullable(boolean isNullable) {
822+
if (isNullable) {
823+
return Primitives.NULLABLE_UUID.type();
824+
} else {
825+
return Primitives.UUID.type();
826+
}
827+
}
828+
829+
@Override
830+
public boolean isResolved() {
831+
return true;
832+
}
833+
834+
@Nonnull
835+
@Override
836+
public DataType resolve(@Nonnull Map<String, Named> resolutionMap) {
837+
return this;
838+
}
839+
840+
@Nonnull
841+
public static UuidType nullable() {
842+
return NULLABLE_INSTANCE;
843+
}
844+
845+
@Nonnull
846+
public static UuidType notNullable() {
847+
return NOT_NULLABLE_INSTANCE;
848+
}
849+
850+
private int computeHashCode() {
851+
return Objects.hash(getCode(), isNullable());
852+
}
853+
854+
@Override
855+
public int hashCode() {
856+
return hashCodeSupplier.get();
857+
}
858+
859+
@Override
860+
public boolean equals(Object other) {
861+
if (this == other) {
862+
return true;
863+
}
864+
865+
if (!(other instanceof UuidType)) {
866+
return false;
867+
}
868+
final var otherUuidType = (UuidType) other;
869+
return this.isNullable() == otherUuidType.isNullable();
870+
}
871+
872+
@Override
873+
public String toString() {
874+
return "uuid" + (isNullable() ? " ∪ ∅" : "");
875+
}
876+
}
877+
804878
public static final class NullType extends DataType {
805879

806880
@Nonnull
@@ -1426,6 +1500,7 @@ public enum Code {
14261500
BYTES,
14271501
VERSION,
14281502
ENUM,
1503+
UUID,
14291504
STRUCT,
14301505
ARRAY,
14311506
UNKNOWN,
@@ -1443,6 +1518,7 @@ public enum Primitives {
14431518
STRING(StringType.notNullable()),
14441519
BYTES(BytesType.notNullable()),
14451520
VERSION(VersionType.notNullable()),
1521+
UUID(UuidType.notNullable()),
14461522
NULLABLE_BOOLEAN(BooleanType.nullable()),
14471523
NULLABLE_LONG(LongType.nullable()),
14481524
NULLABLE_INTEGER(IntegerType.nullable()),
@@ -1451,6 +1527,7 @@ public enum Primitives {
14511527
NULLABLE_STRING(StringType.nullable()),
14521528
NULLABLE_BYTES(BytesType.nullable()),
14531529
NULLABLE_VERSION(VersionType.nullable()),
1530+
NULLABLE_UUID(UuidType.nullable()),
14541531
NULL(NullType.INSTANCE)
14551532
;
14561533

fdb-relational-core/src/main/java/com/apple/foundationdb/relational/recordlayer/metadata/DataTypeUtils.java

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -148,6 +148,7 @@ public static Type toRecordLayerType(@Nonnull final DataType type) {
148148
primitivesMap.put(DataType.Primitives.BYTES.type(), Type.primitiveType(Type.TypeCode.BYTES, false));
149149
primitivesMap.put(DataType.Primitives.STRING.type(), Type.primitiveType(Type.TypeCode.STRING, false));
150150
primitivesMap.put(DataType.Primitives.VERSION.type(), Type.primitiveType(Type.TypeCode.VERSION, false));
151+
primitivesMap.put(DataType.Primitives.UUID.type(), Type.uuidType(false));
151152

152153
primitivesMap.put(DataType.Primitives.NULLABLE_BOOLEAN.type(), Type.primitiveType(Type.TypeCode.BOOLEAN, true));
153154
primitivesMap.put(DataType.Primitives.NULLABLE_INTEGER.type(), Type.primitiveType(Type.TypeCode.INT, true));
@@ -157,6 +158,8 @@ public static Type toRecordLayerType(@Nonnull final DataType type) {
157158
primitivesMap.put(DataType.Primitives.NULLABLE_BYTES.type(), Type.primitiveType(Type.TypeCode.BYTES, true));
158159
primitivesMap.put(DataType.Primitives.NULLABLE_STRING.type(), Type.primitiveType(Type.TypeCode.STRING, true));
159160
primitivesMap.put(DataType.Primitives.NULLABLE_VERSION.type(), Type.primitiveType(Type.TypeCode.VERSION, true));
161+
primitivesMap.put(DataType.Primitives.NULLABLE_UUID.type(), Type.uuidType(true));
162+
160163
primitivesMap.put(DataType.Primitives.NULL.type(), Type.nullType());
161164
}
162165
}

fdb-relational-grpc/src/main/java/com/apple/foundationdb/relational/jdbc/TypeConversion.java

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -44,6 +44,7 @@
4444
import com.apple.foundationdb.relational.jdbc.grpc.v1.column.ListColumnMetadata;
4545
import com.apple.foundationdb.relational.jdbc.grpc.v1.column.Struct;
4646
import com.apple.foundationdb.relational.jdbc.grpc.v1.column.Type;
47+
import com.apple.foundationdb.relational.jdbc.grpc.v1.column.Uuid;
4748
import com.apple.foundationdb.relational.util.PositionalIndex;
4849
import com.google.common.annotations.VisibleForTesting;
4950
import com.google.protobuf.ByteString;
@@ -226,6 +227,8 @@ private static Type toProtobufType(@Nonnull DataType type) {
226227
return Type.VERSION;
227228
case ENUM:
228229
return Type.ENUM;
230+
case UUID:
231+
return Type.UUID;
229232
default:
230233
throw new RelationalException("not supported in toProtobuf: " + type, ErrorCode.INTERNAL_ERROR).toUncheckedWrappedException();
231234
}
@@ -462,6 +465,13 @@ private static Column toColumn(@Nonnull DataType.StructType.Field field, @Nonnul
462465
column = toColumn(wasNull ? null : (Double) value,
463466
(a, b) -> a == null ? b.clearDouble() : b.setDouble(a));
464467
break;
468+
case UUID:
469+
column = toColumn(wasNull ? null : (UUID) value,
470+
(a, b) -> a == null ? b.clearUuid() : b.setUuid(Uuid.newBuilder()
471+
.setMostSignificantBits(a.getMostSignificantBits())
472+
.setLeastSignificantBits(a.getLeastSignificantBits())
473+
.build()));
474+
break;
465475
default:
466476
throw new SQLException("DataType: " + field.getType() + " not supported",
467477
ErrorCode.UNSUPPORTED_OPERATION.getErrorCode());

0 commit comments

Comments
 (0)