-- Retention Cohort -- of users whose first `initial_event` lands on day D, -- what share triggered `return_event` on day D+k for k in 1..Periods. -- -- Required parameters (clickhouse.Named): -- workspace_id : String -- from : DateTime64(3,'UTC') -- to : DateTime64(3,'UTC') -- initial_event : String -- return_event : String -- -- Template inputs: -- .Outer : []{ RIndex int; OffsetDay int; Last bool } -- One entry per follow-up day. RIndex is the position in the retention() -- output array; OffsetDay is the day delta from the cohort day. SELECT cohort_day, countIf(arrayElement(r, 1)) AS cohort_size, {{- range $p := .Outer }} countIf(arrayElement(r, {{ $p.RIndex }})) AS retained_d{{ $p.OffsetDay }}{{ if not $p.Last }},{{ end }} {{- end }} FROM ( SELECT user_id, toDate(min(if(event = {initial_event:String}, timestamp, NULL))) AS cohort_day, retention( event = {initial_event:String} AND toDate(timestamp) = cohort_day, {{- range $p := .Outer }} event = {return_event:String} AND toDate(timestamp) = addDays(cohort_day, {{ $p.OffsetDay }}){{ if not $p.Last }},{{ end }} {{- end }} ) AS r FROM events_track WHERE workspace_id = {workspace_id:String} AND received_at >= {from:DateTime64(3,'UTC')} AND received_at < {to:DateTime64(3,'UTC')} AND user_id != '' AND event IN ({initial_event:String}, {return_event:String}) GROUP BY user_id HAVING cohort_day IS NOT NULL ) GROUP BY cohort_day ORDER BY cohort_day