Files
clickstream-data-platform/docs/labs/5-3-order-pipeline.md
T
ddadmin 596bcba01e docs(labs): разделено задание по заказам на три шага
- Зачем:
  - одно длинное ТЗ заставляло одновременно держать в голове три самостоятельных опыта и их очистку.
- Что:
  - проверки, разбор ODS и сборка DDS разнесены по трем последовательным заданиям.
  - уточнены границы учебной реализации, место диагностики и выбор закрытого дня.
  - оглавление ступени 5 дополнено ссылками на все три задания.
- Проверка:
  - проверены ссылки, пробная пачка jq, кластерные мутации и отсутствие ошибок пробелов в diff.
2026-09-06 16:25:04 -04:00

8.6 KiB
Raw Blame History

Перепишите сборку заказов в DDS

Чему учит: переписать пересборку заказов по состоянию слоев и доказать ее результат на пропущенном закрытом дне.

Сначала прочитать

Граница задания

Удалите готовый SQL и перепишите только три файла:

  • sql/dds/order_scope.sql;
  • sql/dds/order_rebuild.sql;
  • sql/dds/order_replace.sql.

Даг dds_transform, DDL, донор, ODS и обе проверки из первого задания уже задают границу работы. Перед началом убедитесь, что пробные строки предыдущего задания удалены, а семь DQ дают зеленый результат.

Поставьте world_live на паузу и дождитесь завершения активных прогонов. До завершения опыта не запускайте world_live_day, world_initialize и world_recreate. world_next_day понадобится только в явно указанном ниже случае.

Договор с дагом

Сохраните интерфейс dds_transform:

Файл Вход Результат
order_scope.sql без параметров одна строка first_day, last_day
order_rebuild.sql {first_day:Date}, {last_day:Date}, {load_id:String} выбранные дни в dds.order_stage_dist
order_replace.sql день в {{ params.day }} партиция дня в dds.order_rep

Объем состоит из текущего окна источника и хвоста от первого дня, который есть в ODS, но отсутствует в DDS. Текущее окно дают строки последнего snapshot_date: их минимальный и максимальный день заказа. Если источник пуст, order_scope.sql не возвращает строку. Если дыр нет, first_day равен началу окна. Если дыра старше, непрерывный отрезок начинается с нее.

order_rebuild.sql сначала очищает все партиции dds.order_stage_rep на кластере, затем записывает в dds.order_stage_dist весь выбранный отрезок. Он читает текущее состояние ods.order_v, вычисляет order_date, переводит времена в Europe/Samara, разбирает items в три параллельных массива и ставит координаты запуска.

Запись через Distributed должна завершиться до замены и использовать ключ целевой таблицы для раскладки строк. Способ собрать весь отрезок внутри файла выберите сами.

order_replace.sql работает с локальными dds.order_rep и dds.order_stage_rep на всем кластере. REPLACE PARTITION переносит готовую дневную партицию из донора и оставляет донор на месте. Структура, ключи и политика хранения совпадают: DDL объявляет донор через AS dds.order_rep.

Восстановите ближайший закрытый день

Найдите последний по дате день DDS, который лежит левее начала текущего окна ODS. Это ближайший к окну закрытый день: его удаление показывает расширение объема на дыру без пересборки всей истории.

Если такого дня еще нет, один раз продвиньте мир через world_next_day, дождитесь orders_ingest, затем запустите etl_pipeline. После этого снова зафиксируйте модельное время до конца опыта и выберите ближайший закрытый день.

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

ALTER TABLE dds.order_rep ON CLUSTER clickstream_cluster
DROP PARTITION 'YYYY-MM-DD';

Сразу запустите dq_check, до восстановления партиции. Красный результат должны дать orders_vs_ods и purchase_vs_orders_vs_dds. revenue_daily_vs_dds тоже даст красный результат, если в партиции были оплаченные заказы. classes_vs_inventory останется зеленым: до запуска dm_transform эта проверка читает прежнюю витрину сверки.

Запустите etl_pipeline. В группе dds_transform.order значение first_day должно совпасть с удаленным днем, а задачи replace - покрыть непрерывный отрезок от него до конца текущего окна. first_day ищите в строке про объем пересборки в журнале задачи order.scope дага dds_transform. После успешного прогона число заказов и контрольная сумма выбранного дня должны совпасть с сохраненными.

Проверьте раскладку и повтор

Напишите отдельный запрос к dds.order_dist, который получает фактическую ноду через hostName(), вычисляет ожидаемую по cityHash64(order_id) % 2 и считает несовпадения по каждой ноде. Остаток 0 соответствует clickhouse-01, остаток 1 - clickhouse-02. На обеих нодах число строк на чужом шарде должно быть нулевым. Счетные DQ читают Distributed-таблицы и такую ошибку раскладки не обнаруживают.

Запустите etl_pipeline еще раз при неизменном модельном времени. Группа заказов снова должна пересобрать текущее изменяемое окно. Контрольные суммы деловых полей остаются прежними, а все семь проверок дают зеленый результат.

Когда можно остановиться

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

Приемка

  • переписаны только три файла sql/dds/order_*.sql, инфраструктура упражнения не изменена;
  • удален ближайший к окну закрытый день, а красный DQ зафиксирован до восстановления;
  • first_day начался с удаленного дня, задачи замены покрыли непрерывный отрезок до конца окна;
  • число заказов и контрольная сумма восстановленного дня совпали;
  • order_items_total, orders_vs_ods и пять прежних DQ зелены;
  • проверка hostName() не нашла заказов DDS на чужом шарде;
  • повторный etl_pipeline сохранил деловые данные и зеленые проверки.