Перейти к основному содержимому

psql_quotolin. Расширенное квотирование вычислительных ресурсов

Версия: 1.0.

В исходном дистрибутиве установлено по умолчанию: нет

Связанные компоненты: отсутствуют

Схема размещения: ext

Сведения

Функциональность доступна только для редакций Enterprise и Enterprise для ERP-систем.

Расширение psql_quotolin предназначено для продвинутого управления вычислительными ресурсами в СУБД Pangolin. Оно позволяет администраторам:

  • задавать лимиты по CPU, оперативной памяти, памяти подкачки (swap), числу параллельных рабочих процессов;
  • ограничивать скорость чтения/записи на диск (I/O) в разрезе табличных пространств;
  • устанавливать дисковые квоты (soft/hard) для ролей, схем и БД;
  • задавать индивидуальные ограничения для конкретного сеанса по PID;
  • планировать применение лимитов по датам, времени суток и дням недели;
  • наследовать планы ресурсов от родительских ролей.

Ключевой механизм работы psql_quotolinпланы ресурсов, которые назначаются ролям и автоматически применяются фоновым процессом Quotolin Launcher в реальном времени для новых и уже активных сеансов.

Доработка

Доработка не проводилась.

Ограничения

Сведения

Функциональность поддерживается только на операционных системах REDOS 7.3.5, REDOS 8 в связи с использованием библиотекиlibcgroup версии 3.x.x.

Для работы необходима поддержка cgroups v2 и установленный пакет libcgroup (≥ 3.0.0).

ОграничениеОписание
Контроль пула сессийНе входит в состав решения, так как реализован через pg_quota.conf
Область действияОграничения действуют только в той базе данных, где установлено расширение
Первоначальная настройкаТребует участия администратора ОС для включения и настройки cgroups v2
CPUЛимиты применяются только при конкуренции за ресурсы. Процесс с лимитом CPU может удерживать участок памяти, необходимый другому процессу, замедляя его
Dry-runРежим предварительной проверки (dry-run) отсутствует
Ресурсные планыПредопределенных глобальных планов нет. Планы задаются при подключении расширения к каждой БД
Назначение плановПланы ресурсов можно назначать только ролям с атрибутом LOGIN
Часовой поясВсе планы, назначенные одной роли, должны иметь одинаковый timezone
МинимумыВремя активности — 5 мин; память — 100 Мбайт; swap — 10 Мбайт
SwapРекомендуется размер не меньше объема RAM. При превышении лимитов RAM или swap процесс замедляется, но продолжает работу
Применение измененийИзменения ограничений для роли могут задерживаться до значения psql_quotolin.launcher_interval
Дисковые квотыНе применяются к сжатым таблицам
DISKIOЛимиты накладываются на блочное устройство, где находится tablespace. Если на одном устройстве заданы разные лимиты, действует самый строгий
Наследование плановПри наследовании от нескольких ролей применяется план роли с меньшим OID
DockerНе поддерживается
Ручные измененияРучное редактирование /sys/fs/cgroup/postgres приводит к неопределенному поведению

Поведение ограничений ресурсов

Ограничение на процессорное время

Применяется только при возникновении конкуренции за процессорный ресурс. Например, если в системе 8 ядер и только два активных пользователя, то они, с большой вероятностью, будут выполняться на разных ядрах и не столкнутся с ограничением.

Ограничение на оперативную память

При превышении лимита избыточные страницы отправляются в файл подкачки ОС. Если это невозможно (например, из-за лимита swap), процесс будет искусственно замедлен, и выделение памяти станет происходить с задержкой.

Ограничение на файлы подкачки

Применяется к суммарному размеру файлов подкачки, используемых сеансом. При достижении лимита отправка страниц в swap прекращается.

Ограничение на параллельные рабочие процессы

Проверяется в момент старта запроса. Уже запущенный запрос продолжает работать с ранее определенным количеством параллельных воркеров, даже если план изменился во время выполнения.

Ограничение на чтение/запись диска (DISKIO)

Применяется к операциям чтения и записи. При превышении лимита операции замедляются, предотвращая перегрузку дисковой подсистемы.

Дисковые квоты

