PL/Container
- Обзор PL/Container
- Предварительные требования
- Настройка Docker
- Установка PL/Container
- Управление Docker-образами PL/Container
- Управление конфигурациями выполнения PL/Container
- Установка расширения PL/Container
- Разработка функций PL/Container
- Просмотр и обновление конфигураций выполнения в SQL
- Управление ресурсами PL/Container
- Логирование PL/Container
- Настройка образа PL/Container
Расширение языка PL/Container в Greengage DB позволяет создавать и запускать пользовательские функции на PL/Python и PL/R внутри Docker-контейнеров. PL/Container снижает риски безопасности, ограничивая доступ к сегмент-хостам Greengage DB. В этой статье описывается, как установить, настроить и использовать PL/Container.
Обзор PL/Container
Расширение языка PL/Container позволяет безопасно создавать и запускать пользовательские функции, написанные на PL/Python или PL/R, внутри Docker-контейнеров. Docker предоставляет механизм упаковки и выполнения приложений в слабо изолированной среде, называемой контейнером. Для получения дополнительной информации о Docker смотрите документацию на https://www.docker.com.
Запуск пользовательских функций внутри Docker-контейнеров обеспечивает следующие преимущества:
-
Выполнение функции происходит в отдельной среде, что отделяет пользовательскую обработку данных от основной обработки запроса. Операторы SQL, такие как
ScanиFilter, выполняются на стороне исполнителя запросов (Query Executor, QE), тогда как сложная обработка данных выполняется внутри контейнера. -
Пользовательский код полностью изолирован от операционной системы и файловой системы хоста, что предотвращает угрозы безопасности.
-
Функции не могут подключаться к СУБД, если контейнер настроен с ограниченным или отсутствующим доступом к сети, что обеспечивает безопасность данных.
Последовательность выполнения функции PL/Container
Рассмотрим запрос, который выбирает данные из таблиц на всех сегментах Greengage DB и обрабатывает их с помощью функции PL/Container:
-
При первом вызове функции на сегменте исполнитель запроса на мастер-хосте запускает контейнер на этом сегмент-хосте.
-
Затем исполнитель запросов взаимодействует с запущенным контейнером, чтобы выполнить функцию и получить результаты.
-
(Опционально) Контейнер может выполнить вызов SPI (Server Programming Interface) — внутренний SQL-запрос, выполняемый контейнером для получения дополнительных данных из БД — и вернуть полученные данные исполнителю запросов.
-
Контейнер остается в состоянии ожидания, прослушивает сокет и не потребляет ресурсы CPU. Память, потребляемая PL/Container, в основном определяется объемом данных, кешированных в глобальных словарях.
-
Когда сессия Greengage DB, запустившая контейнер, завершается, соединение с контейнером закрывается, и контейнер автоматически останавливается.
Предварительные требования
Для демонстрации настройки и использования PL/Container используется инициализированный и запущенный кластер с четырьмя хостами:
-
mdw— мастер-хост. -
smdw— резервный мастер-хост. -
sdw1иsdw2— сегмент-хосты.
В данном демонстрационном окружении административный пользователь Greengage DB (gpadmin) имеет привилегии sudo, хотя они не требуются для корректной работы СУБД.
Информацию об инициализации СУБД смотрите в статье Инициализация СУБД.
Настройка Docker
Для работы PL/Container требуется установка Docker на всех хостах кластера Greengage DB. Ниже приведены инструкции по установке и настройке Docker на Ubuntu 22.04.
Установка и запуск Docker
Выполните следующие шаги на каждом хосте Greengage DB:
-
Войдите под пользователем
gpadmin.$ sudo su - gpadmin -
Обновите все программные пакеты, установленные в системе:
$ sudo apt-get update -
Установите пакеты, необходимые для Docker:
$ sudo apt-get install ca-certificates curl -
Добавьте GPG-ключ для Docker-репозитория:
$ sudo install -m 0755 -d /etc/apt/keyrings $ sudo curl -fsSL https://download.docker.com/linux/ubuntu/gpg -o /etc/apt/keyrings/docker.asc $ sudo chmod a+r /etc/apt/keyrings/docker.asc -
Добавьте Docker-репозиторий:
$ echo \ "deb [arch=$(dpkg --print-architecture) signed-by=/etc/apt/keyrings/docker.asc] https://download.docker.com/linux/ubuntu \ $(. /etc/os-release && echo "jammy") stable" | \ sudo tee /etc/apt/sources.list.d/docker.list > /dev/null -
Обновите индекс пакетов, чтобы включить репозиторий Docker:
$ sudo apt-get update -
Установите Docker Engine и связанные компоненты:
$ sudo apt-get install docker-ce docker-ce-cli containerd.io docker-buildx-plugin docker-compose-plugin -
Запустите сервис Docker:
$ sudo systemctl start docker -
Включите автозапуск Docker при загрузке системы:
$ sudo systemctl enable docker
Предоставление gpadmin доступа к Docker
После установки Docker необходимо настроить права доступа, чтобы пользователь gpadmin мог управлять Docker-образами и контейнерами:
-
Добавьте пользователя
gpadminв группуdocker:$ sudo usermod -aG docker gpadmin -
Выйдите из текущей сессии и войдите снова под пользователем
gpadmin, чтобы изменения в группах вступили в силу. -
Проверьте доступность Docker, выполнив команду:
$ docker psЕсли Docker настроен корректно, команда отобразит пустой список запущенных контейнеров.
Перезапуск кластера
После настройки Docker перезапустите СУБД Greengage, чтобы применить изменения и обеспечить доступ к Docker:
$ gpstop -r
Установка PL/Container
PL/Container должен быть установлен на всех хостах кластера Greengage DB.
Сборка PL/Container из исходного кода
Выполните следующие действия на каждом хосте кластера Greengage DB, войдя в систему под пользователем gpadmin:
-
Клонируйте репозиторий plcontainer:
$ git clone https://github.com/arenadata/plcontainer.git -
Перейдите в каталог plcontainer:
$ cd plcontainer -
Переключитесь на необходимый тег релиза, чтобы собрать указанную версию, например:
$ git checkout 2.4.0 -
Создайте каталог build и перейдите в него:
$ mkdir build && cd build -
Настройте сборку с помощью
cmake, указав путь к исполняемому файлу pg_config:$ cmake .. -DPG_CONFIG=/usr/local/gpdb/bin/pg_config -
Скомпилируйте PL/Container с помощью
make:$ make -j$(nproc) -
Выполните
make install, чтобы установить PL/Container в каталоги Greengage DB:$ make -j$(nproc) installПример вывода после установки:
-- Installing: /usr/local/gpdb/lib/postgresql/plcontainer.so -- Installing: /usr/local/gpdb/share/postgresql/extension/plcontainer--1.0.0.sql -- Installing: /usr/local/gpdb/share/postgresql/extension/plcontainer.control -- Installing: /usr/local/gpdb/share/postgresql/plcontainer/plcontainer_configuration.xml -- Installing: /usr/local/gpdb/bin/plcontainer -- Installing: /usr/local/gpdb/bin/plcontainer_clients/py3client.sh -- Installing: /usr/local/gpdb/bin/plcontainer_clients/pyclient.sh -- Installing: /usr/local/gpdb/bin/plcontainer_clients/rclient.sh
Управление Docker-образами PL/Container
Подготовка Docker-образов по умолчанию
Выполните следующие действия на мастер-хосте, чтобы собрать Docker-образы PL/Container по умолчанию:
-
Перейдите в каталог plcontainer/build:
$ cd ~/plcontainer/build/ -
Соберите Docker-образы по умолчанию:
$ make images_artifactЭтот шаг генерирует Docker-образы, необходимые для окружений PL/Python и PL/R.
-
Выведите список Docker-образов, чтобы проверить их создание:
$ docker image lsРезультат должен выглядеть так:
IMAGE ID DISK USAGE CONTENT SIZE EXTRA python27.ubuntu:latest 0112f2a648c0 982MB 291MB python39.alpine:latest 5fc35ccbcd5f 397MB 100MB r.alpine:latest 2dceb4e0251b 753MB 203MB
-
Проверьте созданные файлы Docker-образов:
$ ls -1 plcontainer-*.tar.gzВывод должен содержать следующие файлы:
plcontainer-python2-image-2.4.0-gp6.tar.gz plcontainer-python3-image-2.4.0-gp6.tar.gz plcontainer-r-image-2.4.0-gp6.tar.gz
Установка образов на хосты кластера
После сборки Docker-образов используйте утилиту plcontainer для их установки на все хосты кластера Greengage DB, чтобы PL/Container мог использовать эти образы для выполнения функций:
-
Установите образ Python 3 на все хосты кластера с помощью
plcontainer image-add:$ plcontainer image-add -f plcontainer-python3-image-2.4.0-gp6.tar.gzЭта команда копирует файл образа на все хосты и загружает его в Docker. Вывод команды должен выглядеть следующим образом:
20251112:13:37:10:047201 plcontainer:mdw:gpadmin-[INFO]:-Checking whether docker is installed on all hosts... 20251112:13:37:11:047201 plcontainer:mdw:gpadmin-[INFO]:-Distributing image file plcontainer-python3-image-2.4.0-gp6.tar.gz to all hosts... 20251112:13:37:12:047201 plcontainer:mdw:gpadmin-[INFO]:-Loading image on all hosts... 20251112:13:37:17:047201 plcontainer:mdw:gpadmin-[INFO]:-Removing temporary image files on all hosts...
-
Аналогично установите образ R:
$ plcontainer image-add -f plcontainer-r-image-2.4.0-gp6.tar.gzЭта команда устанавливает образ окружения R на все хосты кластера.
-
(Опционально) Чтобы удалить ненужный образ, используйте
plcontainer image-delete:$ plcontainer image-delete -i python27.ubuntu:latest -
Выведите список всех установленных образов для проверки:
$ plcontainer image-listРезультат может выглядеть следующим образом:
IMAGE ID DISK USAGE CONTENT SIZE EXTRA python39.alpine:latest 5fc35ccbcd5f 397MB 100MB r.alpine:latest 2dceb4e0251b 753MB 203MB
Управление конфигурациями выполнения PL/Container
PL/Container использует конфигурации выполнения для сопоставления Docker-образов с языковыми средами:
-
Проверьте существующие конфигурации выполнения:
$ plcontainer runtime-showОжидаемый результат:
PL/Container Runtime Configuration: No runtime or no specified runtime was found.
-
Добавьте конфигурацию для Python 3:
$ plcontainer runtime-add -r plc_python_shared -i python39.alpine:latest -l python3Эта команда добавляет новую конфигурацию выполнения и копирует обновленный файл конфигурации на все хосты кластера. Ожидаемый результат:
20251112:13:49:29:050540 plcontainer:mdw:gpadmin-[INFO]:-Distributing file plcontainer_configuration.xml to all locations... 20251112:13:49:30:050540 plcontainer:mdw:gpadmin-[INFO]:-Configuration has changed. Run "select * from plcontainer_refresh_config" in open sessions. New sessions will get new configuration automatically.
-
Добавьте конфигурацию выполнения для R:
$ plcontainer runtime-add -r plc_r_shared -i r.alpine:latest -l r -
Проверьте конфигурации выполнения снова:
$ plcontainer runtime-showРезультат должен выглядеть следующим образом:
PL/Container Runtime Configuration: --------------------------------------------------------- Runtime ID: plc_python_shared Linked Docker Image: python39.alpine:latest Runtime Setting(s): Shared Directory: ---- Shared Directory From HOST '/usr/local/gpdb/bin/plcontainer_clients' to Container '/clientdir', access mode is 'ro' --------------------------------------------------------- --------------------------------------------------------- Runtime ID: plc_r_shared Linked Docker Image: r.alpine:latest Runtime Setting(s): Shared Directory: ---- Shared Directory From HOST '/usr/local/gpdb/bin/plcontainer_clients' to Container '/clientdir', access mode is 'ro' ---------------------------------------------------------
Команды runtime-* утилиты plcontainer также позволяют заменять конфигурации выполнения, редактировать файл plcontainer_configuration.xml с помощью указанного редактора, проверять соответствие конфигурации выполнения на сегментах с мастер-хостом и выполнять другие сопутствующие задачи.
Установка расширения PL/Container
Перед использованием пользовательских функций PL/Container необходимо установить расширение plcontainer в каждой базе данных, которая будет его использовать:
-
Создайте новую базу данных:
$ createdb marketplace -
Подключитесь к базе данных:
$ psql marketplace -
Установите расширение PL/Container:
CREATE EXTENSION plcontainer;Ожидаемый вывод:
CREATE EXTENSION
Если использование PL/Container в базе данных больше не требуется, вы можете удалить расширение с помощью команды DROP EXTENSION.
Укажите опцию CASCADE, чтобы автоматически удалить все зависимые объекты, включая функции, созданные с использованием PL/Container.
Разработка функций PL/Container
Когда расширение PL/Container установлено, язык plcontainer можно использовать в определениях функций.
Пользовательская функция PL/Container должна содержать:
-
Первая строка:
# container: <ID>— указывает конфигурацию выполнения, которая будет использоваться.<ID>соответствует записиRuntime IDв конфигурации выполнения и определяет фактический язык программирования (Python или R), используемый функцией. -
Атрибут
LANGUAGE plcontainer— указывает, что это функция PL/Container.
Создание Python-функции
Создайте функцию на Python с использованием PL/Container:
CREATE FUNCTION greet_from_python()
RETURNS TEXT
AS
$$
# container: plc_python_shared
return 'Hello from Python!'
$$ LANGUAGE plcontainer;
Выполните созданную функцию:
SELECT greet_from_python();
Результат должен выглядеть так:
greet_from_python -------------------- Hello from Python! (1 row)
Создание R-функции
Вы также можете создать функцию на R с использованием PL/Container:
CREATE FUNCTION greet_from_r()
RETURNS TEXT
AS
$$
# container: plc_r_shared
return("Hi from R!")
$$ LANGUAGE plcontainer;
Выполните функцию:
SELECT greet_from_r();
Результат должен выглядеть следующим образом:
greet_from_r -------------- Hi from R! (1 row)
Создание функции с SPI (plpy)
CREATE TABLE customers
(
customer_id SERIAL PRIMARY KEY,
first_name VARCHAR(25),
last_name VARCHAR(25),
email VARCHAR(25)
)
DISTRIBUTED REPLICATED;
INSERT INTO customers (first_name, last_name, email)
VALUES ('Andrew', 'Fuller', 'andrew@example.com'),
('Michael', 'Suyama', 'michael@testmail.com'),
('Robert', 'King', 'robert@demo.org');
Создайте функцию PL/Container, которая выполняет SPI-запрос из контейнера с помощью plpy.execute().
Функция получает запись о клиенте по идентификатору и возвращает ее в текстовом формате.
Сначала запрос подготавливается через plpy.prepare(), а затем выполняется с использованием списка параметров:
CREATE FUNCTION get_customer_by_id(p_id INT)
RETURNS TEXT
AS
$$
# container: plc_python_shared
plan = plpy.prepare(
"""
SELECT customer_id, first_name, last_name, email
FROM customers
WHERE customer_id = $1
""",
["int"]
)
rows = plpy.execute(plan, [p_id])
if not rows:
return f"No customer with id={p_id}"
r = rows[0]
return f"{r['customer_id']}: {r['first_name']} {r['last_name']} <{r['email']}>"
$$ LANGUAGE plcontainer;
Выполните функцию:
SELECT get_customer_by_id(2);
Результат должен выглядеть следующим образом:
get_customer_by_id ------------------------------------------ 2: Michael Suyama <michael@testmail.com> (1 row)
Для получения информации о методах plpy смотрите соответствующий раздел в документации PostgreSQL: Database Access.
Ограничения функций PL/Container
Учитывайте следующие ограничения при создании и использовании функций PL/Container:
-
Домены Greengage DB не поддерживаются.
-
Многомерные массивы не поддерживаются.
-
При отладке пользовательских функций не отображается стек вызовов Python и R.
-
Методы
nrows()иstatus()уplpy.execute()не поддерживаются. -
Функция PL/Python
plpy.SPIError()не поддерживается. -
Выполнение команды
SAVEPOINTчерезplpy.execute()не поддерживается. -
Триггеры не поддерживаются.
-
Параметры
OUTне поддерживаются. -
Тип
dictв Python не может быть возвращен из пользовательской функции PL/Python. Чтобы вернуть данные, представленные вdict, преобразуйте их в пользовательский тип данных Greengage DB.
Модуль Python предоставляет глобальные словари GD и SD, которые сохраняют данные между вызовами функций.
GD используется для обмена данными между всеми функциями, выполняющимися в одном контейнере, а SD хранит данные между повторными вызовами одной и той же функции.
Доступ к данным возможен только в рамках одной сессии, пока контейнер работает на сегменте или мастере.
При отсутствии активности в сессии Greengage DB может завершить процессы сегментов, что приводит к остановке контейнеров и очистке данных, сохраненных в GD и SD.
Просмотр и обновление конфигураций выполнения в SQL
Файл конфигурации PL/Container загружается один раз — при первом вызове функции PL/Container в рамках сессии Greengage DB.
Вы можете принудительно перечитать файл конфигурации, выполнив команду SELECT для представления plcontainer_refresh_config в рамках текущей сессии.
Например, следующая команда инициирует повторное чтение файла конфигурации:
SELECT * FROM plcontainer_refresh_config;
Команда запускает функцию PL/Container, которая обновляет конфигурацию на мастере и сегментах и возвращает статус обновления:
gp_segment_id | plcontainer_refresh_local_config
---------------+----------------------------------
2 | ok
3 | ok
1 | ok
0 | ok
-1 | ok
(5 rows)
Вы также можете вывести все конфигурации в текущей сессии, выполнив команду SELECT для представления plcontainer_show_config:
SELECT * FROM plcontainer_show_config;
Функция plcontainer_containers_summary() отображает информацию о запущенных в данный момент Docker-контейнерах:
SELECT * FROM plcontainer_containers_summary();
Результат может выглядеть так:
SEGMENT_ID | CONTAINER_ID | UP_TIME | OWNER | MEMORY_USAGE(KB) ------------+------------------------------------------------------------------+---------------+---------+------------------ -1 | ab12497d6f0be12e4c93744b0981a812f89574f9add80fc80783e450b729bb68 | Up 19 seconds | gpadmin | 96596 -1 | 92a15903672ae38d41e407e2cca96dc094c217b6c0776562b341b33429b97af8 | Up 29 seconds | gpadmin | 9608 (2 rows)
Если функцию plcontainer_containers_summary() выполняет пользователь без прав суперпользователя, отображается информация только о контейнерах, созданных этим пользователем.
Если функцию выполняет суперпользователь, выводится информация обо всех контейнерах, созданных пользователями СУБД.
Greengage DB запускает Docker-контейнеры для выполнения функций PL/Container и повторно использует их при последующих вызовах.
Когда исполнитель запросов неактивен определенное время, он завершает работу, а его контейнеры автоматически удаляются.
Время простоя контролируется параметром gp_vmem_idle_resource_timeout, который можно настроить для улучшения повторного использования контейнеров и снижения накладных расходов на их запуск.
Изменение значения параметра gp_vmem_idle_resource_timeout может повлиять на общую производительность кластера из-за особенностей управления ресурсами.
Помимо Docker-контейнеров, этот параметр также управляет освобождением других ресурсов СУБД.
Управление ресурсами PL/Container
Docker-контейнеры PL/Container используют CPU и память совместно с процессами СУБД на тех же хостах. По умолчанию Greengage DB не отслеживает ресурсы, потребляемые запущенными экземплярами PL/Container. Чтобы нагрузка контейнеров не сказывалась на производительности кластера, вы можете управлять ресурсами PL/Container на двух уровнях:
-
На уровне контейнера — установите лимиты CPU и памяти для каждого контейнера с помощью параметров
memory_mbиcpu_shareв конфигурации выполнения PL/Container. Эти ограничения применяются к каждому экземпляру контейнера для данной конфигурации выполнения. -
На уровне среды выполнения — установите общий объем CPU и памяти, используемый всеми контейнерами данной среды, с помощью ресурсных групп. Назначение ресурсной группы накладывает ее ограничения на все контейнеры указанной среды. Если ресурсная группа не настроена, контейнеры ограничиваются только системными ресурсами и могут конкурировать с процессами Greengage DB за CPU и память.
Управление ресурсами PL/Container с помощью ресурсных групп
Вы можете использовать ресурсные группы для контроля общего потребления CPU и памяти средами выполнения PL/Container. Для внешних компонентов, таких как PL/Container, ресурсные группы используют контрольные группы Linux (cgroups) для применения этих ограничений. Ресурсная группа, назначенная конкретной среде выполнения PL/Container, распространяет свои лимиты CPU и памяти на все контейнеры, создаваемые этой средой.
При создании ресурсной группы для PL/Container необходимо задать MEMORY_AUDITOR=cgroup и CONCURRENCY=0, а также указать требуемые лимиты CPU и памяти.
Например, следующая команда создает ресурсную группу с именем rg_plcontainer:
CREATE RESOURCE GROUP rg_plcontainer WITH (
CPUSET = '1;1',
MEMORY_LIMIT = 20,
CONCURRENCY = 0,
MEMORY_AUDITOR = cgroup
);
После создания группы выполните запрос к представлению gp_toolkit.gp_resgroup_config, чтобы получить ее идентификатор:
SELECT * FROM gp_toolkit.gp_resgroup_config;
Пример вывода:
groupid | groupname | concurrency | cpu_rate_limit | memory_limit | memory_shared_quota | memory_spill_ratio | memory_auditor | cpuset
---------+----------------+-------------+----------------+--------------+---------------------+--------------------+----------------+--------
6437 | default_group | 20 | 30 | 0 | 80 | 0 | vmtracker | -1
6438 | admin_group | 10 | 10 | 10 | 80 | 0 | vmtracker | -1
24993 | rg_plcontainer | 0 | -1 | 20 | 80 | 0 | cgroup | 1;1
(3 rows)
Используйте значение groupid при назначении ресурсной группы среде выполнения PL/Container.
Его можно указать с помощью параметра -s resource_group_id=<rg_groupid> в командах plcontainer runtime-add (новая среда выполнения) или plcontainer runtime-replace (существующая среда выполнения), например:
$ plcontainer runtime-add -r plc_python_shared -i python39.alpine:latest -l python3 -s resource_group_id=24993
Логирование PL/Container
Чтобы включить логирование PL/Container для конкретной среды выполнения, установите атрибут use_container_logging в конфигурации данной среды.
По умолчанию логирование отключено.
Когда логирование контейнеров включено, уровень логов регулируется параметром log_min_messages.
Этот параметр влияет как на вывод логов PL/Container, так и на общие системные логи СУБД.
Обратите внимание на следующие моменты:
-
Логи PL/Container содержат сообщения, создаваемые функциями, выполняющимися внутри Docker-контейнера. По умолчанию эти логи перенаправляются в системную службу журналирования. В системах Red Hat или CentOS логи отправляются в службу
journald. -
Для тестирования или отладки функций PL/Container вы можете временно изменить уровень детализации логов в текущей сессии с помощью команды
SET. В этом примере используется уровень логированияdebug1:SET log_min_messages = 'debug1';
Параметр log_min_messages управляет логированием как сервера Greengage DB, так и PL/Container.
Повышение уровня логирования может повлиять на общую производительность кластера, даже если функции PL/Container не выполняются.
Настройка образа PL/Container
В этом разделе описывается, как создать, проверить и развернуть пользовательский образ Docker для PL/Container.
Загрузка базового образа
Перед созданием пользовательского образа загрузите базовые образы по умолчанию, как описано в разделе Подготовка Docker-образов по умолчанию.
Создание нового образа
Создайте Dockerfile для вашего пользовательского образа:
$ vi Dockerfile
Пример Dockerfile, который добавляет NumPy:
FROM python39.alpine
RUN pip install numpy==2.0.2
Сохраните файл и запустите сборку образа:
$ docker build -t python39_with_numpy.alpine:latest .
Проверка совместимости PL/Container с новым образом
Запустите клиент PL/Container для Python внутри нового образа, чтобы проверить совместимость:
$ docker run -it --rm \
-v $(readlink -f /usr/local/gpdb/bin/plcontainer_clients):/clientdir \
python39_with_numpy.alpine:latest \
/clientdir/py3client.sh
Пример вывода:
plcontainer log: pythonclient, unknown, unknown, -1, WARNING: USE_CONTAINER_NETWORK is not set, use default value "no". plcontainer log: pythonclient, unknown, unknown, -1, ERROR: Cannot bind the addr: No such file or directory
Если вы видите ошибки, начинающиеся с plcontainer log, это означает, что образ совместим с клиентом PL/Container.
Эти ошибки ожидаемы при запуске клиента вне базы данных и подтверждают, что контейнер успешно запускает клиентское окружение.
Сохранение образа в архив
Экспортируйте образ в tar-файл для установки на всех хостах кластера:
$ docker save python39_with_numpy.alpine:latest | gzip > python39_with_numpy.alpine.tar.gz
Итоговый файл — python39_with_numpy.alpine.tar.gz.
Установка образа на хосты кластера
Используйте plcontainer image-add, чтобы развернуть образ на всех хостах кластера:
$ plcontainer image-add -f python39_with_numpy.alpine.tar.gz
Пример вывода:
20251113:06:59:51:061170 plcontainer:mdw:gpadmin-[INFO]:-Checking whether docker is installed on all hosts... 20251113:06:59:51:061170 plcontainer:mdw:gpadmin-[INFO]:-Distributing image file python39_with_numpy.alpine.tar.gz to all hosts... 20251113:06:59:52:061170 plcontainer:mdw:gpadmin-[INFO]:-Loading image on all hosts... 20251113:06:59:59:061170 plcontainer:mdw:gpadmin-[INFO]:-Removing temporary image files on all hosts...
Создание конфигурации выполнения
Создайте конфигурацию выполнения PL/Container, которая использует созданный образ:
$ plcontainer runtime-add -r plc_python_numpy -i python39_with_numpy.alpine:latest -l python3
Пример вывода:
20251113:07:00:47:061541 plcontainer:mdw:gpadmin-[INFO]:-Distributing file plcontainer_configuration.xml to all locations... 20251113:07:00:47:061541 plcontainer:mdw:gpadmin-[INFO]:-Configuration has changed. Run "select * from plcontainer_refresh_config" in open sessions. New sessions will get new configuration automatically.
Проверьте конфигурацию выполнения:
$ plcontainer runtime-show -r plc_python_numpy
Результат должен выглядеть так:
PL/Container Runtime Configuration: --------------------------------------------------------- Runtime ID: plc_python_numpy Linked Docker Image: python39_with_numpy.alpine:latest Runtime Setting(s): Shared Directory: ---- Shared Directory From HOST '/usr/local/gpdb/bin/plcontainer_clients' to Container '/clientdir', access mode is 'ro' ---------------------------------------------------------
Создание функции
Подключитесь к базе данных:
$ psql marketplace
Создайте функцию PL/Container, которая использует NumPy:
CREATE OR REPLACE FUNCTION get_array_shape(arr TEXT)
RETURNS TEXT
AS
$$
# container: plc_python_numpy
import numpy as np
import ast
input_array = np.array(ast.literal_eval(arr))
return f"Array shape: {input_array.shape}"
$$ LANGUAGE plcontainer;
Запустите функцию:
SELECT get_array_shape('[[1,2,3],[4,5,6]]');
Результат должен выглядеть следующим образом:
get_array_shape --------------------- Array shape: (2, 3) (1 row)