Привет, Я DocuDroid!
Оценка ИИ поиска
Спасибо за оценку нашего ИИ поиска!
Мы будем признательны, если вы поделитесь своими впечатлениями, чтобы мы могли улучшить наш ИИ поиск для вас и других читателей.
GitHub

Использование коннектора PXF HDFS для чтения и записи данных в формате Avro между Greengage DB и HDFS

Антон Монаков

Apache Avro — фреймворк сериализации данных, предназначенный для эффективного хранения и быстрой обработки. Он предоставляет компактный двоичный формат сериализации и использует JSON для определения как типов данных, так и схем, описывающих их структуру. Схема Avro вместе с данными является полностью самодокументирующейся.

В этой статье описывается настройка и использование коннектора PXF HDFS для чтения и записи данных Avro в HDFS с использованием внешних таблиц, а также приводятся практические примеры.

Сопоставление типов данных

В спецификации Avro определяются примитивные, составные и логические типы данных. Для представления примитивных типов и массивов примитивных типов Avro в Greengage DB необходимо сопоставить значения данных со столбцами Greengage DB того же типа.

Avro поддерживает составные типы данных, включая массивы непримитивных типов, ассоциативные массивы, записи, перечисления и фиксированные типы. Необходимо сопоставить верхнеуровневые поля этих составных типов данных с текстовым типом Greengage DB. PXF по умолчанию не поддерживает чтение составных типов, но вы можете создать функции Greengage DB или код приложения для извлечения или дальнейшей обработки их компонентов.

Avro поддерживает логические типы данных, такие как date, decimal, duration, time, timestamp и uuid.

Сопоставление при чтении

При чтении данных Avro в PXF используется следующее сопоставление типов данных.

Тип данных Avro Тип данных PXF / Greengage DB

boolean

BOOLEAN

bytes

BYTEA

double

DOUBLE

float

REAL

int

INT

long

BIGINT

string

TEXT

Составной тип: массив (любой размерности) типа: boolean, bytes, double, float, int, long, string

Массив (любой размерности) типа: BOOLEAN, BYTEA, DOUBLE, REAL, BIGINT, TEXT

Составной тип: массив других типов (схема Avro указана)

Массив типа TEXT

Составной тип: ассоциативный массив, запись, перечисление

TEXT с разделителями между элементами коллекции, сопоставленными парами ключ/значение и данными записи

Составной тип: фиксированный

BYTEA (поддерживается только для операций чтения)

Union

Следует вышеуказанным принципам для примитивных или составных типов данных в зависимости от конкретного объединения; должен содержать 2 элемента, одним из которых должен быть NULL

Логический тип: Date

DATE

Логический тип: Decimal

DECIMAL или NUMERIC

Логический тип: Duration

BYTEA

Логический тип: Time (миллисекундная точность)

TIME (время без указания часового пояса)

Логический тип: Time (микросекундная точность)

TIME (время без указания часового пояса)

Логический тип: Timestamp (миллисекундная точность)

TIMESTAMP (время без или с указанием часового пояса)

Логический тип: Timestamp (микросекундная точность)

TIMESTAMP (время без или с указанием часового пояса)

Логический тип: Local Timestamp (миллисекундная точность)

TIMESTAMP (время без или с указанием часового пояса)

Логический тип: Local Timestamp (микросекундная точность)

TIMESTAMP (время без или с указанием часового пояса)

Логический тип: UUID

UUID

Сопоставление при записи

PXF поддерживает запись данных Avro примитивных типов и массивов примитивных типов, а также запись прочих составных типов в виде строк (string). При записи данных Avro в PXF используется следующее сопоставление типов данных.

Тип данных PXF / Greengage DB Тип данных Avro

BIGINT

long

BOOLEAN

boolean

BYTEA

bytes

DOUBLE

double

CHAR (1)

string

ENUM

string

INT

int

REAL

float

SMALLINT (2)

int

TEXT

string

VARCHAR

string

NUMERIC, DATE, TIME, TIMESTAMP, TIMESTAMPTZ (схема Avro не указана)

string

Массив (любой размерности) типа: BIGINT, BOOLEAN, BYTEA, DOUBLE, INT, REAL, TEXT (схема Avro указана)