Активны всегда. Два типа ограничений:

  • мягкое (soft) — выдается предупреждение при превышении;
  • жесткое (hard) — генерируется ошибка, запрещающая дальнейшую запись.
Важно

В работе расширения используются таблицы сforeign key. При обычном pg_dump возможны ошибки восстановления из-за нарушений ограничений. Рекомендуется использовать pg_dump -Fc и pg_restore, при которых восстановление выполняется корректно.

Параметры конфигурации (GUC)

ПараметрПо умолчаниюДиапазон/значенияУровеньНазначение
psql_quotolin.max_workers51–128SIGHUPМаксимум воркеров Launcher
psql_quotolin.launcher_interval51–60 секSIGHUPПауза между проходами Launcher
psql_quotolin.activeonon/offSIGHUPГлобальное включение ограничений
psql_quotolin.maintenance_quota_checkonon/offSIGHUPУчет квот при обслуживании БД
psql_quotolin.plan_inhonon/offSIGHUPНаследование планов
psql_quotolin.log_violationsoffon/offSIGHUPЛог нарушений лимитов
psql_quotolin.max_cpu_violations51–1000SIGHUPПорог фиксации нарушений CPU
Сведения

Требуетсяshared_preload_libraries = 'psql_quotolin' в конфигурации сервера.

Установка

Сведения

Администратор операционной системы включает и настраиваетcgroups v2.

Администратор базы данных устанавливает расширение, создает/назначает планы, управляет квотами, меняет GUC.

Подготовка операционной системы

  1. Проверьте поддержку cgroups v2:

    mount | grep cgroup

    Должна присутствовать строка:

    cgroup2 on /sys/fs/cgroup type cgroup2
  2. Установите пакеты:

    # для REDOS
    dnf install libcgroup-tools
  3. Создайте cgroup и выдайте права:

    cgcreate -g cpu,memory,io:/postgres
    chown -R postgres /sys/fs/cgroup/postgres
    chown postgres /sys/fs/cgroup/cgroup.procs

Настройка Pangolin

  1. Включите предварительную загрузку расширения в postgresql.conf:

    shared_preload_libraries = 'psql_quotolin'
  2. Перезапустите кластер и в СУБД Pangolin выполните:

    CREATE EXTENSION psql_quotolin;

Привилегии

После установки расширения все права на управление квотами имеют только суперпользователи.

Доступ к просмотру конфигурационных таблиц и функциям мониторинга, кроме суперпользователей, имеет предопределенная расширением роль psql_read_all_quotolin_stats.

Делегирование прав осуществляется через команду GRANT.

Примеры

Делегация прав на изменение GUC:

GRANT EXECUTE ON FUNCTION pg_reload_conf TO new_role;
GRANT ALTER SYSTEM ON PARAMETER psql_quotolin.active TO new_role;

Делегация прав на использование функции:

GRANT USAGE ON SCHEMA quotolin TO new_role;
GRANT EXECUTE ON FUNCTION quotolin.quotolin_current_plan TO new_role;

Делегация доступа к просмотру конфигурационных таблиц и функциям мониторинга:

GRANT psql_read_all_quotolin_stats TO new_role;

Описание объектов БД

Роли

psql_read_all_quotolin_stats — предопределенная роль расширения для агрегирования доступов на просмотр таблиц и функций мониторинга.

Таблицы

quotolin.quotolin_plans — хранит список всех ресурсных планов и их параметры (CPU, память, swap, параллельные воркеры, ограничения на ввод-вывод).

quotolin.quotolin_user_plans — содержит соответствия ролей и назначенных им планов с указанием временных периодов и часов.

quotolin.quotolin_disk_limits — хранит ограничения дисковой квоты (мягкие и жесткие) для ролей, схем и табличных пространств.

quotolin.quotolin_plans_io_limits — хранит лимиты скорости чтения и записи на диск.

Функции

Управление планами ресурсов:

  • quotolin.quotolin_create_plan(plan_name, cpu_limit, memory_limit_mb, swap_limit_mb, parallel_worker_limit) — создает новый план ресурсов;
  • quotolin.quotolin_update_plan(plan_name, cpu_limit, memory_limit_mb, swap_limit_mb, parallel_worker_limit) — изменяет существующий план;
  • quotolin.quotolin_rename_plan(old_plan_name, new_plan_name) — переименовывает план;
  • quotolin.quotolin_delete_plan(plan_name) — удаляет план (если он не назначен ролям).

