Использование коннектора PXF HDFS для чтения и записи данных в формате Parquet между Greengage DB и HDFS
Apache Parquet — это открытый формат данных с колоночным хранением, используемый в экосистеме Apache Hadoop. Файл данных Parquet содержит компактное двоичное представление данных и включает встроенную схему. Схема определяет структуру данных и состоит из примитивных и сложных типов, перечисленных в разделе Сопоставление типов данных.
В этой статье описывается настройка и использование коннектора PXF HDFS для чтения и записи данных Parquet в HDFS с использованием внешних таблиц, а также приводятся практические примеры.
Сопоставление типов данных
Для чтения и записи примитивных типов данных Parquet в Greengage DB необходимо сопоставить значения данных Parquet столбцам Greengage DB того же типа.
Parquet поддерживает небольшой набор примитивных типов данных и использует аннотации метаданных, которые указывают, как интерпретировать примитивный тип и расширить его до логического типа.
Например, типы INTEGER и DATE хранятся в Parquet как примитивный тип INT32, а аннотация идентифицирует исходный тип как DATE.
Сопоставление при чтении
При чтении данных Parquet в PXF используется следующее сопоставление типов данных.
| Физический тип данных Parquet | Логический тип данных Parquet | Тип данных PXF / Greengage DB |
|---|---|---|
boolean |
— |
BOOLEAN |
|
— |
BYTEA |
|
Date |
DATE |
|
Timestamp_millis |
TIMESTAMP |
|
UTF8 |
TEXT |
double |
— |
FLOAT8 |
fixed_len_byte_array |
Decimal |
NUMERIC |
float |
— |
REAL |
int32 |
int_8 |
SMALLINT |
int32 |
Date |
DATE |
int32 |
Decimal |
NUMERIC |
int32 |
— |
INTEGER |
int64 |
Decimal |
NUMERIC |
int64 |
— |
BIGINT |
int96 |
— |
TIMESTAMP |
PXF поддерживает pushdown предикатов для всех вышеперечисленных типов данных, кроме fixed_len_byte_array и int96.
PXF может читать данные Parquet составного типа LIST, если они представляют собой одномерный массив следующих типов данных Parquet.
| Тип данных Parquet | Тип данных PXF / Greengage DB |
|---|---|
Список |
BOOLEAN[] |
Список |
BYTEA[] |
Список |
DATE[] |
Список |
TIMESTAMP[] |
Список |
TEXT[] |
Список |
FLOAT8[] |
Список |
NUMERIC[] |
Список |
REAL[] |
Список |
SMALLINT[] |
Список |
DATE[] |
Список |
NUMERIC[] |
Список |
INTEGER[] |
Список |
NUMERIC[] |
Список |
BIGINT[] |
Список |
TIMESTAMP[] |
Сопоставление при записи
При записи данных Parquet в PXF используется следующее сопоставление типов данных.
| Тип данных PXF / Greengage DB | Физический тип данных Parquet | Логический тип данных Parquet |
|---|---|---|
BIGINT |
int64 |
— |
BOOLEAN |
boolean |
— |
BPCHAR (1) |
|
UTF8 |
BYTEA |
|
— |
DATE |
int32 |
Date |
FLOAT8 |
double |
— |
INTEGER |
int32 |
— |
|
fixed_len_byte_array |
Decimal |
REAL |
float |
— |
SMALLINT |
int32 |
int_8 |
TEXT |
|
UTF8 |
TIMESTAMP (2) |
int96 |
— |
TIMESTAMPTZ (3) |
int96 |
— |
VARCHAR |
|
UTF8 |
Прочие типы данных |
Не поддерживаются |
— |
PXF может записывать данные одномерного массива LIST следующих типов данных Parquet.
| Тип данных PXF / Greengage DB | Тип данных Parquet |
|---|---|
BIGINT[] |
Список |
BOOLEAN[] |
Список |
BPCHAR[] (1) |
Список |
BYTEA[] |
Список |
DATE[] |
Список |
FLOAT8[] |
Список |
INTEGER[] |
Список |
|
Список |
REAL[] |
Список |
SMALLINT[] |
Список |
TEXT[] |
Список |
TIMESTAMP[] (2) |
Список |
TIMESTAMPTZ[] (3) |
Список |
VARCHAR[] |
Список |
Прочие типы данных |
Не поддерживаются |
-
Parquet не сохраняет длину поля, поэтому
BPCHAR, записанный в Parquet, будет текстом неопределенной длины. -
PXF приводит тип
TIMESTAMPк текущему системному часовому поясу, преобразует его во всемирное координированное время (UTC), а затем конвертирует вint96. -
PXF преобразует тип
TIMESTAMPTZв метку времени в формате UTC, а затем конвертирует ее вint96. При этом информация о часовом поясе теряется.
Создание внешней таблицы с использованием протокола PXF
Чтобы создать внешнюю таблицу Greengage DB для чтения и записи данных в формате Parquet в HDFS, используется следующий синтаксис:
CREATE [READABLE | WRITABLE] EXTERNAL TABLE <table_name>
( <column_name> <data_type> [, ...] | LIKE <other_table> )
LOCATION ('pxf://<path_to_data>?PROFILE=hdfs:parquet[&<custom_option>=<value>[...]]')
FORMAT 'CUSTOM' (FORMATTER='pxfwritable_import'|'pxfwritable_export')
[DISTRIBUTED BY (<column_name> [, ... ] ) | DISTRIBUTED RANDOMLY];
| Ключевое слово | Значение |
|---|---|
<table_name> |
Имя создаваемой таблицы |
<column_name> |
Имя создаваемого столбца |
<data_type> |
Тип данных создаваемого столбца |
LIKE <other_table> |
Указывает таблицу, из которой внешняя таблица копирует все имена столбцов, типы данных и политику распределения |
<path_to_data> |
Путь к каталогу или файлу в хранилище HDFS.
Если в конфигурации сервера |
PROFILE |
Для чтения и записи данных в формате Parquet в HDFS используется профиль |
FORMAT 'CUSTOM' |
Для чтения и записи данных в формате Parquet в HDFS используется кастомный формат с использованием встроенных кастомных функций форматирования для операций чтения ( |
DISTRIBUTED BY |
При загрузке данных из таблицы Greengage DB во внешнюю пишущую таблицу рекомендуется указывать ту же политику распределения или имя столбца в обеих таблицах. Это позволит избежать дополнительного перемещения данных между сегментами при выполнении операции загрузки. Более подробную информацию о распределении таблиц можно получить в статье Распределение данных |
<custom_option> |
Одна из опций, описанных ниже, указываемая в строке |
SERVER=<server_name> |
Имя конфигурации сервера, который используется для доступа к данным. Если значение не указано, используется сервер PXF по умолчанию |
IGNORE_MISSING_PATH |
Действие, которое необходимо выполнить, если |
COMPRESSION_CODEC |
Кодек сжатия, используемый при записи данных: Если сжатия данных не требуется, следует явно указать значение |
ROWGROUP_SIZE |
Размер (в байтах) группы строк, которая обеспечивает логическое разбиение данных на строки. Размер группы строк по умолчанию составляет 8 * 1024 * 1024 байт |
PAGE_SIZE |
Размер (в байтах) страницы, которая делит группы строк в столбце на фрагменты столбцов. Размер страницы по умолчанию составляет 1 * 1024 * 1024 байт |
ENABLE_DICTIONARY |
Указывает, следует ли включать словарное кодирование.
Значение по умолчанию — |
DICTIONARY_PAGE_SIZE |
Когда словарное кодирование включено, для каждого столбца в каждой группе строк определяется единая словарная страница.
Параметр |
PARQUET_VERSION |
Версия Parquet; поддерживаются значения |
SCHEMA |
Абсолютный путь к файлу схемы Parquet на хосте Greengage DB или в HDFS. Если значение не указано, PXF создает схему на основе определения внешней таблицы |
Условия переполнения числовых данных
Для записи числовых данных в формат Parquet через коннектор PXF используется класс HiveDecimal, в котором как точность, так и масштаб числового типа ограничены максимальным значением 38.
При определении столбца внешней таблицы с типом NUMERIC без указания точности и масштаба PXF неявно сопоставляет столбец типу DECIMAL(38, 18).
PXF обрабатывает следующие условия переполнения числовых данных:
-
Столбец внешней таблицы определен с типом
NUMERIC, при этом общее количество цифр значения превышает максимально допустимую точность в 38, например1234567890123456789012345678901234567890.12345, в котором общее количество цифр — 45. -
Столбец внешней таблицы определен с типом
NUMERIC(<precision>)и точностью (<precision>), превышающей 38, напримерNUMERIC(55). -
Столбец внешней таблицы определен с типом
NUMERIC, при этом количество цифр в целой части значения превышает 20 (38-18), например123456789012345678901234567890.12345, в котором количество цифр целой части — 30.
Если определяется столбец с типом NUMERIC(<precision>, <scale>), в котором количество цифр в целой части значения превышает величину <precision>-<scale>, PXF возвращает ошибку.
Например, определен столбец NUMERIC(20,4) со значением 12345678901234567.12, в котором количество цифр целой части равно 17, что превышает 20-4=16.
При обнаружении переполнения числовых данных PXF выполняет одно из следующих действий: округляет значение (по умолчанию), возвращает ошибку или игнорирует переполнение.
Выполняемое действие указывается с помощью свойства pxf.parquet.write.decimal.overflow конфигурационного файла pxf-site.xml сервера PXF.
| Значение | Действие PXF |
|---|---|
round |
Действие по умолчанию. При обнаружении переполнения PXF пытается округлить значение для соответствия требованиям точности и масштаба перед записью и возвращает ошибку, если округление не удалось. Это может потенциально привести к неполному набору данных во внешней системе |
error |
PXF возвращает ошибку при обнаружении переполнения, и транзакция прерывается |
ignore |
PXF возвращает предупреждение и пытается округлить значение для соответствия требованиям точности и масштаба; если округление не удалось, записывается значение |
Подробную информацию о конфигурировании сервера PXF приведена в статье Настройка PXF-сервера документации PXF.
Примеры
Эти примеры демонстрируют, как настроить и использовать коннектор PXF HDFS для чтения и записи данных Parquet между Greengage DB и HDFS с использованием внешних таблиц. Поскольку данные в формате Parquet представлены в двоичном формате и не предназначены для чтения человеком, для создания файлов данных используется пишущая внешняя таблица, а затем эти файлы загружаются в Greengage DB с помощью читающей внешней таблицы.
Конфигурирование коннектора PXF HDFS
Для того чтобы подключиться к HDFS с помощью PXF, необходимо создать конфигурацию сервера, как описано в статье Настройка коннекторов PXF Hadoop документации PXF, а затем синхронизировать конфигурацию между хостами кластера Greengage DB:
-
Подключитесь к мастер-хосту Greengage DB как
gpadmin. -
Перейдите в каталог $PXF_BASE/servers и создайте каталог конфигурации сервера Hadoop с именем hadoop:
$ mkdir $PXF_BASE/servers/hadoop $ cd $PXF_BASE/servers/hadoop -
Скопируйте файлы конфигурации core-site.xml, hdfs-site.xml, mapred-site.xml и yarn-site.xml с хоста NameNode кластера Hadoop на текущий хост:
$ scp hdfsuser@namenode:/etc/hadoop/conf/core-site.xml . $ scp hdfsuser@namenode:/etc/hadoop/conf/hdfs-site.xml . $ scp hdfsuser@namenode:/etc/hadoop/conf/mapred-site.xml . $ scp hdfsuser@namenode:/etc/hadoop/conf/yarn-site.xml . -
Синхронизируйте конфигурацию между хостами кластера Greengage DB:
$ pxf cluster sync
Создание пишущей внешней таблицы
-
На мастер-хосте Greengage DB создайте пишущую внешнюю таблицу, сохраняющую данные в HDFS-каталог /tmp/pxf_examples/customers. В выражении
LOCATIONукажите PXF-профильhdfs:parquetи конфигурацию сервера. В выраженииFORMATукажитеpxfwritable_export— встроенную кастомную функцию форматирования для операций записи:CREATE WRITABLE EXTERNAL TABLE customers_w ( id INT, name TEXT, ordered_items TEXT[] ) LOCATION ('pxf://tmp/pxf_examples/customers?PROFILE=hdfs:parquet&SERVER=hadoop') FORMAT 'CUSTOM' (FORMATTER='pxfwritable_export'); -
Вставьте тестовые данные в таблицу
customers_w:INSERT INTO customers_w VALUES (1, 'John Doe', ARRAY['laptop', 'monitor']), (2, 'Jane Smith', ARRAY['keyboard', 'mouse', 'pad']), (3, 'Bob Brown', ARRAY['headphones']), (4, 'Alice Green', ARRAY['webcam', 'microphone']); -
На хосте HDFS проверьте содержимое созданного каталога /tmp/pxf_examples/customers:
$ hdfs dfs -ls /tmp/pxf_examples/customersВывод должен выглядеть подобным образом:
Found 4 items -rw-r--r-- 3 gpadmin hadoop 799 2026-02-05 14:38 /tmp/pxf_examples/customers/31-0000000034_0.snappy.parquet -rw-r--r-- 3 gpadmin hadoop 769 2026-02-05 14:38 /tmp/pxf_examples/customers/31-0000000034_1.snappy.parquet -rw-r--r-- 3 gpadmin hadoop 807 2026-02-05 14:38 /tmp/pxf_examples/customers/31-0000000034_2.snappy.parquet -rw-r--r-- 3 gpadmin hadoop 789 2026-02-05 14:38 /tmp/pxf_examples/customers/31-0000000034_3.snappy.parquet
Создание читающей внешней таблицы
-
На мастер-хосте Greengage DB создайте внешнюю таблицу, ссылающуюся на файлы из HDFS-каталога /tmp/pxf_examples/customers. В выражении
LOCATIONукажите PXF-профильhdfs:parquetи конфигурацию сервера. В выраженииFORMATукажитеpxfwritable_import— встроенную кастомную функцию форматирования для операций чтения:CREATE EXTERNAL TABLE customers_r ( id INT, name TEXT, ordered_items TEXT[] ) LOCATION('pxf://tmp/pxf_examples/customers?PROFILE=hdfs:parquet&SERVER=hadoop') FORMAT 'CUSTOM' (FORMATTER='pxfwritable_import'); -
Выполните запрос к созданной внешней таблице:
SELECT * FROM customers_r;Вывод должен выглядеть следующим образом:
id | name | ordered_items ----+-------------+---------------------- 1 | John Doe | {laptop,monitor} 3 | Bob Brown | {headphones} 4 | Alice Green | {webcam,microphone} 2 | Jane Smith | {keyboard,mouse,pad} (4 rows)