Массив (любой размерности) типа: long, boolean, bytes, double, int, float, string

Одномерный массив типа: BIGINT, BOOLEAN, BYTEA, DOUBLE, INT, REAL, TEXT (схема Avro не указана)

Одномерный массив типа: long, boolean, bytes, double, int, float, string

Одномерный массив типа: NUMERIC, DATE, TIME, TIMESTAMP, TIMESTAMPTZ (схема Avro указана)

Одномерный массив типа string

ENUM, RECORD

string

  1. При необходимости PXF дополняет типы CHAR[N] пробелами до длины N.

  2. Перед записью данных Avro PXF преобразует типы Greengage DB SMALLINT в INT. Убедитесь, что поле читается как INT.

Схемы и данные Avro

Схемы Avro определяются с помощью JSON и состоят из примитивных и составных типов, перечисленных в разделе Сопоставление типов данных. Файлы схем Avro обычно имеют суффикс .avsc. Поля в файле схемы Avro определяются через массив объектов, в каждом из которых указывается имя и тип. Файл данных Avro содержит схему и компактное двоичное представление данных и обычно имеет суффикс .avro. Для операций чтения и записи в HDFS указать схему Avro можно либо в виде двоичного файла *.avro, либо в виде файла схемы JSON-формата *.avsc.

Тип внешней таблицы Указана ли схема Описание

Читающая

Да

PXF использует указанную схему, переопределяя схему, встроенную в файл данных Avro

Читающая

Нет

PXF использует схему, встроенную в файл данных Avro

Пишущая

Да

PXF использует указанную схему

Пишущая

Нет

PXF создает схему на базе определения внешней таблицы

Указанный файл схемы Avro должен находиться либо в одном и том же каталоге на каждом хосте Greengage DB, либо в файловой системе Hadoop. Сначала PXF выполняет поиск по абсолютному пути к файлу на хостах Greengage DB. Если файл схемы не найден, поиск выполняется относительно пути к классам PXF. Если файл схемы не найден локально, выполняется поиск файла в HDFS.

ПРИМЕЧАНИЕ

Каталог $PXF_BASE/conf указан в пути к классам PXF. PXF может найти файл схемы Avro, если его поместить в этот каталог на каждом хосте Greengage DB.

Запись данных Avro

При создании внешней таблицы для записи данных Avro вы указываете имя каталога HDFS. Имена столбцов внешней таблицы становятся именами полей в Avro, и каждая строка таблицы сохраняется как запись Avro. Если не указан файл схемы, PXF генерирует схему для файла Avro на основе определения внешней таблицы Greengage DB.

В Avro есть тип данных null, но внешние таблицы Greengage DB не поддерживают ограничение столбца NOT NULL. По этой причине PXF оборачивает каждый тип данных в объединение сопоставленного типа Avro и null. Например, в случае внешней таблицы со столбцом, определенным с текстовым типом данных, PXF генерирует следующий элемент схемы:

["string", "null"]

PXF возвращает ошибку, если в данных встречается поле NULL, а предоставленная схема не включает объединение типа данных поля с null.

PXF поддерживает запись только примитивных типов данных Avro и массивов типов, перечисленных в разделе Сопоставление при записи. PXF не поддерживает запись составных типов в Avro:

  • Схема, указанная в выражении LOCATION команды CREATE EXTERNAL TABLE, должна содержать только примитивные типы данных.

  • Когда PXF генерирует схему, любой составной тип, указанный в определении столбца внешней пишущей таблицы, записывается в файл Avro как строковый тип.

Например, массив числового типа Greengage DB при записи преобразуется в строку, и читать эти данные нужно с помощью столбца Greengage DB типа TEXT.

Создание внешней таблицы с использованием протокола PXF

Чтобы создать внешнюю таблицу Greengage DB для чтения и записи данных в формате Avro в HDFS, используется следующий синтаксис:

