vacuumlo. Утилита для удаления потерянных больших объектов#
В исходном дистрибутиве установлено по умолчанию: да.
Связанные компоненты: отсутствуют.
Схема размещения: не используется.
Программа vacuumlo представляет собой утилиту, которая удаляет все «потерянные» большие объекты (LO, Large Objects) из базы данных PostgreSQL. Потерянным считается такой объект, OID которого не фигурирует ни в одном из столбцов oid или lo.
Если в работе появляется необходимость применения утилиты vacuumlo, следует обратить внимание на триггер lo_manage в модуле lo. Триггер lo_manage полезен возможностью предотвратить потерю больших объектов.
Параметры
Обработке подвергаются все базы данных, перечисленные в командной строке при запуске утилиты.
Программа vacuumlo принимает следующие аргументы командной строки:
Аргумент |
Описание |
|---|---|
|
Максимальное количество больших объектов, которые следует удалять в пределах одной транзакции. |
|
Пробный (тестовый) прогон; программа не будет ничего удалять, а только покажет, какие операции должны будут выполняться |
|
Вывод подробного сообщения о прогрессе |
|
Вывод версии утилиты |
|
Вывод справки об аргументах командной строки утилиты |
|
Параметр подключения: адрес сервера баз данных |
|
Параметр подключения: порт сервера баз данных |
|
Параметр подключения: имя пользователя, под которым производится подключение |
|
Параметр подключения: Не выдавать запрос на ввод пароля. Если сервер требует аутентификацию по паролю, который недоступен с помощью специальных средств (утилита |
|
Параметр подключения: Принудительно запрашивать пароль перед подключением к базе данных. Несущественный параметр, так как |
Переменные окружения
Параметры подключения по умолчанию:
PGHOST;PGPORT;PGUSER.
Утилита vacuumlo использует переменные среды, поддерживаемые libpq.
Алгоритм работы
Программа vacuumlo работает следующим образом:
строит временную таблицу, содержащую все OID больших объектов в выбранной базе данных;
сканирует все столбцы в базе данных, имеющие тип
oidилиlo;удаляет соответствующие записи из временной таблицы, при этом рассматриваются только типы именно с такими именами, оставшиеся записи во временной таблице указывают на потерянные БО, которые затем и удаляются.
Доработка#
Доработка не проводилась.
Ограничения#
Ограничения отсутствуют.
Установка#
Установка не требуется.
Исполняемый файл vacuumlo по умолчанию расположен в каталоге $PGHOME/bin.
Настройка#
Настройка не требуется.
Использование модуля#
Создайте простой файл
lo_file.txtдля импорта в базу данных:echo abcdefghqwerty > /tmp/lo_file.txtВызовите функцию
lo_importи передайте имя файла, который требуется загрузить:SELECT lo_import('/tmp/lo_file.txt');Пример вывода результата выполнения запроса:
lo_import ----------- 19014 (1 row)В ответ СУБД выдает число – это идентификатор объекта.
Создайте таблицу и сохраните в ней полученный идентификатор, используйте тип данных
OIDдля хранения идентификаторов объектов:CREATE TABLE lo_file (name text, oid_number oid);INSERT INTO lo_file VALUES ('/tmp/lo_file.txt', lo_import('/tmp/lo_file.txt')) RETURNING *;Пример вывода результата выполнения запроса:
name | oid_number ------------------+------------ /tmp/lo_file.txt | 19021 (1 row) INSERT 0 1Большой объект полностью независим от файла в файловой системе.
Для проверки работы программы импортируйте указанный файл большое количество раз, в данном примере - 100 тысяч раз:
INSERT INTO lo_file SELECT '/tmp/lo_file.txt', lo_import('/tmp/lo_file.txt') FROM generate_series(1, 100000);Проверка результата выполнения запроса:
lo_tst=# SELECT * FROM lo_file LIMIT 10; name | oid_number -----------------+------------ /tmp/lo_file.txt | 19021 /tmp/lo_file.txt | 19022 /tmp/lo_file.txt | 19023 /tmp/lo_file.txt | 19024 /tmp/lo_file.txt | 19025 /tmp/lo_file.txt | 19026 /tmp/lo_file.txt | 19027 /tmp/lo_file.txt | 19028 /tmp/lo_file.txt | 19029 /tmp/lo_file.txt | 19030 (10 rows)Файл был импортирован. Каждый файл имеет новый идентификатор объекта, как показано в списке.
Просмотрите внутренние компоненты при помощи системного каталога
pg_largeobject, чтобы понимать, как данные хранятся в СУБД:lo_tst=# \d pg_largeobjectВывод результата:
Table "pg_catalog.pg_largeobject" Column | Type | Collation | Nullable | Default -------+---------+-----------+----------+--------- loid | oid | | not null | pageno | integer | | not null | data | bytea | | not null | Indexes: "pg_largeobject_loid_pn_index" UNIQUE, btree (loid, pageno)Подробное описание значений столбцов таблицы
pg_largeobjectв документации: https://www.postgresql.org/docs/15/catalog-pg-largeobject.html.Отобразите массив байтов столбца
dataс типомbytea:SELECT * FROM pg_largeobject WHERE loid = 19029 ORDER BY pageno;Пример вывода результата выполнения запроса:
loid | pageno | data ------+--------+---------------------------------- 19029 | 0 | \x61626364656667687177657274790a (1 row)Для удобства чтения переведите вывод двоичных данных в формат
escape:SET bytea_output TO escape; SELECT * FROM pg_largeobject WHERE loid = 19029 ORDER BY pageno;Пример вывода результата выполнения запроса:
loid | pageno | data ------+--------+-------------------- 19029 | 0 | abcdefghqwerty\012 (1 row)С помощью функции
lo_unlink()удалите большой объект с OID19029:SELECT lo_unlink(19029);Пример вывода результата выполнения запроса:
lo_unlink ----------- 1 (1 row)Подробное описание функции
lo_unlink()в документации https://www.postgresql.org/docs/15/lo-funcs.html.Запустите утилиту с аргументом
--dry-runили-nдля проверки количества больших объектов, подлежащих удалению:vacuumlo --dry-run --verbose lo_tst Connected to database "lo_tst" Test run: no large objects will be removed! Checking oid_number in ext.lo_file Would remove 1 large objects from database "lo_tst".Удалите найденный потерянный большой объект:
vacuumlo --verbose lo_tst Connected to database "lo_tst" Checking oid_number in ext.lo_file Successfully removed 1 large objects from database "lo_tst".Убедитесь, что повторная проверка не находит потерянных больших объектов в выбранной базе данных:
vacuumlo --dry-run --verbose lo_tst Connected to database "lo_tst" Test run: no large objects will be removed! Checking oid_number in ext.lo_file Would remove 0 large objects from database "lo_tst".Проверьте отсутствие объекта с OID
19029, который присутствовал на этапе 6 данного примера:SELECT * FROM pg_largeobject WHERE loid = 19029 ORDER BY pageno; loid | pageno | data -----+--------+------ (0 rows)
Ссылки на документацию разработчика#
Исходная документация PosgreSQL по утилите vacuumlo: https://www.postgresql.org/docs/15/vacuumlo.html.