Search in sources :

Example 1 with ValueClob

use of org.h2.value.ValueClob in project h2database by h2database.

the class LobStorageMap method createClob.

@Override
public ValueClob createClob(Reader reader, long maxLength) {
    MVStore.TxCounter txCounter = mvStore.registerVersionUsage();
    try {
        // we multiple by 3 here to get the worst-case size in bytes
        if (maxLength != -1 && maxLength * 3 <= database.getMaxLengthInplaceLob()) {
            char[] small = new char[(int) maxLength];
            int len = IOUtils.readFully(reader, small, (int) maxLength);
            if (len > maxLength) {
                throw new IllegalStateException("len > blobLength, " + len + " > " + maxLength);
            }
            byte[] utf8 = new String(small, 0, len).getBytes(StandardCharsets.UTF_8);
            if (utf8.length > database.getMaxLengthInplaceLob()) {
                throw new IllegalStateException("len > maxinplace, " + utf8.length + " > " + database.getMaxLengthInplaceLob());
            }
            return ValueClob.createSmall(utf8, len);
        }
        if (maxLength < 0) {
            maxLength = Long.MAX_VALUE;
        }
        CountingReaderInputStream in = new CountingReaderInputStream(reader, maxLength);
        ValueBlob blob = createBlob(in);
        LobData lobData = blob.getLobData();
        return new ValueClob(lobData, blob.octetLength(), in.getLength());
    } catch (IllegalStateException e) {
        throw DbException.get(ErrorCode.OBJECT_CLOSED, e);
    } catch (IOException e) {
        throw DbException.convertIOException(e, null);
    } finally {
        mvStore.deregisterVersionUsage(txCounter);
    }
}
Also used : MVStore(org.h2.mvstore.MVStore) LobData(org.h2.value.lob.LobData) CountingReaderInputStream(org.h2.store.CountingReaderInputStream) ValueBlob(org.h2.value.ValueBlob) ValueClob(org.h2.value.ValueClob) IOException(java.io.IOException)

Example 2 with ValueClob

use of org.h2.value.ValueClob in project h2database by h2database.

the class LobStorageMap method copyLob.

@Override
public ValueLob copyLob(ValueLob old, int tableId) {
    MVStore.TxCounter txCounter = mvStore.registerVersionUsage();
    try {
        final LobDataDatabase lobData = (LobDataDatabase) old.getLobData();
        final int type = old.getValueType();
        final long oldLobId = lobData.getLobId();
        long octetLength = old.octetLength();
        // get source lob
        final byte[] streamStoreId;
        if (isTemporaryLob(lobData.getTableId())) {
            streamStoreId = tempLobMap.get(oldLobId);
        } else {
            BlobMeta value = lobMap.get(oldLobId);
            streamStoreId = value.streamStoreId;
        }
        // create destination lob
        final long newLobId = generateLobId();
        if (isTemporaryLob(tableId)) {
            tempLobMap.put(newLobId, streamStoreId);
        } else {
            BlobMeta value = new BlobMeta(streamStoreId, tableId, type == Value.CLOB ? old.charLength() : octetLength, 0);
            lobMap.put(newLobId, value);
        }
        BlobReference refMapKey = new BlobReference(streamStoreId, newLobId);
        refMap.put(refMapKey, ValueNull.INSTANCE);
        LobDataDatabase newLobData = new LobDataDatabase(database, tableId, newLobId);
        ValueLob lob = type == Value.BLOB ? new ValueBlob(newLobData, octetLength) : new ValueClob(newLobData, octetLength, old.charLength());
        if (TRACE) {
            trace("copy " + lobData.getTableId() + "/" + lobData.getLobId() + " > " + tableId + "/" + newLobId);
        }
        return lob;
    } finally {
        mvStore.deregisterVersionUsage(txCounter);
    }
}
Also used : MVStore(org.h2.mvstore.MVStore) LobDataDatabase(org.h2.value.lob.LobDataDatabase) ValueLob(org.h2.value.ValueLob) ValueBlob(org.h2.value.ValueBlob) ValueClob(org.h2.value.ValueClob)

Example 3 with ValueClob

use of org.h2.value.ValueClob in project h2database by h2database.