CREATE [READABLE | WRITABLE] EXTERNAL TABLE <table_name>
    ( <column_name> <data_type> [, ...] | LIKE <other_table> )

    LOCATION ('pxf://<path-to-hdfs>?PROFILE=hdfs:avro[&<custom-option>=<value>[...]]')
    FORMAT 'CUSTOM' (FORMATTER='pxfwritable_import'|'pxfwritable_export')
    [DISTRIBUTED BY (<column_name> [, ... ] ) | DISTRIBUTED RANDOMLY];
Ключевое слово Значение

<path‑to‑hdfs>

Путь к каталогу или файлу в хранилище HDFS. Если в конфигурации сервера <server_name> указано свойство pxf.fs.basePath, значение <path‑to‑hdfs> трактуется как относительный путь к указанному базовому пути. В противном случае путь считается абсолютным. Значение пути не должно содержать символ $.

PXF поддерживает чтение и запись файлов Avro с использованием кодеков bzip2, xz, snappy и deflate

PROFILE=hdfs:avro

Для чтения и записи данных в формате Avro в HDFS используется профиль hdfs:avro

FORMAT 'CUSTOM'

Для чтения и записи данных в формате Avro в HDFS используется кастомный формат с использованием встроенных кастомных функций форматирования для операций чтения (pxfwritable_import) и записи (pxfwritable_export)

DISTRIBUTED BY

При загрузке данных из таблицы Greengage DB во внешнюю пишущую таблицу рекомендуется указывать ту же политику распределения или имя столбца в обеих таблицах. Это позволит избежать дополнительного перемещения данных между сегментами при выполнении операции загрузки. Более подробную информацию о распределении таблиц можно получить в статье Распределение данных

<custom‑option>

Одна из опций, описанных ниже, указываемая в строке LOCATION

SERVER=<server_name>

Имя конфигурации сервера, который используется для доступа к данным. Если значение не указано, используется сервер PXF по умолчанию

COLLECTION_DELIM

Символы, используемые в качестве разделителя элементов массива, ассоциативного массива или записи верхнего уровня при сопоставлении составного типа данных Avro и текстового столбца во время чтения данных. По умолчанию используется символ запятой (,)

MAPKEY_DELIM

Символы, используемые в качестве разделителя ключа и значения элемента ассоциативного массива при сопоставлении составного типа данных Avro и текстового столбца во время чтения данных. По умолчанию используется символ двоеточия (:)

RECORDKEY_DELIM

Символы, используемые в качестве разделителя имени и значения поля элемента записи при сопоставлении составного типа данных Avro и текстового столбца во время чтения данных. По умолчанию используется символ двоеточия (:)

SCHEMA

Абсолютный путь к файлу схемы Avro на хосте Greengage DB или в HDFS либо относительный путь к файлу схемы на хосте

IGNORE_MISSING_PATH

Действие, которое необходимо выполнить, если <path-to-hdfs> отсутствует или указан неверно. Если установлено значение false (по умолчанию), возвращается ошибка. Если установлено значение true, PXF игнорирует ошибку и возвращает пустой фрагмент

COMPRESSION_CODEC

Кодек сжатия, используемый при записи данных: bzip2, xz, snappy, deflate или uncompressed. Если значение не указано (или указано uncompressed), сжатие не производится

CODEC_LEVEL

Уровень сжатия (применяется только для кодеков deflate и xz), обеспечивающий баланс между скоростью и уровнем сжатия. Допустимые значения — от 1 (высокая скорость) до 9 (высокая степень сжатия). По умолчанию используется уровень 6

Примеры

Эти примеры демонстрируют, как настроить и использовать коннектор PXF HDFS для чтения и записи данных Avro между Greengage DB и HDFS с использованием внешних таблиц.

Предварительные требования

Для выполнения практических примеров подключитесь к мастер-хосту Greengage DB как gpadmin с помощью psql, как описано в статье Подключение к Greengage DB с использованием psql. Затем создайте тестовую базу данных customers и подключитесь к ней:

DROP DATABASE IF EXISTS customers;
CREATE DATABASE customers;
\c customers

Чтобы создать внешнюю таблицу с использованием протокола PXF, предварительно зарегистрируйте в БД расширение PXF, как описано в разделе Регистрация PXF в БД документации PXF:

CREATE EXTENSION pxf;

Конфигурирование коннектора PXF HDFS

