Построение сегментов
Проектирование любой маркетинговой кампании начинается с построения сегмента.
Логика рассуждений маркетингового менеджера примерно следующая: сначала отбираем eligible-клиентов, потом учитываем другие данные (чеки/модели/предложения), проверяем контактную политику, в конце – делим на A-, B-выборки и контрольную и тестовую группы.
Таким образом, шагов сегментации в типовых кампаниях может быть от 2–3 до 20, а в редких случаях – до 100. Для бизнес-пользователя критически необходимо видеть “счётчик” на каждом шаге – это означает, что расчёт одного такого сегмента приводит к 20 последовательно выполняемым SQL-запросам, и эта последовательность должна выполняться быстро.
При этом критерии построения могут меняться на ходу – в зависимости от того, что видит пользователь на счётчиках воронки. Например, если выборка составила всего лишь 1% активной клиентской базы при ожидаемых 10–15%, бизнес-пользователь может начать менять критерии на шагах, где отсекается наибольший процент. То есть, чтобы получить итоговый набор шагов построения сегмента, может быть пройдено множество итераций, каждая из которых будет сопровождаться большим количеством аналитических запросов в БД.
Именно построение сегмента занимает бОльшую часть времени работы бизнес-пользователя с инструментом.
Как итог, процесс построения сегмента – это не просто один из рутинных шагов построения кампании, а процесс, вокруг которого выстраивается всё остальное. И скорость расчёта сегмента, соответственно, – не просто нефункциональное требование, красиво звучащее для спонсоров в контексте снижения time-to-market, а то, что формирует у бизнес-пользователя отношение к инструменту и напрямую влияет на эффективность работы.
Здесь и раскрываются преимущества MPP и GreenPlum в частности:
- Обработка и хранение данных на автономных узлах параллельно, что позволяет максимально эффективно производить расчёты.
- Хранение данных в колоночном формате, то есть при чтении используются только те данные (столбцы), которые указаны в запросе, что также даёт прирост производительности.
- Сжатие данных легковесными алгоритмами компрессии, что делает чтение ещё эффективнее.
Нюансы “приготовления” GreenPlum
Использование MPP РСУБД вместо классических РСУБД может ускорить систему и дать дополнительные преимущества в части масштабирования. Но ошибки в конфигурации могут замедлить её настолько, что бизнес-процессы остановятся. Во избежание второго сценария необходимо правильно “готовить” MPP РСУБД, то есть на этапе внедрения сконфигурировать и спроектировать базу с учётом особенностей хранения и обработки данных.
Ниже представлены наши lessons learned по итогам нескольких итераций оптимизации, проведения нагрузочного тестирования и вывода системы в промышленную эксплуатацию.
При использовании GreenPlum и проектировании процессов и модели данных важно обратить внимание на следующие аспекты:
- В контексте автоматизации маркетинга GreenPlum целесообразен только под OLAP-нагрузку, поэтому если система предполагает OLTP или смешанную с OLTP нагрузку, то имеет смысл рассмотреть либо разделение БД (как в нашем проекте), либо просто классическую РСУБД – тот же PostgreSQL.
- Ключ дистрибуции отвечает за логику распределения данных по сегментам (нодам). GreenPlum позволяет его задавать на уровне отдельной таблицы. При этом нужно учесть следующие аспекты:
- Выбор атрибута, используемого в качестве ключа. При правильном выборе данные будут распределены по сегментам достаточно равномерно, что обеспечит максимальную эффективность и быстродействие системы.
- Ключи дистрибуции для таблиц, которые должны пересекаться/соединяться при построении сегментов. Если при джойне данные первой таблицы распределены иначе, чем данные второй таблицы, возникает необходимость переливки данных между сегментами для этой операции (redistribution). Такой процесс кардинально замедляет систему в случае джойна объёмных сущностей.
- С версии 6 есть возможность помечать таблицы для загрузки копии на каждый сегмент (то есть не распределять данные, а копировать полностью), что в случае с небольшими таблицами (справочниками/dimension-таблицами) позволяет снизить количество переливок и тоже положительно сказывается на производительности.
- Партицирование – обязательно для “глубоких” таблиц, позволяет снять головную боль в будущем при соблюдении условий:
- В таблицах предусмотрен ключ партицирования (неизменяемый атрибут, по которому возможно замерить “глубину” таблицы) – как правило, дата, например дата вставки записи.
- Размер партиции адекватно подобран под объём данных и типовую нагрузку в рамках системы: единственный 100% способ определить, что размер подобран хорошо, – это провести корректное нагрузочное тестирование.
- Важно помнить: при N партициях и M колонках в "колоночной" таблице в ОС создаётся NxM файлов даже для пустой таблицы.
- Автоматизированы процессы создания будущих партиций.
- Автоматизированы процессы архивации (удаления) данных – по партициям.
- Массовая загрузка данных. Необходимо учесть нюансы способов загрузки данных в кластер и выбирать среди них, исходя из источников данных/предполагаемой нагрузки/предполагаемого увеличения количества нод в кластере и т. д. Мы рассматривали 2 вариант заливки данных в GreenPlum:
- С помощью pxf – способа подключения сторонних БД/хранилищ (Hadoop: HDFS, Hive, HBase; объектные: S3, Azure, Google Cloud Storage; классические РСУБД через jdbc) к GreenPlum. Прожорливый на количество коннектов, причём прожорливость растёт с увеличением числа сегментов в кластере.
- С помощью gpfdist – способа подключения внешних файлов к GreenPlum. Требует установленного пакета greenplum-loader на сервере, с которого затягиваются файлы.
- Единый кластер под разные системы. Одной из идей заказчика была экономия в виде возможности переиспользовать существующий кластер GreenPlum, который обеспечивал нужды аналитических процессов другой системы. Для разграничения нагрузки были настроены ресурсные группы (aka Oracle Resource Manager). Ресурсные группы позволяют разграничивать CPU/RAM, но нагрузка на диски не разделяется. Поэтому для гарантии нормальной работы нескольких систем необходимо – по аналогии с традиционными СУБД:
- расселять потребителей в отдельные tablespace на разных дисковых массивах,
- в крайнем случае, разворачивать отдельные кластеры СУБД под отдельные системы.
- HouseKeeping. Следить за пользовательской нагрузкой и карать за плохие запросы. Токсичная нагрузка вызывает деградацию всего кластера из-за неразделимости некоторых ресурсов. В случае с операционными СУБД и аналитическими запросами от пользователей – выносить их с операционной БД системы в контур для аналитики/отчётности или как минимум загонять в менее приоритетную ресурсную группу.
- Ресурсные группы. Сами по себе ресурсные группы – отличный инструмент для разграничения нагрузки в рамках одной системы. К примеру, в контексте маркетинговой системы не избежать наложения процессов наполнения витрины, создания внутренних сущностей (предложений/контактов), а также построения сегментов. В реальности это всё сопровождается пользовательскими ad-hoc-запросами. Исходя из требований бизнеса ко времени работы кампаний/времени загрузки витрины и т. д., ресурсные группы позволят затюнить БД нужным образом.
- Также хорошей практикой является разделение "долгих" (запросы к тяжелым таблицам/переливка данных) и "быстрых" (запросы к метаданным, справочникам) запросов в разные ресурсные группы (заранее исполняя их через разных пользователей). На примере загрузки витрины это дало прирост в производительности.
- Более того, можно настроить динамическое переключение ресурсных групп: идея в том, чтобы менять настройки ресурсных групп по расписанию. Например:
- ночью почти нет маркетинговых кампаний, но зато есть ETL для наполнения витрин: поменяем настройки так, чтобы больше ресурсов было у пользователей под ETL;
- днём основная нагрузка от маркетинговых кампаний: поменяем настройки так, чтобы больше ресурсов было у пользователей Campaign Management.
- Сайзинг/инфраструктура – обязательно необходимо учесть следующее:
- заложить быстрые диски (ssd/nvme) под temp/spill, которые в любом случае понадобятся;
- предусмотреть максимально близкое расположение нод кластера GreenPlum – в том числе физически, так как GreenPlum чувствителен к сетевой инфраструктуре и требует высокой скорости интерконнекта между нодами кластера.
- Коннекты к GreenPlum. Аналогично PostgreSQL может потребоваться пулер соединений, если приложение генерит их много/не имеет встроенного пулера. Самый популярный пулер для PostgreSQL – pgBouncer – поддерживает и GreenPlum.
- Незакрытые (idle/idle in transaction) сессии. Регламентно закрывать такие сессии, так как они держат коннект и могут блокировать объекты.
Результаты проекта
Одна из главных целей проекта внедрения системы Campaign Management – возможность быстро и удобно строить сегменты для проведения маркетинговых кампаний – была полностью выполнена с использованием СУБД GreenPlum.
Как итог, были зафиксированы следующие метрики в части запуска боевых кампаний: