Автоматически генерировать поле в select запросе
У меня есть запрос
select B.cohort_month,
S.num_users as total_users,
B.month_number,
B.num_users * 100 / S.num_users as percentage
from (select C.cohort_month,
A.month_number,
count(1) as num_users
from (select A.device_id,
dateDiff('month', cm.cohort_month, toDate(date_trunc('month', event_date))) as month_number
from logs.track A
left join (SELECT device_id,
date_trunc('month', min(event_date)) cohort_month
FROM logs.track
WHERE app_name in ('com.yard', 'com.yard')
GROUP BY device_id) cm
ON A.device_id = cm.device_id
where app_name in ('com.citylan.yard', 'com.yard')
group by A.device_id, month_number) A
left join (SELECT device_id,
date_trunc('month', min(event_date)) cohort_month
FROM logs.track
WHERE app_name in ('com.yard', 'com.yard')
GROUP BY device_id) C ON A.device_id = C.device_id
group by C.cohort_month, A.month_number) B
left join (select cohort_month, count(1) as num_users
from (SELECT device_id,
date_trunc('month', min(event_date)) cohort_month
FROM logs.track
WHERE app_name in ('com.yard', 'com.yard')
GROUP BY device_id)
group by cohort_month
order by cohort_month) S ON B.cohort_month = S.cohort_month
where B.cohort_month IS NOT NULL
order by B.cohort_month, B.month_number;
Он формирует таблицу следующего вида

Мне нужно, что бы была таблица такого вида

и так до текущего месяца, дело в том что, количество месяцев не фиксированно (month_0, month_1, month_2 и т.д.) и каждый месяц будте +1 месяц, можно ли как то сделать что бы поле формировалось автоматически?
Ответы (2 шт):
Так что-бы совсем динамический получилось колонка из значения ресурсами SQL скорее всего никак, Но можно через CASE прогнать, и с интересующими тебя колонками.
https://stackoverflow.com/questions/1241178/mysql-rows-to-columns
Хотя отдельный гвоздь в гроб, хз поддерживает ли ClickHouse case'инг
Добавлять колонки динамически, не зная заранее их количество, нельзя (есть функция untuple, но количество элементов в tuple фиксированно). Но можно использовать массив, в котором хранить вычисления от заданного момента времени по текущий. Напримр, так можно сгенерировать массив:
WITH toDate('2021-02-01') AS begin_date
SELECT arrayMap(x -> (begin_date + toIntervalMonth(x)), range(toUInt32(dateDiff('month', begin_date, toStartOfMonth(today())) + 1)))
┌─arrayMap(lambda(tuple(x), plus(begin_date, toIntervalMonth(x))), range(toUInt32(plus(dateDiff('month', begin_date, toStartOfMonth(today())), 1))))─┐
│ ['2021-02-01','2021-03-01','2021-04-01','2021-05-01','2021-06-01','2021-07-01','2021-08-01','2021-09-01','2021-10-01','2021-11-01','2021-12-01'] │
└────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────┘
Если динамичность ну нужна, тогда можно просто добавть колонки, перечислив варианты.