Ограничения на ввод-вывод (DISKIO):

  • quotolin.quotolin_plan_add_io_limits(plan_name, tbs_name, io_rkbps_limit, io_wkbps_limit) — добавляет ограничения на чтение/запись для табличного пространства;
  • quotolin.quotolin_plan_update_io_limits(plan_name, tbs_name, io_rkbps_limit, io_wkbps_limit) — обновляет параметры I/O;
  • quotolin.quotolin_plan_remove_io_limits(plan_name, tbs_name) — удаляет ограничения I/O.

Назначение и управление планами:

  • quotolin.quotolin_grant_plan(role_name, plan_name, from_date, till_date, start_time, end_time, days_of_week, timezone) — назначает план роли на период;
  • quotolin.quotolin_revoke_plan(role_name, plan_name) — отзывает план у роли;
  • quotolin.quotolin_current_plan(role_name) — возвращает текущий активный план роли;
  • quotolin.quotolin_update_timeframe(role_name, plan_name, from_date, till_date, start_time, end_time, days_of_week, timezone) — изменяет временной интервал действия плана.

Сессионные ограничения:

  • quotolin.quotolin_prepare_session_quota(session_pid) — подготавливает сеанс к установке индивидуальных лимитов;
  • quotolin.quotolin_set_session_quota(session_pid, cpu_limit, memory_limit_mb, swap_limit_mb, parallel_worker_limit) — устанавливает лимиты для сессии;
  • quotolin.quotolin_delete_session_quota(session_pid) — удаляет лимиты сессии;
  • quotolin.quotolin_set_session_io_limit(session_pid, tbs_name, io_rkbps_limit, io_wkbps_limit) — назначает I/O-ограничения для сессии;
  • quotolin.quotolin_remove_session_io_limits(session_pid, tbs_name) — удаляет I/O-ограничения сессии.

Дисковые квоты:

  • quotolin.quotolin_plan_add_disk_limits(role_name, schema_name, tablespace_name, soft_limit, hard_limit) — назначает мягкие и жесткие лимиты дисковой квоты (можно задать NULL для схемы или tablespace);
  • quotolin.quotolin_plan_update_disk_limits(role_name, schema_name, tablespace_name, soft_limit, hard_limit) — обновляет квоты;
  • quotolin.quotolin_plan_remove_disk_limits(role_name, schema_name, tablespace_name) — снимает дисковые квоты;
  • quotolin.quotolin_recalculate_disk_quota() — пересчитывает дисковые квоты после изменений или смены владельцев объектов.

Мониторинг:

  • quotolin.quotolin_get_disk_quota_hash() — возвращает доступное дисковое пространство для пользователей;
  • quotolin.quotolin_get_session_limit_hash() — показывает наличие активных сессионных ограничений;
  • quotolin.quotolin_get_user_plan_hash() — выводит текущие планы для пользователей;
  • quotolin.quotolin_get_plan_usage_stats() — статистика использования ресурсов по каждому плану;
  • quotolin.quotolin_get_session_limits_stats() — статистика использования ресурсов по сеансам.

Основные функции API

Управление планами ресурсов (без DISKIO)

  1. Создание нового плана ресурсов

    SELECT quotolin.quotolin_create_plan(
    plan_name TEXT,
    cpu_limit INT, -- NULL - ограничение отсутствует
    memory_limit_mb INT, -- NULL - ограничение отсутствует
    swap_limit_mb INT, -- NULL - ограничение отсутствует
    parallel_worker_limit INT -- NULL - ограничение отсутствует
    ) RETURNS BOOLEAN;
  2. Обновление неназначенного плана ресурсов

    SELECT quotolin.quotolin_update_plan(
    plan_name TEXT,
    cpu_limit INT, -- NULL - ограничение отсутствует
    memory_limit_mb INT, -- NULL - ограничение отсутствует
    swap_limit_mb INT, -- NULL - ограничение отсутствует
    parallel_worker_limit INT -- NULL - ограничение отсутствует
    ) RETURNS BOOLEAN;
  3. Переименование плана ресурсов

    SELECT quotolin.quotolin_rename_plan(
    old_plan_name TEXT,
    new_plan_name TEXT
    ) RETURNS BOOLEAN;
  4. Удаление неназначенного плана ресурсов

    SELECT quotolin.quotolin_delete_plan(
    plan_name TEXT
    ) RETURNS BOOLEAN;

