- Зачем:
- в docs/labs/ будет много заданий; номер ступени и номер задания в имени
делают папку оглавлением программы и избавляют от поиска по README (#230).
- Что:
- шесть ТЗ переименованы через git mv: 1-1…1-5 для ступени 1,
2-1-superset-chart.md для ступени 2; факультатив superset-dashboard.md
остался без номера.
- обновлены ссылки в docs/labs/README.md, 2-1-superset-chart.md,
docs/architecture/dds/session.md и пути в dags/homework_check.py.
- правило имен для docs/labs/ в AGENTS.md переписано под S-N-slug.
- Проверка:
- make lint; скрипт обхода относительных ссылок в docs/ и AGENTS.md —
битых нет.
Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
8.1 KiB
Задание 3: dm.session_overview
Чему учит: хранить слагаемые, а не готовые средние и доли. Понимать,
почему сумма visitors по строкам сейчас сходится, но начнет завышать
аудиторию, если у одной куки появятся визиты с двух устройств.
Сначала прочитать
Роль витрины
Витрина нужна, чтобы по дням сравнивать визиты с телефона и компьютера: их число, длительность, просмотры страниц и частоту покупок.
На прошлом стенде витрина выделяла визиты сама. Теперь их рассчитывают в DDS, а повторять зерно сессий ради представления с переименованными колонками незачем. Здесь вы учитесь дневной агрегации, поэтому зерно — день и устройство. Выбор описан в разделе «Форма: по зерну, не по цене запроса» справочника DM.
Что сделать
Источник — dds.session_v. Зерно — день сессии × категория устройства.
Зерно новое, поэтому витрина хранится готовым агрегатом — см. «Как принято
на ступени 1». Создайте пять объектов:
dm.session_overview_rep / _dist, донор _stage_rep / _stage_dist и
публичное представление dm.session_overview_v. Ключ партиции — день.
Состав колонок
| Колонка | Тип | Значение |
|---|---|---|
report_date |
Date |
День сессии |
device_category |
LowCardinality(String) |
Категория устройства |
sessions |
UInt64 |
Число визитов |
visitors |
UInt64 |
Число разных client_id |
bounce_sessions |
UInt64 |
Визиты ровно из одного события |
purchase_sessions |
UInt64 |
Визиты хотя бы с одной покупкой |
duration_seconds_total |
UInt64 |
Суммарная длительность визитов |
events_total |
UInt64 |
Число событий во всех визитах |
pageviews |
UInt64 |
Число просмотров страниц |
cart_adds |
UInt64 |
Число добавлений в корзину |
purchases |
UInt64 |
Число покупок |
_load_id |
String |
Идентификатор запуска, собравшего день |
_load_ts |
DateTime64(3, 'UTC') |
Время сборки |
Возьмите device_category из сессии: DDS уже заменил код словом. Из четырех
категорий встречаются desktop, mobile и tablet. Строку для tv
создавайте только при появлении таких визитов.
Вместо avg_duration_seconds храните слагаемые. Среднее из средних по трем
устройствам даст неверный ответ за день: число сессий в категориях
различается, поэтому средние нужно взвешивать. Потребитель делит сумму
duration_seconds_total на сумму sessions. Долю отказов считают так же:
сумму bounce_sessions делят на сумму sessions, а не усредняют готовые
доли.
Ритм пересборки
Сессии прожитого дня больше не меняются. Как в задании 2, определяйте
диапазон от первого несобранного прожитого дня до последнего прожитого.
Соберите его в донор и замените дневные партиции. Добавьте задачу в
dm_transform.
Ключ шардирования
Выберите ключ самостоятельно. Визитов с планшета мало, с телефонов и
компьютеров — значительно больше. Если хотите взять хеш только от
device_category, сначала посчитайте строки на каждом шарде. Затем
объясните, почему такое распределение вас устраивает.
Ключ донора — тот же, что у цели (см. «Как принято на ступени 1» и раздел «Раскладка по шардам» справочника хранилища).
Почему сумма visitors сходится с dm.daily_traffic_v
Сравните сумму visitors по устройствам за день с dm.daily_traffic_v. На
стенде значения совпадут: устройство приписано куке на всю жизнь, поэтому за
день она учитывается только в одной строке. Это свойство мира стенда; см.
раздел «Паспорт куки» в словаре понятий.
Если появятся визиты одной куки с двух устройств, сумма начнет завышать
аудиторию. Проверки счетчиков по категориям этого не обнаружат. Число
посетителей дня берите из dm.daily_traffic_v, где оно рассчитано для дня
целиком.
Типичная ошибка
Повторное выделение визитов из событий может дать другие границы сессий, чем
в DDS. Используйте готовые сессии из dds.session_v. Если общее число
событий совпало с источником, а число сессий завышено, вероятная причина —
сборка витрины из событий вместо сессий.
Как проверить себя
Деловой ключ — device_category внутри дня. Получите прямой агрегат из
dds.session_v за день. Соедините его с dm.session_overview_v полным
внешним соединением по ключу. Посчитайте строки, где ключ отсутствует с
одной из сторон или различается любой счетчик. Расхождений должно быть ноль.
Еще две проверки дневных итогов:
- сумма
sessionsравна числу строкdds.session_vза день — без потерь и повторного учета визитов; - сумма
events_totalравна суммеevents_totalпо сессиям того же дня.
Приемка
- созданы пять объектов, донор объявлен через
ASи шардируется ключом цели; - в
dm.session_overview_vколонки перечислены явно; - источник —
dds.session_v, повторного выделения визитов нет; - физическая таблица не хранит средние и доли;
- задача
session_overviewвhomework_checkзавершилась успешно; - задача витрины добавлена в
dm_transform.