3.2. Миграция данных

При миграции данных важен порядок полей в исходной и целевой схеме. Порядок полей и их тип в таблицах нераспределённой и распределённой БД должен быть одинаковым.

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

Shardman предоставляет удобные инструменты для миграции данных. При уже созданной схеме и выбранном ключе сегментирования остаётся определить правила миграции данных. Источником данных могут быть, как файлы экспорта данных в формате CSV, так и одиночный сервер СУБД.

Далеко не всегда удобно использовать CSV-файлы, так как они могут значительно увеличиваться в объёме и требовать дополнительных ресурсов для хранения и передачи.

Гораздо удобнее использовать прямую миграцию данных из БД в БД без этапа промежуточного хранения.

При миграции данных следует учитывать порядок загрузки данных. Таблицы могут быть связаны друг с другом внешним ключом, поэтому сначала нужно загружать данные таблиц, на которые будут ссылаться другие таблицы. Для этого в файле миграции следует задать приоритет, определяющий порядок загрузки данных из таблиц. Чем больше значение параметра priority, тем выше приоритет. Например, если заданы приоритеты 1, 2 и 3, то сначала будут загружены данные из таблиц с приоритетом 3, потом с приоритетом 2, последними — с приоритетом 1.

Команда shardmanctl load позволяет определить порядок миграции таблиц, который можно указать в конфигурационном файле в формате YML.

3.2.1. Наивный подход

Ниже представлен пример содержимого файла migrate.yml:

version: "1.0"
migrate:
 connstr: "dbname=demo host=single-pg-instance port=5432 user=postgres password=******"
 jobs: 8
 batch: 2000
 options:
 schemas:
   - name: bookings
     # параметр all со значением false отключает автоматическое создание таблиц
     # таблицы уже созданы ранее, на этапе миграции схемы
     all: false
     tables:
       - name: airports
         # определяем глобальную таблицу
         type: global
         # так как таблицы связаны, нужно задать порядок миграции данных,
          # выставляем наивысший приоритет таблицам, данные которых
         # должны быть скопированы в первую очередь
         priority: 3
       - name: aircrafts
         type: global
         priority: 3
       - name: seats
         type: global
         priority: 3
       - name: bookings
         type: global
         priority: 3
       - name: flights
         type: global
         priority: 3
       - name: tickets
         type: sharded
         # определяем сегментированную таблицу
         # указываем ключ распределения
         distributedby: ticket_no
         partitions: 4
         priority: 2
       - name: ticket_flights
         type: sharded
         distributedby: ticket_no
         # определяем сегментированную и совместно размещённую таблицу
         # указываем имя таблицы с которой будет совместно размещена таблица tickets_flights
         colocatewith: tickets
         partitions: 4
         priority: 2
       - name: boarding_passes
         type: sharded
         distributedby: ticket_no
         colocatewith: tickets
         partitions: 4
         priority: 1

В данном файле определён источник данных — узел с именем single-pg-instance, его порт для подключения, имя пользователя и пароль, а также имя БД источника данных. Определены также и некоторые параметры работы утилиты (их может быть довольно много, как показано Подразделе «Загрузка данных из схемы PostgreSQL»). В файле также задано количество потоков — 8, то есть размер порции обрабатываемых данных в строках при миграции, а также приоритеты для последовательной обработки таблиц. Сначала мигрируют данные в глобальные таблицы, следом данные в распределённые таблицы tickets и ticket_flights, затем данные в таблицу boarding_passes. Значение priority задаёт приоритет загрузки данных, чем больше значение ключа, тем раньше будут загружены данные соответствующих таблиц. Миграция выполняется с помощью следующей команды:

shardmanctl load --schema migrate.yml

Если в конце работы утилиты выводится сообщение: «data loading completed successfully» (загрузка данных успешно завершена), то миграция данных прошла успешно.

3.2.2. Комплексный подход

При данном подходе, запуск и работа утилиты shardmanctl в режиме load не будет отличаться от работы при наивном подходе. Однако, немного изменится файл, определяющий порядок загрузки таблиц, так как изменился ключ сегментирования:

 ---
version: "1.0"
migrate:
 connstr: "dbname=demo host=single-pg-instance port=5432 user=postgres password=postgres"
 jobs: 8
 batch: 2000
 options:
 schemas:
   - name: bookings
     all: false
     tables:
       - name: airports
         type: global
         priority: 5
       - name: aircrafts
         type: global
         priority: 5
       - name: seats
         type: global
         priority: 5
       - name: flights
         type: global
         priority: 5
       - name: bookings
         type: sharded
         priority: 4
         partitions: 4
         distributedby: book_ref
       - name: tickets
         type: sharded
         distributedby: book_ref
         colocatewith: bookings
         partitions: 4
         priority: 3
       - name: ticket_flights
         type: sharded
         distributedby: book_ref
         colocatewith: bookings
         partitions: 4
         priority: 2
       - name: boarding_passes
         type: sharded
         distributedby: book_ref
         colocatewith: bookings
         partitions: 4
         priority: 1