Для того чтобы подключиться к HDFS с помощью PXF, необходимо создать конфигурацию сервера, как описано в статье Настройка коннекторов PXF Hadoop документации PXF, а затем синхронизировать конфигурацию между хостами кластера Greengage DB:

  1. Подключитесь к мастер-хосту Greengage DB как gpadmin:

  2. Перейдите в каталог $PXF_BASE/servers и создайте каталог конфигурации сервера Hadoop с именем hadoop:

    $ mkdir $PXF_BASE/servers/hadoop
    $ cd $PXF_BASE/servers/hadoop
  3. Скопируйте файлы конфигурации 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 .
  4. Синхронизируйте конфигурацию между хостами кластера Greengage DB:

    $ pxf cluster sync

Создание читающей внешней таблицы

  1. В каталоге /tmp на хосте HDFS создайте файл под названием avro_schema.avsc, содержащий схему Avro:

    {
      "type": "record",
      "name": "Customer",
      "fields": [
        {"name": "id", "type": "int"},
        {"name": "name", "type": "string"},
        {"name": "email", "type": "string"},
        {"name": "preferredChannels", "type": {"type": "array", "items": "string"}},
        {
          "name": "address",
          "type": {
            "type": "record",
            "name": "Address",
            "fields": [
              {"name": "street", "type": "string"},
              {"name": "city", "type": "string"},
              {"name": "state", "type": "string"},
              {"name": "zipCode", "type": "string"}
            ]
          }
        },
        {
          "name": "preferences",
          "type": {
            "type": "map",
            "values": "string"
          }
        }
      ]
    }

    В схеме используются следующие имена полей и типы данных:

    • id — int;

    • name — string;

    • email — string;

    • preferredChannels — массив элементов типа string (string[]);

    • address — запись, состоящая из полей типа string;

    • preferences — ассоциативный массив элементов типа string.

  2. В каталоге /tmp на хосте HDFS создайте JSON-файл данных Avro с именем customers.txt, соответствующий схеме выше. В данных примера в качестве разделителя записей верхнего уровня используется символ запятой (,), а в качестве разделителя ключей и значений ассоциативного массива и имен и значений записи — символ двоеточия (:):

    {
      "id": 123,
      "name": "Alice Smith",
      "email": "alice.smith@example.com",
      "preferredChannels": ["email", "sms"],
      "address": {
        "street": "123 Main St",
        "city": "Anytown",
        "state": "CA",
        "zipCode": "91234"
      },
      "preferences": {
        "notificationsEnabled": "true",
        "language": "en-US",
        "theme": "dark"
      }
    }
    {
      "id": 456,
      "name": "Bob Johnson",
      "email": "bob.johnson@example.com",
      "preferredChannels": ["push", "in-app"],
      "address": {
        "street": "456 Oak Ave",
        "city": "Springfield",
        "state": "IL",
        "zipCode": "62704"
      },
      "preferences": {
        "notificationsEnabled": "false",
        "language": "fr-CA",
        "theme": "light"
      }
    }
  3. Существуют различные способы преобразования текстовых файлов в формат Avro — как программно, так и через командную строку. В данном примере используется Java Avro tools. Загрузите последнюю версию JAR-файла Java Avro tools из Maven Central в каталог /tmp и преобразуйте файл customers.txt в двоичный формат Avro:

    $ curl -O https://repo1.maven.org/maven2/org/apache/avro/avro-tools/1.12.1/avro-tools-1.12.1.jar
    $ java -jar ./avro-tools-1.12.1.jar fromjson --schema-file /tmp/avro_schema.avsc /tmp/customers.txt > /tmp/customers.avro
  4. Создайте HDFS-каталог /tmp/pxf_examples для хранения файлов с тестовыми данными PXF и добавьте в HDFS созданный файл Avro:

    $ hdfs dfs -mkdir -p /tmp/pxf_examples
    $ hdfs dfs -put /tmp/customers.avro /tmp/pxf_examples/
  5. На мастер-хосте Greengage DB создайте внешнюю таблицу, ссылающуюся на файл customers.avro. Сопоставьте верхнеуровневые поля примитивных типов данных, id, name и email с типами данных Greengage DB (INT и TEXT). Сопоставьте поля составных типов (preferredChannels, address и preferences) с текстовым массивом Greengage DB (TEXT[]). В выражении LOCATION укажите PXF-профиль hdfs:avro и конфигурацию сервера. Установите символы разделителя для записи, ассоциативного массива и коллекции с помощью соответствующих опций. В выражении FORMAT укажите pxfwritable_import — встроенную кастомную функцию форматирования для операций чтения:

    CREATE EXTERNAL TABLE customers_r (
            id INT,
            name TEXT,
            email TEXT,
            preferredChannels TEXT[],
            address TEXT[],
            preferences TEXT[]
        )
        LOCATION ('pxf://tmp/pxf_examples/customers.avro?&PROFILE=hdfs:avro&SERVER=hadoop&COLLECTION_DELIM=,&MAPKEY_DELIM=:&RECORDKEY_DELIM=:')
        FORMAT 'CUSTOM' (FORMATTER='pxfwritable_import');
  6. Выполните запрос к созданной внешней таблице:

    SELECT * FROM customers_r;

    Вывод должен выглядеть следующим образом:

     id  |    name     |          email          | preferredchannels |                            address                             |                       preferences
    -----+-------------+-------------------------+-------------------+----------------------------------------------------------------+---------------------------------------------------------
     123 | Alice Smith | alice.smith@example.com | {email,sms}       | {"street:123 Main St",city:Anytown,state:CA,zipCode:91234}     | {theme:dark,notificationsEnabled:true,language:en-US}
     456 | Bob Johnson | bob.johnson@example.com | {push,in-app}     | {"street:456 Oak Ave",city:Springfield,state:IL,zipCode:62704} | {theme:light,notificationsEnabled:false,language:fr-CA}
    (2 rows)
  7. Опционально, выполните запрос к таблице для вывода идентификатора клиента и первых элементов текстовых массивов preferences и preferredchannels:

    SELECT id, preferences[1], preferredChannels[1] FROM customers_r;

    Вывод должен выглядеть следующим образом:

     id  | preferences | preferredchannels
    -----+-------------+-------------------
     123 | theme:dark  | email
     456 | theme:light | push
    (2 rows)