the class ValueDataType method readValue.

/**
 * Read a value.
 *
 * @param buff the source buffer
 * @param columnType the data type of value, or {@code null}
 * @return the value
 */
Value readValue(ByteBuffer buff, TypeInfo columnType) {
    int type = buff.get() & 255;
    switch(type) {
        case NULL:
            return ValueNull.INSTANCE;
        case BOOLEAN_TRUE:
            return ValueBoolean.TRUE;
        case BOOLEAN_FALSE:
            return ValueBoolean.FALSE;
        case INT_NEG:
            return ValueInteger.get(-readVarInt(buff));
        case INTEGER:
            return ValueInteger.get(readVarInt(buff));
        case BIGINT_NEG:
            return ValueBigint.get(-readVarLong(buff));
        case BIGINT:
            return ValueBigint.get(readVarLong(buff));
        case TINYINT:
            return ValueTinyint.get(buff.get());
        case SMALLINT:
            return ValueSmallint.get(buff.getShort());
        case NUMERIC_0_1:
            return ValueNumeric.ZERO;
        case NUMERIC_0_1 + 1:
            return ValueNumeric.ONE;
        case NUMERIC_SMALL_0:
            return ValueNumeric.get(BigDecimal.valueOf(readVarLong(buff)));
        case NUMERIC_SMALL:
            {
                int scale = readVarInt(buff);
                return ValueNumeric.get(BigDecimal.valueOf(readVarLong(buff), scale));
            }
        case NUMERIC:
            {
                int scale = readVarInt(buff);
                return ValueNumeric.get(new BigDecimal(new BigInteger(readVarBytes(buff)), scale));
            }
        case DECFLOAT:
            {
                int scale = readVarInt(buff), len = readVarInt(buff);
                switch(len) {
                    case -3:
                        return ValueDecfloat.NEGATIVE_INFINITY;
                    case -2:
                        return ValueDecfloat.POSITIVE_INFINITY;
                    case -1:
                        return ValueDecfloat.NAN;
                    default:
                        byte[] b = Utils.newBytes(len);
                        buff.get(b, 0, len);
                        return ValueDecfloat.get(new BigDecimal(new BigInteger(b), scale));
                }
            }
        case DATE:
            return ValueDate.fromDateValue(readVarLong(buff));
        case TIME:
            return ValueTime.fromNanos(readTimestampTime(buff));
        case TIME_TZ:
            return ValueTimeTimeZone.fromNanos(readVarInt(buff) * DateTimeUtils.NANOS_PER_SECOND + readVarInt(buff), readTimeZone(buff));
        case TIMESTAMP:
            return ValueTimestamp.fromDateValueAndNanos(readVarLong(buff), readTimestampTime(buff));
        case TIMESTAMP_TZ_OLD:
            return ValueTimestampTimeZone.fromDateValueAndNanos(readVarLong(buff), readTimestampTime(buff), readVarInt(buff) * 60);
        case TIMESTAMP_TZ:
            return ValueTimestampTimeZone.fromDateValueAndNanos(readVarLong(buff), readTimestampTime(buff), readTimeZone(buff));
        case VARBINARY:
            return ValueVarbinary.getNoCopy(readVarBytes(buff));
        case BINARY:
            return ValueBinary.getNoCopy(readVarBytes(buff));
        case JAVA_OBJECT:
            return ValueJavaObject.getNoCopy(readVarBytes(buff));
        case UUID:
            return ValueUuid.get(buff.getLong(), buff.getLong());
        case VARCHAR:
            return ValueVarchar.get(readString(buff));
        case VARCHAR_IGNORECASE:
            return ValueVarcharIgnoreCase.get(readString(buff));
        case CHAR:
            return ValueChar.get(readString(buff));
        case ENUM:
            {
                int ordinal = readVarInt(buff);
                if (columnType != null) {
                    return ((ExtTypeInfoEnum) columnType.getExtTypeInfo()).getValue(ordinal, provider);
                }
                return ValueInteger.get(ordinal);
            }
        case INTERVAL:
            {
                int ordinal = buff.get();
                boolean negative = ordinal < 0;
                if (negative) {
                    ordinal = ~ordinal;
                }
                return ValueInterval.from(IntervalQualifier.valueOf(ordinal), negative, readVarLong(buff), ordinal < 5 ? 0 : readVarLong(buff));
            }
        case REAL_0_1:
            return ValueReal.ZERO;
        case REAL_0_1 + 1:
            return ValueReal.ONE;
        case DOUBLE_0_1:
            return ValueDouble.ZERO;
        case DOUBLE_0_1 + 1:
            return ValueDouble.ONE;
        case DOUBLE:
            return ValueDouble.get(Double.longBitsToDouble(Long.reverse(readVarLong(buff))));
        case REAL:
            return ValueReal.get(Float.intBitsToFloat(Integer.reverse(readVarInt(buff))));
        case BLOB:
            {
                int smallLen = readVarInt(buff);
                if (smallLen >= 0) {
                    byte[] small = Utils.newBytes(smallLen);
                    buff.get(small, 0, smallLen);
                    return ValueBlob.createSmall(small);
                } else if (smallLen == -3) {
                    return new ValueBlob(readLobDataDatabase(buff), readVarLong(buff));
                } else {
                    throw DbException.get(ErrorCode.FILE_CORRUPTED_1, "lob type: " + smallLen);
                }
            }
        case CLOB:
            {
                int smallLen = readVarInt(buff);
                if (smallLen >= 0) {
                    byte[] small = Utils.newBytes(smallLen);
                    buff.get(small, 0, smallLen);
                    return ValueClob.createSmall(small, readVarLong(buff));
                } else if (smallLen == -3) {
                    return new ValueClob(readLobDataDatabase(buff), readVarLong(buff), readVarLong(buff));
                } else {
                    throw DbException.get(ErrorCode.FILE_CORRUPTED_1, "lob type: " + smallLen);
                }
            }
        case ARRAY:
            {
                if (columnType != null) {
                    TypeInfo elementType = (TypeInfo) columnType.getExtTypeInfo();
                    return ValueArray.get(elementType, readArrayElements(buff, elementType), provider);
                }
                return ValueArray.get(readArrayElements(buff, null), provider);
            }
        case ROW:
            {
                int len = readVarInt(buff);
                Value[] list = new Value[len];
                if (columnType != null) {
                    ExtTypeInfoRow extTypeInfoRow = (ExtTypeInfoRow) columnType.getExtTypeInfo();
                    Iterator<Entry<String, TypeInfo>> fields = extTypeInfoRow.getFields().iterator();
                    for (int i = 0; i < len; i++) {
                        list[i] = readValue(buff, fields.next().getValue());
                    }
                    return ValueRow.get(columnType, list);
                }
                TypeInfo[] columnTypes = rowFactory.getColumnTypes();
                for (int i = 0; i < len; i++) {
                    list[i] = readValue(buff, columnTypes[i]);
                }
                return ValueRow.get(list);
            }
        case GEOMETRY:
            return ValueGeometry.get(readVarBytes(buff));
        case JSON:
            return ValueJson.getInternal(readVarBytes(buff));
        default:
            if (type >= INT_0_15 && type < INT_0_15 + 16) {
                int i = type - INT_0_15;
                if (columnType != null && columnType.getValueType() == Value.ENUM) {
                    return ((ExtTypeInfoEnum) columnType.getExtTypeInfo()).getValue(i, provider);
                }
                return ValueInteger.get(i);
            } else if (type >= BIGINT_0_7 && type < BIGINT_0_7 + 8) {
                return ValueBigint.get(type - BIGINT_0_7);
            } else if (type >= VARBINARY_0_31 && type < VARBINARY_0_31 + 32) {
                int len = type - VARBINARY_0_31;
                byte[] b = Utils.newBytes(len);
                buff.get(b, 0, len);
                return ValueVarbinary.getNoCopy(b);
            } else if (type >= VARCHAR_0_31 && type < VARCHAR_0_31 + 32) {
                return ValueVarchar.get(readString(buff, type - VARCHAR_0_31));
            }
            throw DbException.get(ErrorCode.FILE_CORRUPTED_1, "type: " + type);
    }
}
Also used : ExtTypeInfoEnum(org.h2.value.ExtTypeInfoEnum) ExtTypeInfoRow(org.h2.value.ExtTypeInfoRow) ValueBlob(org.h2.value.ValueBlob) Iterator(java.util.Iterator) BigInteger(java.math.BigInteger) ValueClob(org.h2.value.ValueClob) DataUtils.readString(org.h2.mvstore.DataUtils.readString) TypeInfo(org.h2.value.TypeInfo) ValueBigint(org.h2.value.ValueBigint) ValueTinyint(org.h2.value.ValueTinyint) ValueSmallint(org.h2.value.ValueSmallint) BigDecimal(java.math.BigDecimal)