Расширение ресурсных планов ограничениями на скорость чтения/записи диска (DISKIO)

  1. Прикрепление ограничений на скорость чтения/записи диска к ресурсному плану

    SELECT quotolin.quotolin_plan_add_io_limits(
    plan_name TEXT,
    tbs_name TEXT,
    io_rkbps_limit INT, -- NULL - ограничение отсутствует
    io_wkbps_limit INT -- NULL - ограничение отсутствует
    ) RETURNS BOOLEAN;
  2. Изменение ограничений на скорость чтения/записи диска

    SELECT quotolin.quotolin_plan_update_io_limits(
    plan_name TEXT,
    tbs_name TEXT,
    io_rkbps_limit INT, -- NULL - ограничение отсутствует
    io_wkbps_limit INT -- NULL - ограничение отсутствует
    ) RETURNS BOOLEAN;
  3. Удаление ограничений на скорость чтения/записи диска

    SELECT quotolin.quotolin_plan_remove_io_limits(
    plan_name TEXT,
    tbs_name TEXT
    ) RETURNS BOOLEAN;

Управление назначением ресурсных планов и временем их активности

  1. Назначение ресурсного плана роли:

    SELECT quotolin.quotolin_grant_plan(
    role_name TEXT,
    plan_name TEXT,
    from_date TIMESTAMP, -- NULL - текущая дата
    till_date TIMESTAMP, -- NULL - бесконечно
    start_time TIME, -- NULL - активен с начала дня
    end_time TIME, -- NULL - активен до конца дня
    days_of_week TEXT[], -- NULL - активен в любой день недели
    timezone TEXT -- NULL - используется временная зона текущего сеанса
    ) RETURNS BOOLEAN;
  2. Изменение времени активности назначенного ресурсного плана:

    SELECT quotolin.quotolin_update_timeframe(
    role_name TEXT,
    plan_name TEXT,
    from_date TIMESTAMP, -- NULL - текущая дата
    till_date TIMESTAMP, -- NULL - бесконечно
    start_time TIME, -- NULL - активен с начала дня
    end_time TIME, -- NULL - активен до конца дня
    days_of_week TEXT[], -- NULL - активен в любой день недели
    timezone TEXT -- NULL - используется временная зона текущего сеанса
    ) RETURNS BOOLEAN;
  3. Отзыв назначенного ресурсного плана:

    SELECT quotolin.quotolin_revoke_plan(
    role_name TEXT,
    plan_name TEXT
    ) RETURNS BOOLEAN;
  4. Получение активного ресурсного плана для роли:

    SELECT quotolin.quotolin_current_plan(
    role_name TEXT
    ) RETURNS BOOLEAN;

Управление ограничениями для сессии

  1. Подготовка сессии к пользовательским ограничениям:

    SELECT quotolin.quotolin_prepare_session_quota(
    session_pid INT
    ) RETURNS BOOLEAN;
  2. Установка ограничений для сессии (без DISKIO):

    SELECT quotolin.quotolin_set_session_quota(
    session_pid INT,
    cpu_limit INT, -- NULL - ограничение отсутствует
    memory_limit_mb INT, -- NULL - ограничение отсутствует
    swap_limit_mb INT, -- NULL - ограничение отсутствует
    parallel_worker_limit INT -- NULL - ограничение отсутствует
    ) RETURNS BOOLEAN;
  3. Удаление ограничений для сессии (без DISKIO):

    SELECT quotolin.quotolin_delete_session_quota(
    session_pid INT
    ) RETURNS BOOLEAN;
  4. Установка ограничения на скорость чтения/записи диска для сессии (DISKIO):

    SELECT quotolin.quotolin_set_session_io_limit(
    session_pid INT,
    tbs_name TEXT,
    io_rkbps_limit INT, -- NULL - ограничение отсутствует
    io_wkbps_limit INT -- NULL - ограничение отсутствует
    ) RETURNS BOOLEAN;
  5. Удаление ограничения на скорость чтения/записи диска для сессии (DISKIO):

    SELECT quotolin.quotolin_remove_session_io_limits(
    session_pid INT,
    tbs_name TEXT
    ) RETURNS BOOLEAN;

