32. Системные пакеты
32.1. RDB$TIME_ZONE_UTIL
Пакет RDB$TIME_ZONE_UTIL содержит процедуру TRANSITIONS и функцию DATABASE_VERSION для работы с часовыми поясами.
Функция DATABASE_VERSION
Функция RDB$TIME_ZONE_UTIL.DATABASE_VERSION возвращает версию базы данных часовых
поясов (из библиотеки icu) типа VARCHAR(10) CHARACTER SET ASCII.
SELECT rdb$time_zone_util.database_version()
FROM rdb$database;
DATABASE_VERSION
================
2024a
Процедура TRANSITIONS
Процедура RDB$TIME_ZONE_UTIL.TRANSITIONS возвращает набор правил для часового пояса
между начальной и конечной временной меткой.
Параметр |
Тип |
Описание |
|---|---|---|
RDB$TIME_ZONE_NAME |
CHAR(63) |
Наименование часового пояса |
RDB$FROM_TIMESTAMP |
TIMESTAMP WITH TIME ZONE |
Начало интервала дат |
RDB$TO_TIMESTAMP |
TIMESTAMP WITH TIME ZONE |
Окончание интервала дат |
Параметр |
Тип |
Описание |
|---|---|---|
RDB$START_TIMESTAMP |
TIMESTAMP WITH TIME ZONE |
Дата начала действия правила |
RDB$END_TIMESTAMP |
TIMESTAMP WITH TIME ZONE |
Дата окончания действия правила |
RDB$ZONE_OFFSET |
SMALLINT |
Смещение времени в минутах для заданного часового пояса |
RDB$DST_OFFSET |
SMALLINT |
Летннее смещение времени в минутах для заданного часового пояса |
RDB$EFFECTIVE_OFFSET |
SMALLINT |
Эффективное смещение, вычисляется как |
SELECT
RDB$START_TIMESTAMP AS START_TIMESTAMP,
RDB$END_TIMESTAMP AS END_TIMESTAMP,
RDB$ZONE_OFFSET AS ZONE_OFF,
RDB$DST_OFFSET AS DST_OFF,
RDB$EFFECTIVE_OFFSET AS OFF
FROM rdb$time_zone_util.transitions('America/Sao_Paulo' ,
timestamp '2017-01-01' ,
timestamp '2019-01-01' );
START_TIMESTAMP END_TIMESTAMP ZONE_OFF DST_OFF OFF
============================ ============================ ======== ======= ====
2016-10-16 03:00:00.0000 GMT 2017-02-19 01:59:59.9999 GMT -180 60 -120
2017-02-19 02:00:00.0000 GMT 2017-10-15 02:59:59.9999 GMT -180 0 -180
2017-10-15 03:00:00.0000 GMT 2018-02-18 01:59:59.9999 GMT -180 60 -120
2018-02-18 02:00:00.0000 GMT 2018-11-04 02:59:59.9999 GMT -180 0 -180
2018-11-04 03:00:00.0000 GMT 2019-02-17 01:59:59.9999 GMT -180 60 -120
32.2. RDB$BLOB_UTIL
Пакет RDB$BLOB_UTIL предназначен для обработки данных BLOB напрямую, чего не могут делать
стандартные функции, такие как BLOB_APPEND и SUBSTRING.
Функция NEW_BLOB
Функция NEW_BLOB используется для создания нового BLOB. Она возвращает BLOB,
предназначенный для добавления данных, как BLOB_APPEND. Преимущество перед BLOB_APPEND
заключается в том, что можно задать опции SEGMENTED и TEMP_STORAGE. BLOB_APPEND всегда
создает BLOB во временном хранилище, что может быть не лучшим подходом, если созданный BLOB
будет храниться в постоянной таблице, поскольку потребуется копирование. BLOB, возвращаемый
функцией NEW_BLOB, даже если TEMP_STORAGE = FALSE, может использоваться с BLOB_APPEND
для добавления данных.
Параметр |
Тип |
Описание |
|---|---|---|
SEGMENTED |
BOOLEAN NOT NULL |
Тип |
TEMP_STORAGE |
BOOLEAN NOT NULL |
Место хранения BLOB: |
Пример создания BLOB во временном пространстве и возвращение его в EXECUTE BLOCK:
execute block returns (b blob)
as
begin
-- Создание дескриптора BLOB во временном пространстве.
b = rdb$blob_util.new_blob(false, true);
-- Добавление фрагментов данных.
b = blob_append(b, '12345');
b = blob_append(b, '67');
suspend;
end!
Функция OPEN_BLOB
Функция OPEN_BLOB используется для открытия существующего BLOB для чтения. Она возвращает
дескриптор (целое число, связанное с транзакцией), подходящий для использования с другими функциями
этого пакета, такими как SEEK, READ_DATA и CLOSE_HANDLE.
Параметр |
Тип |
Описание |
|---|---|---|
BLOB |
BLOB NOT NULL |
Переменная типа BLOB |
Функция IS_WRITABLE
Функция IS_WRITABLE возвращает true, если BLOB подходит для добавления данных без копирования с помощью BLOB_APPEND.
Параметр |
Тип |
Описание |
|---|---|---|
BLOB |
BLOB NOT NULL |
Переменная типа BLOB |
Пример проверки BLOB на доступность для записи:
create table t(b blob);
set term !;
execute block returns (bool boolean)
as
declare b blob;
begin
b = blob_append(null, 'writable');
bool = rdb$blob_util.is_writable(b);
suspend;
insert into t (b) values ('not writable') returning b into b;
bool = rdb$blob_util.is_writable(b);
suspend;
end!
set term ;!
Функция READ_DATA
Функция READ_DATA используется для чтения фрагментов данных по дескриптору BLOB, открытому с
помощью RDB$BLOB_UTIL.OPEN_BLOB. Возвращает NULL, когда BLOB полностью прочитан.
Если LENGTH передается с положительным числом, он возвращает VARBINARY с его максимальной
длиной. Если LENGTH равна NULL, то возвращается только сегмент BLOB с максимальной длиной 32765.
Параметр |
Тип |
Описание |
|---|---|---|
HANDLE |
INTEGER NOT NULL |
Дескриптор |
LENGTH |
INTEGER |
Длина |
Пример открытия BLOB и возвращения его частей с помощью EXECUTE BLOCK:
execute block returns (s varchar(10))
as
declare b blob = '1234567';
declare bhandle integer;
begin
-- Открытие BLOB и получение дескриптора BLOB.
bhandle = rdb$blob_util.open_blob(b);
-- Получение и возвращение фрагментов данных в виде строки.
s = rdb$blob_util.read_data(bhandle, 3);
suspend;
s = rdb$blob_util.read_data(bhandle, 3);
suspend;
s = rdb$blob_util.read_data(bhandle, 3);
suspend;
-- Здесь BLOB полностью прочитан, поэтому возвращается NULL.
s = rdb$blob_util.read_data(bhandle, 3);
suspend;
-- Закрытие дескриптора BLOB.
execute procedure rdb$blob_util.close_handle(bhandle);
end!
Функция SEEK
Функция SEEK возвращает новую позицию для следующего READ_DATA.
MODE может быть 0 (c начала), 1 (c текущей позиции) или 2 (c конца).
Если MODE равен 2, OFFSET должен быть нулевым или отрицательным.
Параметр |
Тип |
Описание |
|---|---|---|
HANDLE |
INTEGER NOT NULL |
Дескриптор |
MODE |
INTEGER NOT NULL |
Режим |
OFFSET |
INTEGER NOT NULL |
Смещение |
Пример работы функции SEEK:
set term !;
execute block returns (s varchar(10))
as
declare b blob;
declare bhandle integer;
begin
-- Создание дескриптора потокового BLOB
b = rdb$blob_util.new_blob(false, true);
-- Добавление данных.;
b = blob_append(b, '0123456789');
-- Открытие BLOB.;
bhandle = rdb$blob_util.open_blob(b);
-- Поиск с начала до 5.;
rdb$blob_util.seek(bhandle, 0, 5);
s = rdb$blob_util.read_data(bhandle, 3);
suspend;
-- Поиск с начала до 2.
rdb$blob_util.seek(bhandle, 0, 2);
s = rdb$blob_util.read_data(bhandle, 3);
suspend;
-- Ещё на 2 вперед.
rdb$blob_util.seek(bhandle, 1, 2);
s = rdb$blob_util.read_data(bhandle, 3);
suspend;
-- Поиск с конца на один элемент назад.
rdb$blob_util.seek(bhandle, 2, -1);
s = rdb$blob_util.read_data(bhandle, 3);
suspend;
end!
set term ;!
Процедура CANCEL_BLOB
Процедура CANCEL_BLOB используется для немедленного освобождения временного BLOB, например,
созданного с помощью BLOB_APPEND.
Предупреждение
Обратите внимание, что если тот же BLOB будет использован после отмены, используя ту же переменную
или другую переменную с той же ссылкой на BLOB id, будет выдана ошибка invalid blob id.
Процедура CLOSE_HANDLE
Процедура CLOSE_HANDLE используется для закрытия дескриптора BLOB, открытого с помощью
OPEN_BLOB. Незакрытые дескрипторы закрываются автоматически только в конце транзакции.
Параметр |
Тип |
Описание |
|---|---|---|
HANDLE |
INTEGER NOT NULL |
Дескриптор |