org.duckdb.DuckDBVector Maven / Gradle / Ivy
Go to download
Show more of this group Show more artifacts with this name
Show all versions of duckdb_jdbc Show documentation
Show all versions of duckdb_jdbc Show documentation
A JDBC-Compliant driver for the DuckDB data management system
The newest version!
package org.duckdb;
import java.math.BigDecimal;
import java.math.BigInteger;
import java.nio.ByteBuffer;
import java.nio.ByteOrder;
import java.sql.Array;
import java.sql.Blob;
import java.sql.Date;
import java.sql.SQLException;
import java.sql.SQLFeatureNotSupportedException;
import java.sql.Struct;
import java.sql.Time;
import java.sql.Timestamp;
import java.time.LocalDate;
import java.time.LocalDateTime;
import java.time.LocalTime;
import java.time.OffsetDateTime;
import java.time.OffsetTime;
import java.time.format.DateTimeFormatter;
import java.time.format.DateTimeFormatterBuilder;
import java.time.format.TextStyle;
import java.time.temporal.ChronoField;
import java.util.Calendar;
import java.util.HashMap;
import java.util.Map;
import java.util.UUID;
import java.util.concurrent.TimeUnit;
class DuckDBVector {
// Constant to construct BigDecimals from hugeint_t
private final static BigDecimal ULONG_MULTIPLIER = new BigDecimal("18446744073709551616");
private final static DateTimeFormatter ERA_FORMAT =
new DateTimeFormatterBuilder()
.appendValue(ChronoField.YEAR_OF_ERA)
.appendLiteral("-")
.appendValue(ChronoField.MONTH_OF_YEAR)
.appendLiteral("-")
.appendValue(ChronoField.DAY_OF_MONTH)
.appendOptional(new DateTimeFormatterBuilder()
.appendLiteral(" (")
.appendText(ChronoField.ERA, TextStyle.SHORT)
.appendLiteral(")")
.toFormatter())
.toFormatter();
DuckDBVector(String duckdb_type, int length, boolean[] nullmask) {
super();
this.duckdb_type = DuckDBResultSetMetaData.TypeNameToType(duckdb_type);
this.meta = this.duckdb_type == DuckDBColumnType.DECIMAL
? DuckDBColumnTypeMetaData.parseColumnTypeMetadata(duckdb_type)
: null;
this.length = length;
this.nullmask = nullmask;
}
private final DuckDBColumnTypeMetaData meta;
protected final DuckDBColumnType duckdb_type;
final int length;
private final boolean[] nullmask;
private ByteBuffer constlen_data = null;
private Object[] varlen_data = null;
Object getObject(int idx) throws SQLException {
if (check_and_null(idx)) {
return null;
}
switch (duckdb_type) {
case BOOLEAN:
return getBoolean(idx);
case TINYINT:
return getByte(idx);
case SMALLINT:
return getShort(idx);
case INTEGER:
return getInt(idx);
case BIGINT:
return getLong(idx);
case HUGEINT:
return getHugeint(idx);
case UHUGEINT:
return getUhugeint(idx);
case UTINYINT:
return getUint8(idx);
case USMALLINT:
return getUint16(idx);
case UINTEGER:
return getUint32(idx);
case UBIGINT:
return getUint64(idx);
case FLOAT:
return getFloat(idx);
case DOUBLE:
return getDouble(idx);
case DECIMAL:
return getBigDecimal(idx);
case TIME:
return getLocalTime(idx);
case TIME_WITH_TIME_ZONE:
return getOffsetTime(idx);
case DATE:
return getLocalDate(idx);
case TIMESTAMP:
case TIMESTAMP_NS:
case TIMESTAMP_S:
case TIMESTAMP_MS:
return getTimestamp(idx);
case TIMESTAMP_WITH_TIME_ZONE:
return getOffsetDateTime(idx);
case JSON:
return getJsonObject(idx);
case BLOB:
return getBlob(idx);
case UUID:
return getUuid(idx);
case MAP:
return getMap(idx);
case LIST:
case ARRAY:
return getArray(idx);
case STRUCT:
return getStruct(idx);
case UNION:
return getUnion(idx);
default:
return getLazyString(idx);
}
}
LocalTime getLocalTime(int idx) {
if (check_and_null(idx)) {
return null;
}
if (isType(DuckDBColumnType.TIME)) {
long microseconds = getbuf(idx, 8).getLong();
long nanoseconds = TimeUnit.MICROSECONDS.toNanos(microseconds);
return LocalTime.ofNanoOfDay(nanoseconds);
}
String lazyString = getLazyString(idx);
return lazyString == null ? null : LocalTime.parse(lazyString);
}
LocalDate getLocalDate(int idx) {
if (check_and_null(idx)) {
return null;
}
if (isType(DuckDBColumnType.DATE)) {
return LocalDate.ofEpochDay(getbuf(idx, 4).getInt());
}
String lazyString = getLazyString(idx);
if ("infinity".equals(lazyString))
return LocalDate.MAX;
else if ("-infinity".equals(lazyString))
return LocalDate.MIN;
return lazyString == null ? null : LocalDate.from(ERA_FORMAT.parse(lazyString));
}
BigDecimal getBigDecimal(int idx) throws SQLException {
if (check_and_null(idx)) {
return null;
}
if (isType(DuckDBColumnType.DECIMAL)) {
switch (meta.type_size) {
case 16:
return new BigDecimal((int) getbuf(idx, 2).getShort()).scaleByPowerOfTen(meta.scale * -1);
case 32:
return new BigDecimal(getbuf(idx, 4).getInt()).scaleByPowerOfTen(meta.scale * -1);
case 64:
return new BigDecimal(getbuf(idx, 8).getLong()).scaleByPowerOfTen(meta.scale * -1);
case 128:
ByteBuffer buf = getbuf(idx, 16);
long lower = buf.getLong();
long upper = buf.getLong();
return new BigDecimal(upper)
.multiply(ULONG_MULTIPLIER)
.add(new BigDecimal(Long.toUnsignedString(lower)))
.scaleByPowerOfTen(meta.scale * -1);
}
}
Object o = getObject(idx);
return new BigDecimal(o.toString());
}
OffsetDateTime getOffsetDateTime(int idx) throws SQLException {
if (check_and_null(idx)) {
return null;
}
if (isType(DuckDBColumnType.TIMESTAMP_WITH_TIME_ZONE)) {
return DuckDBTimestamp.toOffsetDateTime(getbuf(idx, 8).getLong());
}
Object o = getObject(idx);
return OffsetDateTime.parse(o.toString());
}
Timestamp getTimestamp(int idx) throws SQLException {
if (check_and_null(idx)) {
return null;
}
if (isType(DuckDBColumnType.TIMESTAMP) || isType(DuckDBColumnType.TIMESTAMP_WITH_TIME_ZONE)) {
return DuckDBTimestamp.toSqlTimestamp(getbuf(idx, 8).getLong());
}
if (isType(DuckDBColumnType.TIMESTAMP_MS)) {
return DuckDBTimestamp.toSqlTimestamp(getbuf(idx, 8).getLong() * 1000);
}
if (isType(DuckDBColumnType.TIMESTAMP_NS)) {
return DuckDBTimestamp.toSqlTimestampNanos(getbuf(idx, 8).getLong());
}
if (isType(DuckDBColumnType.TIMESTAMP_S)) {
return DuckDBTimestamp.toSqlTimestamp(getbuf(idx, 8).getLong() * 1_000_000);
}
Object o = getObject(idx);
return Timestamp.valueOf(o.toString());
}
UUID getUuid(int idx) throws SQLException {
if (check_and_null(idx)) {
return null;
}
if (isType(DuckDBColumnType.UUID)) {
ByteBuffer buffer = getbuf(idx, 16);
long leastSignificantBits = buffer.getLong();
// Account for unsigned
long mostSignificantBits = buffer.getLong() - Long.MAX_VALUE - 1;
return new UUID(mostSignificantBits, leastSignificantBits);
}
Object o = getObject(idx);
return UUID.fromString(o.toString());
}
String getLazyString(int idx) {
if (check_and_null(idx)) {
return null;
}
return varlen_data[idx].toString();
}
Array getArray(int idx) throws SQLException {
if (check_and_null(idx)) {
return null;
}
if (isType(DuckDBColumnType.LIST) || isType(DuckDBColumnType.ARRAY)) {
return (Array) varlen_data[idx];
}
throw new SQLFeatureNotSupportedException("getArray");
}
Map
© 2015 - 2024 Weber Informatics LLC | Privacy Policy