Создание пишущей внешней таблицы

  1. На мастер-хосте Greengage DB создайте пишущую внешнюю таблицу, сохраняющую данные в HDFS-каталог /tmp/pxf_examples/customers_w. В выражении LOCATION укажите PXF-профиль hdfs:avro и конфигурацию сервера. В выражении FORMAT укажите pxfwritable_export — встроенную кастомную функцию форматирования для операций записи:

    CREATE WRITABLE EXTERNAL TABLE customers_w(
            id INT,
            name TEXT, 
            preferredChannels TEXT[]    
        )
        LOCATION ('pxf://tmp/pxf_examples/customers_w?PROFILE=hdfs:avro&SERVER=hadoop')
        FORMAT 'CUSTOM' (FORMATTER='pxfwritable_export');
  2. Вставьте тестовые данные в таблицу customers_w:

    INSERT INTO customers_w 
    VALUES (1, 'Alice Smith', ARRAY['email', 'sms']),
           (1, 'Bob Johnson', ARRAY['push', 'in-app']);
  3. Скопируйте HDFS-каталог /tmp/pxf_examples/customers_w в локальный каталог /tmp:

    $ hdfs dfs -get -f /tmp/pxf_examples/customers_w /tmp
  4. Объедините файлы в каталоге customers_w в один файл customers_w.avro:

    $ java -jar ./avro-tools-1.12.1.jar concat /tmp/customers_w/ /tmp/customers_w.avro
  5. Просмотрите содержимое файла:

    $ java -jar ./avro-tools-1.12.1.jar tojson /tmp/customers_w.avro

    Вывод должен выглядеть следующим образом:

    {"id":{"int":1},"name":{"string":"Alice Smith"},"preferredchannels":{"array":[{"string":"email"},{"string":"sms"}]}}
    {"id":{"int":1},"name":{"string":"Bob Johnson"},"preferredchannels":{"array":[{"string":"push"},{"string":"in-app"}]}}