Example 4 with ValueClob

use of org.h2.value.ValueClob in project h2database by h2database.

the class ValueClob method copy.

@Override
public ValueLob copy(DataHandler database, int tableId) {
    if (lobData instanceof LobDataInMemory) {
        byte[] small = ((LobDataInMemory) lobData).getSmall();
        if (small.length > database.getMaxLengthInplaceLob()) {
            LobStorageInterface s = database.getLobStorage();
            ValueClob v = s.createClob(getReader(), charLength);
            ValueLob v2 = v.copy(database, tableId);
            v.remove();
            return v2;
        }
        return this;
    } else if (lobData instanceof LobDataDatabase) {
        return database.getLobStorage().copyLob(this, tableId);
    } else {
        throw new UnsupportedOperationException();
    }
}
Also used : LobDataInMemory(org.h2.value.lob.LobDataInMemory) LobStorageInterface(org.h2.store.LobStorageInterface) LobDataDatabase(org.h2.value.lob.LobDataDatabase)

Example 5 with ValueClob

use of org.h2.value.ValueClob in project h2database by h2database.

the class ValueClob method createTemporary.

/**
 * Create a CLOB in a temporary file.
 */
private static ValueClob createTemporary(DataHandler handler, Reader in, long remaining) throws IOException {
    String fileName = ValueLob.createTempLobFileName(handler);
    FileStore tempFile = handler.openFile(fileName, "rw", false);
    tempFile.autoDelete();
    long octetLength = 0L, charLength = 0L;
    try (FileStoreOutputStream out = new FileStoreOutputStream(tempFile, null)) {
        char[] buff = new char[Constants.IO_BUFFER_SIZE];
        while (true) {
            int len = ValueLob.getBufferSize(handler, remaining);
            len = IOUtils.readFully(in, buff, len);
            if (len == 0) {
                break;
            }
            // TODO reduce memory allocation
            byte[] data = new String(buff, 0, len).getBytes(StandardCharsets.UTF_8);
            out.write(data);
            octetLength += data.length;
            charLength += len;
        }
    }
    return new ValueClob(new LobDataFile(handler, fileName, tempFile), octetLength, charLength);
}
Also used : FileStore(org.h2.store.FileStore) LobDataFile(org.h2.value.lob.LobDataFile) FileStoreOutputStream(org.h2.store.FileStoreOutputStream)

Aggregations

ValueBlob (org.h2.value.ValueBlob)13 ValueClob (org.h2.value.ValueClob)13 LobDataDatabase (org.h2.value.lob.LobDataDatabase)13 IOException (java.io.IOException)12 LobData (org.h2.value.lob.LobData)10 ValueBigint (org.h2.value.ValueBigint)7 ValueSmallint (org.h2.value.ValueSmallint)7 ValueTinyint (org.h2.value.ValueTinyint)7 BufferedReader (java.io.BufferedReader)6 BigDecimal (java.math.BigDecimal)6 BigInteger (java.math.BigInteger)6 DataUtils.readString (org.h2.mvstore.DataUtils.readString)6 MVStore (org.h2.mvstore.MVStore)6 RangeReader (org.h2.store.RangeReader)6 LobDataInMemory (org.h2.value.lob.LobDataInMemory)6 Reader (java.io.Reader)4 Value (org.h2.value.Value)4 ValueInterval (org.h2.value.ValueInterval)4 ValueTimeTimeZone (org.h2.value.ValueTimeTimeZone)4 ValueTimestamp (org.h2.value.ValueTimestamp)4