Управление дисковыми квотами

  1. Добавление дисковой квоты:

    SELECT quotolin.quotolin_plan_add_disk_limits(
    role_name TEXT,
    schema_name TEXT, -- NULL - действует для всех схем
    tablespace_name TEXT, -- NULL - действует для всех табличных пространств
    soft_limit BIGINT, -- NULL - ограничение отсутствует
    hard_limit BIGINT -- NULL - ограничение отсутствует
    ) RETURNS BOOLEAN;
  2. Изменение дисковой квоты:

    SELECT quotolin.quotolin_plan_update_disk_limits(
    role_name TEXT,
    schema_name TEXT, -- NULL - действует для всех схем
    tablespace_name TEXT, -- NULL - действует для всех табличных пространств
    soft_limit BIGINT, -- NULL - ограничение отсутствует
    hard_limit BIGINT -- NULL - ограничение отсутствует
    ) RETURNS BOOLEAN;
  3. Удаление дисковой квоты:

    SELECT quotolin.quotolin_plan_remove_disk_limits(
    role_name TEXT,
    schema_name TEXT,
    tablespace_name TEXT
    ) RETURNS BOOLEAN;
  4. Пересчет дисковых квот:

    SELECT quotolin.quotolin_recalculate_disk_quota(
    ) RETURNS BOOLEAN;

Мониторинг

  1. Применение планов ограничений:

    SELECT quotolin.quotolin_get_user_plan_hash()
    RETURNS TABLE(
    db_oid OID,
    role_oid OID,
    plan_id Oid
    );
  2. Статистика использования ресурсов по планам ограничений:

    SELECT quotolin.quotolin_get_plan_usage_stats()
    RETURNS TABLE(
    plan_name TEXT,
    cpu_usage BIGINT,
    memory_usage BIGINT,
    swap_usage BIGINT,
    io_usage TEXT
    );
  3. Применение сессионных ограничений:

    SELECT quotolin.quotolin_get_session_limit_hash()
    RETURNS TABLE(
    pid INT,
    active BOOLEAN,
    cpu_limit BOOLEAN,
    memory_limit BOOLEAN,
    swap_limit BOOLEAN,
    parallel_worker_limit BOOLEAN,
    parallel_workers INT
    );
  4. Статистика использования ресурсов по ограничиваемым сессиям:

    SELECT quotolin.quotolin_get_session_limits_stats()
    RETURNS TABLE(
    pid INT,
    cpu_usage BIGINT,
    memory_usage BIGINT,
    swap_usage BIGINT,
    io_usage TEXT
    );
  5. Количество свободного пространства для дисковых квот:

    SELECT quotolin.quotolin_get_disk_quota_hash()
    RETURNS TABLE(
    role_oid OID,
    schema_oid OID,
    tablespace_oid OID,
    db_oid Oid,
    freeSoft BIGINT,
    freeHard BIGINT
    );

Диагностика

При включенном log_violations в журнал пишутся предупреждения:

WARNING: CPU limit exceeded for PID 12345: usage 85% > limit 50%

Для анализа загрузки:

SELECT * FROM quotolin.quotolin_get_plan_usage_stats();
SELECT * FROM quotolin.quotolin_get_session_limits_stats();

Проверка cgroups:

  • для сессий: /proc/<pid>/cgroup должен указывать на .../session_<pid>;
  • для планов: /proc/<pid>/cgroup → .../plan_<db_oid>_<plan_id>;
  • параметры проверяются в /sys/fs/cgroup/postgres/quota/<cgroup_name>/ (cpu.weight, memory.high, memory.swap.max, io.max).

Резервное копирование/восстановление

Рекомендуемый формат pg_dump -Fc / pg_restore.

Важно

Таблицы расширения содержат foreign key, поэтому для корректного восстановления необходимо использовать именно pg_dump -Fc.