0
0
mirror of https://github.com/PostHog/posthog.git synced 2024-11-21 13:39:22 +01:00

feat: enable trend actors in udfs (and enable matched recordings for trends) (#25641)

Co-authored-by: github-actions <41898282+github-actions[bot]@users.noreply.github.com>
This commit is contained in:
Sandy Spicer 2024-10-17 13:12:04 -07:00 committed by GitHub
parent a9b5a600bd
commit e468f3b81f
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
35 changed files with 1359 additions and 1704 deletions

View File

@ -138,7 +138,7 @@
<function>
<type>executable_pool</type>
<name>aggregate_funnel_trends</name>
<return_type>Array(Tuple(UInt64, Int8, Nullable(String)))</return_type>
<return_type>Array(Tuple(UInt64, Int8, Nullable(String), UUID))</return_type>
<return_name>result</return_name>
<argument>
<type>UInt8</type>
@ -169,7 +169,7 @@
<name>prop_vals</name>
</argument>
<argument>
<type>Array(Tuple(Nullable(Float64), UInt64, Nullable(String), Array(Int8)))</type>
<type>Array(Tuple(Nullable(Float64), UInt64, UUID, Nullable(String), Array(Int8)))</type>
<name>value</name>
</argument>
<format>JSONEachRow</format>
@ -181,7 +181,7 @@
<type>executable_pool</type>
<name>aggregate_funnel_array_trends</name>
<!-- Return type for trends is a start interval time, a success flag (1 or -1), and a breakdown value -->
<return_type>Array(Tuple(UInt64, Int8, Array(String)))</return_type>
<return_type>Array(Tuple(UInt64, Int8, Array(String), UUID))</return_type>
<return_name>result</return_name>
<argument>
<type>UInt8</type>
@ -208,7 +208,7 @@
<name>prop_vals</name>
</argument>
<argument>
<type>Array(Tuple(Nullable(Float64), UInt64, Array(String), Array(Int8)))</type>
<type>Array(Tuple(Nullable(Float64), UInt64, UUID, Array(String), Array(Int8)))</type>
<name>value</name>
</argument>
<format>JSONEachRow</format>
@ -220,7 +220,7 @@
<type>executable_pool</type>
<name>aggregate_funnel_cohort_trends</name>
<!-- Return type for trends is a start interval time, a success flag (1 or -1), and a breakdown value -->
<return_type>Array(Tuple(UInt64, Int8, UInt64))</return_type>
<return_type>Array(Tuple(UInt64, Int8, UInt64, UUID))</return_type>
<return_name>result</return_name>
<argument>
<type>UInt8</type>
@ -247,7 +247,7 @@
<name>prop_vals</name>
</argument>
<argument>
<type>Array(Tuple(Nullable(Float64), UInt64, UInt64, Array(Int8)))</type>
<type>Array(Tuple(Nullable(Float64), UInt64, UUID, UInt64, Array(Int8)))</type>
<name>value</name>
</argument>
<format>JSONEachRow</format>
@ -285,7 +285,7 @@
<name>prop_vals</name>
</argument>
<argument>
<type>Array(Tuple(Nullable(Float64), UInt64, Array(String), Array(Int8)))</type>
<type>Array(Tuple(Nullable(Float64), UInt64, UUID, Array(String), Array(Int8)))</type>
<name>value</name>
</argument>
<format>JSONEachRow</format>

View File

@ -87,6 +87,7 @@ export function FunnelLineGraph({
kind: NodeKind.FunnelsActorsQuery,
source: querySource,
funnelTrendsDropOff: false,
includeRecordings: true,
funnelTrendsEntrancePeriodStart: dayjs(day).format('YYYY-MM-DD HH:mm:ss'),
}
openPersonsModal({

View File

@ -3,6 +3,7 @@ use std::str::FromStr;
use itertools::Itertools;
use serde::{Deserialize, Serialize};
use serde_json::{json, Value};
use uuid::Uuid;
use crate::PropVal;
fn deserialize_number_from_string<'de, D>(deserializer: D) -> Result<u64, D::Error>
@ -15,8 +16,7 @@ where
#[derive(Clone, Deserialize)]
struct EnteredTimestamp {
timestamp: f64,
timings: Vec<f64>,
timestamp: f64
}
#[derive(Clone, Deserialize)]
@ -24,6 +24,7 @@ struct Event {
timestamp: f64,
#[serde(deserialize_with = "deserialize_number_from_string")]
interval_start: u64,
uuid: Uuid,
breakdown: PropVal,
steps: Vec<i8>,
}
@ -40,10 +41,16 @@ struct Args {
}
#[derive(Serialize)]
struct ResultStruct(u64, i8, PropVal);
struct ResultStruct(u64, i8, PropVal, Uuid);
struct IntervalData {
max_step: usize,
max_step_event_uuid: Uuid,
entered_timestamp: Vec<EnteredTimestamp>,
}
struct Vars {
interval_start_to_entered_timestamps: HashMap<u64, Vec<EnteredTimestamp>>,
interval_start_to_entered_timestamps: HashMap<u64, IntervalData>,
}
struct AggregateFunnelRow {
@ -53,7 +60,6 @@ struct AggregateFunnelRow {
const DEFAULT_ENTERED_TIMESTAMP: EnteredTimestamp = EnteredTimestamp {
timestamp: 0.0,
timings: vec![],
};
pub fn process_line(line: &str) -> Value {
@ -114,9 +120,9 @@ impl AggregateFunnelRow {
// At this point, everything left in entered_timestamps is a failure, if it has made it to from_step
for entered_timestamp in vars.interval_start_to_entered_timestamps.values() {
if !self.results.contains_key(&(entered_timestamp[0].timestamp as u64)) && entered_timestamp[0].timings.len() > 0 {
self.results.insert(entered_timestamp[0].timestamp as u64, ResultStruct(entered_timestamp[0].timestamp as u64, -1, prop_val.clone() ));
for interval_data in vars.interval_start_to_entered_timestamps.values() {
if !self.results.contains_key(&(interval_data.entered_timestamp[0].timestamp as u64)) && interval_data.max_step >= args.from_step + 1 {
self.results.insert(interval_data.entered_timestamp[0].timestamp as u64, ResultStruct(interval_data.entered_timestamp[0].timestamp as u64, -1, prop_val.clone(), interval_data.max_step_event_uuid));
}
}
}
@ -141,36 +147,32 @@ impl AggregateFunnelRow {
if step == 1 {
if !vars.interval_start_to_entered_timestamps.contains_key(&event.interval_start) && !self.results.contains_key(&event.interval_start) {
let mut entered_timestamp = vec![DEFAULT_ENTERED_TIMESTAMP.clone(); args.num_steps + 1];
entered_timestamp[0] = EnteredTimestamp { timestamp: event.interval_start as f64, timings: if args.from_step == 0 {vec![1.0]} else {vec![]} };
entered_timestamp[1] = EnteredTimestamp { timestamp: event.timestamp, timings: vec![event.timestamp] };
vars.interval_start_to_entered_timestamps.insert(event.interval_start, entered_timestamp);
entered_timestamp[0] = EnteredTimestamp { timestamp: event.interval_start as f64 };
entered_timestamp[1] = EnteredTimestamp { timestamp: event.timestamp };
vars.interval_start_to_entered_timestamps.insert(event.interval_start, IntervalData { max_step: 1, max_step_event_uuid: event.uuid, entered_timestamp: entered_timestamp });
}
} else {
for entered_timestamp in vars.interval_start_to_entered_timestamps.values_mut() {
let in_match_window = (event.timestamp - entered_timestamp[step - 1].timestamp) <= args.conversion_window_limit as f64;
let already_reached_this_step = entered_timestamp[step].timestamp == entered_timestamp[step - 1].timestamp;
for interval_data in vars.interval_start_to_entered_timestamps.values_mut() {
let in_match_window = (event.timestamp - interval_data.entered_timestamp[step - 1].timestamp) <= args.conversion_window_limit as f64;
let already_reached_this_step = interval_data.entered_timestamp[step].timestamp == interval_data.entered_timestamp[step - 1].timestamp;
if in_match_window && !already_reached_this_step {
if exclusion {
return false;
}
let is_unmatched_step_attribution = self.breakdown_step.map(|breakdown_step| step == breakdown_step - 1).unwrap_or(false) && *prop_val != event.breakdown;
if !is_unmatched_step_attribution {
entered_timestamp[step] = EnteredTimestamp {
timestamp: entered_timestamp[step - 1].timestamp,
timings: {
let mut timings = entered_timestamp[step - 1].timings.clone();
timings.push(event.timestamp);
timings
},
interval_data.entered_timestamp[step] = EnteredTimestamp {
timestamp: interval_data.entered_timestamp[step - 1].timestamp
};
// check if we have hit the goal. if we have, remove it from the list and add it to the successful_timestamps
if entered_timestamp[args.num_steps].timestamp != 0.0 {
if interval_data.entered_timestamp[args.num_steps].timestamp != 0.0 {
self.results.insert(
entered_timestamp[0].timestamp as u64,
ResultStruct(entered_timestamp[0].timestamp as u64, 1, prop_val.clone())
interval_data.entered_timestamp[0].timestamp as u64,
ResultStruct(interval_data.entered_timestamp[0].timestamp as u64, 1, prop_val.clone(), event.uuid)
);
} else if step == args.from_step + 1 {
entered_timestamp[0].timings.push(1.0)
} else if step > interval_data.max_step {
interval_data.max_step = step;
interval_data.max_step_event_uuid = event.uuid;
}
}
}
@ -180,10 +182,10 @@ impl AggregateFunnelRow {
// If a strict funnel, clear all of the steps that we didn't match to
// If we are processing multiple events, skip this step, because ordering makes it complicated
if args.funnel_order_type == "strict" {
for entered_timestamp in vars.interval_start_to_entered_timestamps.values_mut() {
for i in 1..entered_timestamp.len() {
for interval_data in vars.interval_start_to_entered_timestamps.values_mut() {
for i in 1..interval_data.entered_timestamp.len() {
if !event.steps.contains(&(i as i8)) {
entered_timestamp[i] = DEFAULT_ENTERED_TIMESTAMP;
interval_data.entered_timestamp[i] = DEFAULT_ENTERED_TIMESTAMP;
}
}
}

View File

@ -5,7 +5,8 @@ from .funnel_strict import FunnelStrict
from .funnel_unordered import FunnelUnordered
from .funnel_time_to_convert import FunnelTimeToConvert
from .funnel_trends import FunnelTrends
from .funnel_trends_udf import FunnelTrendsUDF
from .funnel_persons import FunnelActors
from .funnel_strict_persons import FunnelStrictActors
from .funnel_unordered_persons import FunnelUnorderedActors
from .funnel_trends_persons import FunnelTrendsActors
from .funnel_strict_actors import FunnelStrictActors
from .funnel_unordered_actors import FunnelUnorderedActors
from .funnel_trends_actors import FunnelTrendsActors

View File

@ -7,8 +7,8 @@ from posthog.hogql.property import property_to_expr
from posthog.hogql_queries.insights.funnels import FunnelUDF
from posthog.hogql_queries.insights.funnels.funnel_event_query import FunnelEventQuery
from posthog.hogql_queries.insights.funnels.funnel_persons import FunnelActors
from posthog.hogql_queries.insights.funnels.funnel_strict_persons import FunnelStrictActors
from posthog.hogql_queries.insights.funnels.funnel_unordered_persons import FunnelUnorderedActors
from posthog.hogql_queries.insights.funnels.funnel_strict_actors import FunnelStrictActors
from posthog.hogql_queries.insights.funnels.funnel_unordered_actors import FunnelUnorderedActors
from posthog.models.action.action import Action
from posthog.models.element.element import chain_to_elements
from posthog.models.event.util import ElementSerializer

View File

@ -1,19 +1,27 @@
from typing import cast
from typing import cast, Optional
from rest_framework.exceptions import ValidationError
from posthog.hogql import ast
from posthog.hogql.constants import HogQLQuerySettings
from posthog.hogql.parser import parse_select
from posthog.hogql.parser import parse_select, parse_expr
from posthog.hogql_queries.insights.funnels import FunnelTrends
from posthog.hogql_queries.insights.funnels.funnel_udf import udf_event_array_filter
from posthog.hogql_queries.insights.utils.utils import get_start_of_interval_hogql_str
from posthog.schema import BreakdownType, BreakdownAttributionType
from posthog.utils import DATERANGE_MAP
from posthog.utils import DATERANGE_MAP, relative_date_parse
TIMESTAMP_FORMAT = "%Y-%m-%d %H:%M:%S"
HUMAN_READABLE_TIMESTAMP_FORMAT = "%-d-%b-%Y"
class FunnelTrendsUDF(FunnelTrends):
def __init__(self, *args, **kwargs):
super().__init__(*args, **kwargs)
# In base, these fields only get added if you're running an actors query
if "uuid" not in self._extra_event_fields:
self._extra_event_fields.append("uuid")
def get_step_counts_query(self):
max_steps = self.context.max_steps
return self._get_step_counts_query(
@ -30,7 +38,18 @@ class FunnelTrendsUDF(FunnelTrends):
self.context.funnelWindowInterval * DATERANGE_MAP[self.context.funnelWindowIntervalUnit].total_seconds()
)
def get_query(self) -> ast.SelectQuery:
def matched_event_select(self):
if self._include_matched_events():
return """
groupArray(tuple(timestamp, uuid, $session_id, $window_id)) as user_events,
mapFromArrays(arrayMap(x -> x.2, user_events), user_events) as user_events_map,
[user_events_map[af_tuple.4]] as matching_events,
"""
return ""
# This is the function that calls the UDF
# This is used by both the query itself and the actors query
def _inner_aggregation_query(self):
# If they're asking for a "to_step" just truncate the funnel
funnelsFilter = self.context.funnelsFilter
max_steps = self.context.max_steps if funnelsFilter.funnelToStep is None else funnelsFilter.funnelToStep + 1
@ -79,7 +98,12 @@ class FunnelTrendsUDF(FunnelTrends):
parse_select(
f"""
SELECT
arraySort(t -> t.1, groupArray(tuple(toFloat(timestamp), _toUInt64(toDateTime({get_start_of_interval_hogql_str(self.context.interval.value, team=self.context.team, source='timestamp')})), {prop_selector}, arrayFilter((x) -> x != 0, [{steps}{exclusions}])))) as events_array,
arraySort(t -> t.1, groupArray(tuple(
toFloat(timestamp),
_toUInt64(toDateTime({get_start_of_interval_hogql_str(self.context.interval.value, team=self.context.team, source='timestamp')})),
uuid,
{prop_selector},
arrayFilter((x) -> x != 0, [{steps}{exclusions}])))) as events_array,
arrayJoin({fn}(
{from_step},
{max_steps},
@ -91,7 +115,9 @@ class FunnelTrendsUDF(FunnelTrends):
)) as af_tuple,
toTimeZone(toDateTime(_toUInt64(af_tuple.1)), '{self.context.team.timezone}') as entrance_period_start,
af_tuple.2 as success_bool,
af_tuple.3 as breakdown
af_tuple.3 as breakdown,
{self.matched_event_select()}
aggregation_target as aggregation_target
FROM {{inner_event_query}}
GROUP BY aggregation_target{breakdown_prop}
""",
@ -100,6 +126,10 @@ class FunnelTrendsUDF(FunnelTrends):
)
# This is necessary so clickhouse doesn't truncate timezone information when passing datetimes to and from python
inner_select.settings = HogQLQuerySettings(date_time_output_format="iso", date_time_input_format="best_effort")
return inner_select
def get_query(self) -> ast.SelectQuery:
inner_select = self._inner_aggregation_query()
conversion_rate_expr = (
"if(reached_from_step_count > 0, round(reached_to_step_count / reached_from_step_count * 100, 2), 0)"
@ -163,3 +193,62 @@ class FunnelTrendsUDF(FunnelTrends):
{"fill_query": fill_query, "inner_select": inner_select},
)
return cast(ast.SelectQuery, s)
def _matching_events(self):
if (
hasattr(self.context, "actorsQuery")
and self.context.actorsQuery is not None
and self.context.actorsQuery.includeRecordings
):
return [ast.Alias(alias="matching_events", expr=ast.Field(chain=["matching_events"]))]
return []
def actor_query(
self,
extra_fields: Optional[list[str]] = None,
) -> ast.SelectQuery:
team, actorsQuery = self.context.team, self.context.actorsQuery
if actorsQuery is None:
raise ValidationError("No actors query present.")
# At this time, we do not support self.dropOff (we don't use it anywhere in the frontend)
if actorsQuery.funnelTrendsDropOff is None:
raise ValidationError(f"Actors parameter `funnelTrendsDropOff` must be provided for funnel trends persons!")
if actorsQuery.funnelTrendsEntrancePeriodStart is None:
raise ValidationError(
f"Actors parameter `funnelTrendsEntrancePeriodStart` must be provided funnel trends persons!"
)
entrancePeriodStart = relative_date_parse(actorsQuery.funnelTrendsEntrancePeriodStart, team.timezone_info)
if entrancePeriodStart is None:
raise ValidationError(
f"Actors parameter `funnelTrendsEntrancePeriodStart` must be a valid relative date string!"
)
select: list[ast.Expr] = [
ast.Alias(alias="actor_id", expr=ast.Field(chain=["aggregation_target"])),
*self._matching_events(),
*([ast.Field(chain=[field]) for field in extra_fields or []]),
]
select_from = ast.JoinExpr(table=self._inner_aggregation_query())
where = ast.And(
exprs=[
parse_expr("success_bool != 1") if actorsQuery.funnelTrendsDropOff else parse_expr("success_bool = 1"),
ast.CompareOperation(
op=ast.CompareOperationOp.Eq,
left=parse_expr("entrance_period_start"),
right=ast.Constant(value=entrancePeriodStart),
),
]
)
order_by = [ast.OrderExpr(expr=ast.Field(chain=["aggregation_target"]))]
return ast.SelectQuery(
select=select,
select_from=select_from,
order_by=order_by,
where=where,
)

View File

@ -35,23 +35,22 @@ class FunnelUDF(FunnelBase):
if property not in self._extra_event_properties:
self._extra_event_properties.append(property)
# I think I can delete this
def get_step_counts_query(self):
max_steps = self.context.max_steps
return self._get_step_counts_query(
outer_select=[
*self._get_matching_event_arrays(max_steps),
],
inner_select=[
*self._get_matching_events(max_steps),
],
)
def conversion_window_limit(self) -> int:
return int(
self.context.funnelWindowInterval * DATERANGE_MAP[self.context.funnelWindowIntervalUnit].total_seconds()
)
def matched_event_arrays_selects(self):
# We use matched events to get timestamps for the funnel as well as recordings
if self._include_matched_events() or self.context.includePrecedingTimestamp or self.context.includeTimestamp:
return """
af_tuple.4 as matched_event_uuids_array_array,
groupArray(tuple(timestamp, uuid, $session_id, $window_id)) as user_events,
mapFromArrays(arrayMap(x -> x.2, user_events), user_events) as user_events_map,
arrayMap(matched_event_uuids_array -> arrayMap(event_uuid -> user_events_map[event_uuid], arrayDistinct(matched_event_uuids_array)), matched_event_uuids_array_array) as matched_events_array,
"""
return ""
# This is the function that calls the UDF
# This is used by both the query itself and the actors query
def _inner_aggregation_query(self):
@ -90,21 +89,6 @@ class FunnelUDF(FunnelBase):
breakdown_attribution_string = f"{self.context.breakdownAttributionType}{f'_{self.context.funnelsFilter.breakdownAttributionValue}' if self.context.breakdownAttributionType == BreakdownAttributionType.STEP else ''}"
def matched_event_arrays_selects():
# We use matched events to get timestamps for the funnel as well as recordings
if (
self._include_matched_events()
or self.context.includePrecedingTimestamp
or self.context.includeTimestamp
):
return """
af_tuple.4 as matched_event_uuids_array_array,
groupArray(tuple(timestamp, uuid, $session_id, $window_id)) as user_events,
mapFromArrays(arrayMap(x -> x.2, user_events), user_events) as user_events_map,
arrayMap(matched_event_uuids_array -> arrayMap(event_uuid -> user_events_map[event_uuid], arrayDistinct(matched_event_uuids_array)), matched_event_uuids_array_array) as matched_events_array,
"""
return ""
inner_select = parse_select(
f"""
SELECT
@ -121,7 +105,7 @@ class FunnelUDF(FunnelBase):
af_tuple.1 + 1 as steps, -- Backward compatibility
af_tuple.2 as breakdown,
af_tuple.3 as timings,
{matched_event_arrays_selects()}
{self.matched_event_arrays_selects()}
aggregation_target
FROM {{inner_event_query}}
GROUP BY aggregation_target{breakdown_prop}

View File

@ -26,7 +26,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -77,7 +77,7 @@
JOIN
(SELECT aggregation_target AS actor_id, matched_events_array[plus(step_reached, 1)] AS matching_events, (matched_events_array[1][1]).1 AS timestamp, nullIf((matched_events_array[2][1]).1, 0) AS final_timestamp, (matched_events_array[1][1]).1 AS first_timestamp, steps AS steps, final_timestamp, first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array, arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple, af_tuple.1 AS step_reached, plus(af_tuple.1, 1) AS steps, af_tuple.2 AS breakdown, af_tuple.3 AS timings, af_tuple.4 AS matched_event_uuids_array_array, groupArray(tuple(timestamp, uuid, `$session_id`, `$window_id`)) AS user_events, mapFromArrays(arrayMap(x -> x.2, user_events), user_events) AS user_events_map, arrayMap(matched_event_uuids_array -> arrayMap(event_uuid -> user_events_map[event_uuid], arrayDistinct(matched_event_uuids_array)), matched_event_uuids_array_array) AS matched_events_array, aggregation_target AS aggregation_target
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array, arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple, af_tuple.1 AS step_reached, plus(af_tuple.1, 1) AS steps, af_tuple.2 AS breakdown, af_tuple.3 AS timings, af_tuple.4 AS matched_event_uuids_array_array, groupArray(tuple(timestamp, uuid, `$session_id`, `$window_id`)) AS user_events, mapFromArrays(arrayMap(x -> x.2, user_events), user_events) AS user_events_map, arrayMap(matched_event_uuids_array -> arrayMap(event_uuid -> user_events_map[event_uuid], arrayDistinct(matched_event_uuids_array)), matched_event_uuids_array_array) AS matched_events_array, aggregation_target AS aggregation_target
FROM
(SELECT toTimeZone(e.timestamp, 'UTC') AS timestamp, if(not(empty(e__override.distinct_id)), e__override.person_id, e.person_id) AS aggregation_target, e.uuid AS uuid, e.`$session_id` AS `$session_id`, e.`$window_id` AS `$window_id`, if(equals(e.event, '$pageview'), 1, 0) AS step_0, if(equals(e.event, 'insight analyzed'), 1, 0) AS step_1
FROM events AS e
@ -149,7 +149,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1), multiply(3, step_2)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(3, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(3, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -201,7 +201,7 @@
JOIN
(SELECT aggregation_target AS actor_id, matched_events_array[plus(step_reached, 1)] AS matching_events, (matched_events_array[1][1]).1 AS timestamp, nullIf((matched_events_array[3][1]).1, 0) AS final_timestamp, (matched_events_array[1][1]).1 AS first_timestamp, steps AS steps, final_timestamp, first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1), multiply(3, step_2)])))) AS events_array, arrayJoin(aggregate_funnel_array_v1(3, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple, af_tuple.1 AS step_reached, plus(af_tuple.1, 1) AS steps, af_tuple.2 AS breakdown, af_tuple.3 AS timings, af_tuple.4 AS matched_event_uuids_array_array, groupArray(tuple(timestamp, uuid, `$session_id`, `$window_id`)) AS user_events, mapFromArrays(arrayMap(x -> x.2, user_events), user_events) AS user_events_map, arrayMap(matched_event_uuids_array -> arrayMap(event_uuid -> user_events_map[event_uuid], arrayDistinct(matched_event_uuids_array)), matched_event_uuids_array_array) AS matched_events_array, aggregation_target AS aggregation_target
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1), multiply(3, step_2)])))) AS events_array, arrayJoin(aggregate_funnel_array_v2(3, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple, af_tuple.1 AS step_reached, plus(af_tuple.1, 1) AS steps, af_tuple.2 AS breakdown, af_tuple.3 AS timings, af_tuple.4 AS matched_event_uuids_array_array, groupArray(tuple(timestamp, uuid, `$session_id`, `$window_id`)) AS user_events, mapFromArrays(arrayMap(x -> x.2, user_events), user_events) AS user_events_map, arrayMap(matched_event_uuids_array -> arrayMap(event_uuid -> user_events_map[event_uuid], arrayDistinct(matched_event_uuids_array)), matched_event_uuids_array_array) AS matched_events_array, aggregation_target AS aggregation_target
FROM
(SELECT toTimeZone(e.timestamp, 'UTC') AS timestamp, if(not(empty(e__override.distinct_id)), e__override.person_id, e.person_id) AS aggregation_target, e.uuid AS uuid, e.`$session_id` AS `$session_id`, e.`$window_id` AS `$window_id`, if(equals(e.event, '$pageview'), 1, 0) AS step_0, if(equals(e.event, 'insight analyzed'), 1, 0) AS step_1, if(equals(e.event, 'insight updated'), 1, 0) AS step_2
FROM events AS e
@ -265,7 +265,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -319,7 +319,7 @@
FROM
(SELECT aggregation_target AS actor_id, matched_events_array[plus(step_reached, 1)] AS matching_events, (matched_events_array[1][1]).1 AS timestamp, nullIf((matched_events_array[2][1]).1, 0) AS final_timestamp, (matched_events_array[1][1]).1 AS first_timestamp, steps AS steps, final_timestamp, first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array, arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple, af_tuple.1 AS step_reached, plus(af_tuple.1, 1) AS steps, af_tuple.2 AS breakdown, af_tuple.3 AS timings, af_tuple.4 AS matched_event_uuids_array_array, groupArray(tuple(timestamp, uuid, `$session_id`, `$window_id`)) AS user_events, mapFromArrays(arrayMap(x -> x.2, user_events), user_events) AS user_events_map, arrayMap(matched_event_uuids_array -> arrayMap(event_uuid -> user_events_map[event_uuid], arrayDistinct(matched_event_uuids_array)), matched_event_uuids_array_array) AS matched_events_array, aggregation_target AS aggregation_target
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array, arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple, af_tuple.1 AS step_reached, plus(af_tuple.1, 1) AS steps, af_tuple.2 AS breakdown, af_tuple.3 AS timings, af_tuple.4 AS matched_event_uuids_array_array, groupArray(tuple(timestamp, uuid, `$session_id`, `$window_id`)) AS user_events, mapFromArrays(arrayMap(x -> x.2, user_events), user_events) AS user_events_map, arrayMap(matched_event_uuids_array -> arrayMap(event_uuid -> user_events_map[event_uuid], arrayDistinct(matched_event_uuids_array)), matched_event_uuids_array_array) AS matched_events_array, aggregation_target AS aggregation_target
FROM
(SELECT toTimeZone(e.timestamp, 'UTC') AS timestamp, if(not(empty(e__override.distinct_id)), e__override.person_id, e.person_id) AS aggregation_target, e.uuid AS uuid, e.`$session_id` AS `$session_id`, e.`$window_id` AS `$window_id`, if(equals(e.event, '$pageview'), 1, 0) AS step_0, if(equals(e.event, 'insight analyzed'), 1, 0) AS step_1
FROM events AS e
@ -375,8 +375,6 @@
# ---
# name: TestFunnelCorrelationsActorsUDF.test_strict_funnel_correlation_with_recordings
'''
<<<<<<< HEAD
=======
SELECT sum(step_1) AS step_1,
sum(step_2) AS step_2,
arrayMap(x -> if(isNaN(x), NULL, x), [avgArrayOrNull(step_1_conversion_times)])[1] AS step_1_average_conversion_time,
@ -430,132 +428,6 @@
allow_experimental_analyzer=1
'''
# ---
# name: TestFunnelCorrelationsActorsUDF.test_strict_funnel_correlation_with_recordings.1
'''
>>>>>>> origin/master
SELECT persons.id,
persons.id AS id,
source.matching_events AS matching_events
FROM
(SELECT funnel_actors.actor_id AS actor_id,
any(funnel_actors.matching_events) AS matching_events
FROM
(SELECT aggregation_target AS actor_id,
matched_events_array[plus(step_reached, 1)] AS matching_events,
(matched_events_array[1][1]).1 AS timestamp,
nullIf((matched_events_array[2][1]).1, 0) AS final_timestamp,
(matched_events_array[1][1]).1 AS first_timestamp,
steps AS steps,
final_timestamp,
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
<<<<<<< HEAD
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'strict', [[]], arrayFilter((x, x2) -> not(and(empty(x.4), empty(x2.4), ifNull(equals(x.3, x2.3), isNull(x.3)
and isNull(x2.3)), ifNull(greater(x.1, x2.1), 0))), events_array, arrayRotateRight(events_array, 1)))) AS af_tuple,
=======
arrayJoin(aggregate_funnel_array(2, 1209600, 'first_touch', 'strict', [[]], arrayFilter((x, x2) -> not(and(empty(x.4), empty(x2.4), ifNull(equals(x.3, x2.3), isNull(x.3)
and isNull(x2.3)), ifNull(greater(x.1, x2.1), 0))), events_array, arrayRotateRight(events_array, 1)))) AS af_tuple,
>>>>>>> origin/master
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
af_tuple.3 AS timings,
af_tuple.4 AS matched_event_uuids_array_array,
groupArray(tuple(timestamp, uuid, `$session_id`, `$window_id`)) AS user_events,
mapFromArrays(arrayMap(x -> x.2, user_events), user_events) AS user_events_map,
arrayMap(matched_event_uuids_array -> arrayMap(event_uuid -> user_events_map[event_uuid], arrayDistinct(matched_event_uuids_array)), matched_event_uuids_array_array) AS matched_events_array,
aggregation_target AS aggregation_target
FROM
(SELECT toTimeZone(e.timestamp, 'UTC') AS timestamp,
if(not(empty(e__override.distinct_id)), e__override.person_id, e.person_id) AS aggregation_target,
e.uuid AS uuid,
e.`$session_id` AS `$session_id`,
e.`$window_id` AS `$window_id`,
if(equals(e.event, '$pageview'), 1, 0) AS step_0,
if(equals(e.event, 'insight analyzed'), 1, 0) AS step_1
FROM events AS e
LEFT OUTER JOIN
(SELECT argMax(person_distinct_id_overrides.person_id, person_distinct_id_overrides.version) AS person_id,
person_distinct_id_overrides.distinct_id AS distinct_id
FROM person_distinct_id_overrides
WHERE equals(person_distinct_id_overrides.team_id, 2)
GROUP BY person_distinct_id_overrides.distinct_id
HAVING ifNull(equals(argMax(person_distinct_id_overrides.is_deleted, person_distinct_id_overrides.version), 0), 0) SETTINGS optimize_aggregation_in_order=1) AS e__override ON equals(e.distinct_id, e__override.distinct_id)
LEFT JOIN
(SELECT person.id AS id,
replaceRegexpAll(nullIf(nullIf(JSONExtractRaw(person.properties, 'foo'), ''), 'null'), '^"|"$', '') AS properties___foo
FROM person
WHERE and(equals(person.team_id, 2), ifNull(in(tuple(person.id, person.version),
(SELECT person.id AS id, max(person.version) AS version
FROM person
WHERE equals(person.team_id, 2)
GROUP BY person.id
HAVING and(ifNull(equals(argMax(person.is_deleted, person.version), 0), 0), ifNull(less(argMax(toTimeZone(person.created_at, 'UTC'), person.version), plus(now64(6, 'UTC'), toIntervalDay(1))), 0)))), 0)) SETTINGS optimize_aggregation_in_order=1) AS e__person ON equals(if(not(empty(e__override.distinct_id)), e__override.person_id, e.person_id), e__person.id)
WHERE and(equals(e.team_id, 2), and(greaterOrEquals(toTimeZone(e.timestamp, 'UTC'), toDateTime64('2021-01-01 00:00:00.000000', 6, 'UTC')), lessOrEquals(toTimeZone(e.timestamp, 'UTC'), toDateTime64('2021-01-08 23:59:59.999999', 6, 'UTC'))), ifNull(equals(e__person.properties___foo, 'bar'), 0)))
GROUP BY aggregation_target
HAVING ifNull(greaterOrEquals(step_reached, 0), 0))
WHERE ifNull(greaterOrEquals(step_reached, 0), 0)
ORDER BY aggregation_target ASC) AS funnel_actors
WHERE ifNull(equals(funnel_actors.steps, 2), 0)
GROUP BY funnel_actors.actor_id
ORDER BY funnel_actors.actor_id ASC) AS source
INNER JOIN
(SELECT person.id AS id
FROM person
WHERE and(equals(person.team_id, 2), in(id,
(SELECT source.actor_id AS actor_id
FROM
(SELECT funnel_actors.actor_id AS actor_id, any(funnel_actors.matching_events) AS matching_events
FROM
(SELECT aggregation_target AS actor_id, matched_events_array[plus(step_reached, 1)] AS matching_events, (matched_events_array[1][1]).1 AS timestamp, nullIf((matched_events_array[2][1]).1, 0) AS final_timestamp, (matched_events_array[1][1]).1 AS first_timestamp, steps AS steps, final_timestamp, first_timestamp
FROM
<<<<<<< HEAD
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array, arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'strict', [[]], arrayFilter((x, x2) -> not(and(empty(x.4), empty(x2.4), ifNull(equals(x.3, x2.3), isNull(x.3)
and isNull(x2.3)), ifNull(greater(x.1, x2.1), 0))), events_array, arrayRotateRight(events_array, 1)))) AS af_tuple, af_tuple.1 AS step_reached, plus(af_tuple.1, 1) AS steps, af_tuple.2 AS breakdown, af_tuple.3 AS timings, af_tuple.4 AS matched_event_uuids_array_array, groupArray(tuple(timestamp, uuid, `$session_id`, `$window_id`)) AS user_events, mapFromArrays(arrayMap(x -> x.2, user_events), user_events) AS user_events_map, arrayMap(matched_event_uuids_array -> arrayMap(event_uuid -> user_events_map[event_uuid], arrayDistinct(matched_event_uuids_array)), matched_event_uuids_array_array) AS matched_events_array, aggregation_target AS aggregation_target
=======
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array, arrayJoin(aggregate_funnel_array(2, 1209600, 'first_touch', 'strict', [[]], arrayFilter((x, x2) -> not(and(empty(x.4), empty(x2.4), ifNull(equals(x.3, x2.3), isNull(x.3)
and isNull(x2.3)), ifNull(greater(x.1, x2.1), 0))), events_array, arrayRotateRight(events_array, 1)))) AS af_tuple, af_tuple.1 AS step_reached, plus(af_tuple.1, 1) AS steps, af_tuple.2 AS breakdown, af_tuple.3 AS timings, af_tuple.4 AS matched_event_uuids_array_array, groupArray(tuple(timestamp, uuid, `$session_id`, `$window_id`)) AS user_events, mapFromArrays(arrayMap(x -> x.2, user_events), user_events) AS user_events_map, arrayMap(matched_event_uuids_array -> arrayMap(event_uuid -> user_events_map[event_uuid], arrayDistinct(matched_event_uuids_array)), matched_event_uuids_array_array) AS matched_events_array, aggregation_target AS aggregation_target
>>>>>>> origin/master
FROM
(SELECT toTimeZone(e.timestamp, 'UTC') AS timestamp, if(not(empty(e__override.distinct_id)), e__override.person_id, e.person_id) AS aggregation_target, e.uuid AS uuid, e.`$session_id` AS `$session_id`, e.`$window_id` AS `$window_id`, if(equals(e.event, '$pageview'), 1, 0) AS step_0, if(equals(e.event, 'insight analyzed'), 1, 0) AS step_1
FROM events AS e
LEFT OUTER JOIN
(SELECT argMax(person_distinct_id_overrides.person_id, person_distinct_id_overrides.version) AS person_id, person_distinct_id_overrides.distinct_id AS distinct_id
FROM person_distinct_id_overrides
WHERE equals(person_distinct_id_overrides.team_id, 2)
GROUP BY person_distinct_id_overrides.distinct_id
HAVING ifNull(equals(argMax(person_distinct_id_overrides.is_deleted, person_distinct_id_overrides.version), 0), 0) SETTINGS optimize_aggregation_in_order=1) AS e__override ON equals(e.distinct_id, e__override.distinct_id)
LEFT JOIN
(SELECT person.id AS id, replaceRegexpAll(nullIf(nullIf(JSONExtractRaw(person.properties, 'foo'), ''), 'null'), '^"|"$', '') AS properties___foo
FROM person
WHERE and(equals(person.team_id, 2), ifNull(in(tuple(person.id, person.version),
(SELECT person.id AS id, max(person.version) AS version
FROM person
WHERE equals(person.team_id, 2)
GROUP BY person.id
HAVING and(ifNull(equals(argMax(person.is_deleted, person.version), 0), 0), ifNull(less(argMax(toTimeZone(person.created_at, 'UTC'), person.version), plus(now64(6, 'UTC'), toIntervalDay(1))), 0)))), 0)) SETTINGS optimize_aggregation_in_order=1) AS e__person ON equals(if(not(empty(e__override.distinct_id)), e__override.person_id, e.person_id), e__person.id)
WHERE and(equals(e.team_id, 2), and(greaterOrEquals(toTimeZone(e.timestamp, 'UTC'), toDateTime64('2021-01-01 00:00:00.000000', 6, 'UTC')), lessOrEquals(toTimeZone(e.timestamp, 'UTC'), toDateTime64('2021-01-08 23:59:59.999999', 6, 'UTC'))), ifNull(equals(e__person.properties___foo, 'bar'), 0)))
GROUP BY aggregation_target
HAVING ifNull(greaterOrEquals(step_reached, 0), 0))
WHERE ifNull(greaterOrEquals(step_reached, 0), 0)
ORDER BY aggregation_target ASC) AS funnel_actors
WHERE ifNull(equals(funnel_actors.steps, 2), 0)
GROUP BY funnel_actors.actor_id
ORDER BY funnel_actors.actor_id ASC) AS source)))
GROUP BY person.id
HAVING and(ifNull(equals(argMax(person.is_deleted, person.version), 0), 0), ifNull(less(argMax(toTimeZone(person.created_at, 'UTC'), person.version), plus(now64(6, 'UTC'), toIntervalDay(1))), 0)) SETTINGS optimize_aggregation_in_order=1) AS persons ON equals(persons.id, source.actor_id)
ORDER BY persons.id ASC
LIMIT 101
OFFSET 0 SETTINGS readonly=2,
max_execution_time=60,
allow_experimental_object_type=1,
format_csv_allow_double_quotes=0,
max_ast_elements=4000000,
max_expanded_ast_elements=4000000,
max_bytes_before_external_group_by=0
'''
# ---
# name: TestFunnelCorrelationsActorsUDF.test_strict_funnel_correlation_with_recordings.1
'''
SELECT DISTINCT session_replay_events.session_id AS session_id
@ -589,13 +461,10 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
<<<<<<< HEAD
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'strict', [[]], arrayFilter((x, x2) -> not(and(empty(x.4), empty(x2.4), ifNull(equals(x.3, x2.3), isNull(x.3)
and isNull(x2.3)), ifNull(greater(x.1, x2.1), 0))), events_array, arrayRotateRight(events_array, 1)))) AS af_tuple,
=======
arrayJoin(aggregate_funnel_array(2, 1209600, 'first_touch', 'strict', [[]], arrayFilter((x, x2) -> not(and(empty(x.4), empty(x2.4), ifNull(equals(x.3, x2.3), isNull(x.3)
and isNull(x2.3)), ifNull(greater(x.1, x2.1), 0))), events_array, arrayRotateRight(events_array, 1)))) AS af_tuple,
>>>>>>> origin/master
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -649,13 +518,10 @@
FROM
(SELECT aggregation_target AS actor_id, matched_events_array[plus(step_reached, 1)] AS matching_events, (matched_events_array[1][1]).1 AS timestamp, nullIf((matched_events_array[2][1]).1, 0) AS final_timestamp, (matched_events_array[1][1]).1 AS first_timestamp, steps AS steps, final_timestamp, first_timestamp
FROM
<<<<<<< HEAD
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array, arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'strict', [[]], arrayFilter((x, x2) -> not(and(empty(x.4), empty(x2.4), ifNull(equals(x.3, x2.3), isNull(x.3)
and isNull(x2.3)), ifNull(greater(x.1, x2.1), 0))), events_array, arrayRotateRight(events_array, 1)))) AS af_tuple, af_tuple.1 AS step_reached, plus(af_tuple.1, 1) AS steps, af_tuple.2 AS breakdown, af_tuple.3 AS timings, af_tuple.4 AS matched_event_uuids_array_array, groupArray(tuple(timestamp, uuid, `$session_id`, `$window_id`)) AS user_events, mapFromArrays(arrayMap(x -> x.2, user_events), user_events) AS user_events_map, arrayMap(matched_event_uuids_array -> arrayMap(event_uuid -> user_events_map[event_uuid], arrayDistinct(matched_event_uuids_array)), matched_event_uuids_array_array) AS matched_events_array, aggregation_target AS aggregation_target
=======
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array, arrayJoin(aggregate_funnel_array(2, 1209600, 'first_touch', 'strict', [[]], arrayFilter((x, x2) -> not(and(empty(x.4), empty(x2.4), ifNull(equals(x.3, x2.3), isNull(x.3)
and isNull(x2.3)), ifNull(greater(x.1, x2.1), 0))), events_array, arrayRotateRight(events_array, 1)))) AS af_tuple, af_tuple.1 AS step_reached, plus(af_tuple.1, 1) AS steps, af_tuple.2 AS breakdown, af_tuple.3 AS timings, af_tuple.4 AS matched_event_uuids_array_array, groupArray(tuple(timestamp, uuid, `$session_id`, `$window_id`)) AS user_events, mapFromArrays(arrayMap(x -> x.2, user_events), user_events) AS user_events_map, arrayMap(matched_event_uuids_array -> arrayMap(event_uuid -> user_events_map[event_uuid], arrayDistinct(matched_event_uuids_array)), matched_event_uuids_array_array) AS matched_events_array, aggregation_target AS aggregation_target
>>>>>>> origin/master
FROM
(SELECT toTimeZone(e.timestamp, 'UTC') AS timestamp, if(not(empty(e__override.distinct_id)), e__override.person_id, e.person_id) AS aggregation_target, e.uuid AS uuid, e.`$session_id` AS `$session_id`, e.`$window_id` AS `$window_id`, if(equals(e.event, '$pageview'), 1, 0) AS step_0, if(equals(e.event, 'insight analyzed'), 1, 0) AS step_1
FROM events AS e

View File

@ -22,7 +22,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -70,7 +70,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -129,7 +129,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -190,7 +190,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -249,7 +249,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -303,7 +303,7 @@
FROM
(SELECT aggregation_target AS actor_id, matched_events_array[plus(step_reached, 1)] AS matching_events, (matched_events_array[1][1]).1 AS timestamp, nullIf((matched_events_array[2][1]).1, 0) AS final_timestamp, (matched_events_array[1][1]).1 AS first_timestamp, steps AS steps, final_timestamp, first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array, arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple, af_tuple.1 AS step_reached, plus(af_tuple.1, 1) AS steps, af_tuple.2 AS breakdown, af_tuple.3 AS timings, af_tuple.4 AS matched_event_uuids_array_array, groupArray(tuple(timestamp, uuid, `$session_id`, `$window_id`)) AS user_events, mapFromArrays(arrayMap(x -> x.2, user_events), user_events) AS user_events_map, arrayMap(matched_event_uuids_array -> arrayMap(event_uuid -> user_events_map[event_uuid], arrayDistinct(matched_event_uuids_array)), matched_event_uuids_array_array) AS matched_events_array, aggregation_target AS aggregation_target
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array, arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple, af_tuple.1 AS step_reached, plus(af_tuple.1, 1) AS steps, af_tuple.2 AS breakdown, af_tuple.3 AS timings, af_tuple.4 AS matched_event_uuids_array_array, groupArray(tuple(timestamp, uuid, `$session_id`, `$window_id`)) AS user_events, mapFromArrays(arrayMap(x -> x.2, user_events), user_events) AS user_events_map, arrayMap(matched_event_uuids_array -> arrayMap(event_uuid -> user_events_map[event_uuid], arrayDistinct(matched_event_uuids_array)), matched_event_uuids_array_array) AS matched_events_array, aggregation_target AS aggregation_target
FROM
(SELECT toTimeZone(e.timestamp, 'UTC') AS timestamp, if(not(empty(e__override.distinct_id)), e__override.person_id, e.person_id) AS aggregation_target, e.uuid AS uuid, e.`$session_id` AS `$session_id`, e.`$window_id` AS `$window_id`, if(equals(e.event, 'user signed up'), 1, 0) AS step_0, if(equals(e.event, 'paid'), 1, 0) AS step_1
FROM events AS e
@ -376,7 +376,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -430,7 +430,7 @@
FROM
(SELECT aggregation_target AS actor_id, matched_events_array[plus(step_reached, 1)] AS matching_events, (matched_events_array[1][1]).1 AS timestamp, nullIf((matched_events_array[2][1]).1, 0) AS final_timestamp, (matched_events_array[1][1]).1 AS first_timestamp, steps AS steps, final_timestamp, first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array, arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple, af_tuple.1 AS step_reached, plus(af_tuple.1, 1) AS steps, af_tuple.2 AS breakdown, af_tuple.3 AS timings, af_tuple.4 AS matched_event_uuids_array_array, groupArray(tuple(timestamp, uuid, `$session_id`, `$window_id`)) AS user_events, mapFromArrays(arrayMap(x -> x.2, user_events), user_events) AS user_events_map, arrayMap(matched_event_uuids_array -> arrayMap(event_uuid -> user_events_map[event_uuid], arrayDistinct(matched_event_uuids_array)), matched_event_uuids_array_array) AS matched_events_array, aggregation_target AS aggregation_target
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array, arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple, af_tuple.1 AS step_reached, plus(af_tuple.1, 1) AS steps, af_tuple.2 AS breakdown, af_tuple.3 AS timings, af_tuple.4 AS matched_event_uuids_array_array, groupArray(tuple(timestamp, uuid, `$session_id`, `$window_id`)) AS user_events, mapFromArrays(arrayMap(x -> x.2, user_events), user_events) AS user_events_map, arrayMap(matched_event_uuids_array -> arrayMap(event_uuid -> user_events_map[event_uuid], arrayDistinct(matched_event_uuids_array)), matched_event_uuids_array_array) AS matched_events_array, aggregation_target AS aggregation_target
FROM
(SELECT toTimeZone(e.timestamp, 'UTC') AS timestamp, if(not(empty(e__override.distinct_id)), e__override.person_id, e.person_id) AS aggregation_target, e.uuid AS uuid, e.`$session_id` AS `$session_id`, e.`$window_id` AS `$window_id`, if(equals(e.event, 'user signed up'), 1, 0) AS step_0, if(equals(e.event, 'paid'), 1, 0) AS step_1
FROM events AS e
@ -503,7 +503,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -557,7 +557,7 @@
FROM
(SELECT aggregation_target AS actor_id, matched_events_array[plus(step_reached, 1)] AS matching_events, (matched_events_array[1][1]).1 AS timestamp, nullIf((matched_events_array[2][1]).1, 0) AS final_timestamp, (matched_events_array[1][1]).1 AS first_timestamp, steps AS steps, final_timestamp, first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array, arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple, af_tuple.1 AS step_reached, plus(af_tuple.1, 1) AS steps, af_tuple.2 AS breakdown, af_tuple.3 AS timings, af_tuple.4 AS matched_event_uuids_array_array, groupArray(tuple(timestamp, uuid, `$session_id`, `$window_id`)) AS user_events, mapFromArrays(arrayMap(x -> x.2, user_events), user_events) AS user_events_map, arrayMap(matched_event_uuids_array -> arrayMap(event_uuid -> user_events_map[event_uuid], arrayDistinct(matched_event_uuids_array)), matched_event_uuids_array_array) AS matched_events_array, aggregation_target AS aggregation_target
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array, arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple, af_tuple.1 AS step_reached, plus(af_tuple.1, 1) AS steps, af_tuple.2 AS breakdown, af_tuple.3 AS timings, af_tuple.4 AS matched_event_uuids_array_array, groupArray(tuple(timestamp, uuid, `$session_id`, `$window_id`)) AS user_events, mapFromArrays(arrayMap(x -> x.2, user_events), user_events) AS user_events_map, arrayMap(matched_event_uuids_array -> arrayMap(event_uuid -> user_events_map[event_uuid], arrayDistinct(matched_event_uuids_array)), matched_event_uuids_array_array) AS matched_events_array, aggregation_target AS aggregation_target
FROM
(SELECT toTimeZone(e.timestamp, 'UTC') AS timestamp, if(not(empty(e__override.distinct_id)), e__override.person_id, e.person_id) AS aggregation_target, e.uuid AS uuid, e.`$session_id` AS `$session_id`, e.`$window_id` AS `$window_id`, if(equals(e.event, 'user signed up'), 1, 0) AS step_0, if(equals(e.event, 'paid'), 1, 0) AS step_1
FROM events AS e
@ -630,7 +630,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -684,7 +684,7 @@
FROM
(SELECT aggregation_target AS actor_id, matched_events_array[plus(step_reached, 1)] AS matching_events, (matched_events_array[1][1]).1 AS timestamp, nullIf((matched_events_array[2][1]).1, 0) AS final_timestamp, (matched_events_array[1][1]).1 AS first_timestamp, steps AS steps, final_timestamp, first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array, arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple, af_tuple.1 AS step_reached, plus(af_tuple.1, 1) AS steps, af_tuple.2 AS breakdown, af_tuple.3 AS timings, af_tuple.4 AS matched_event_uuids_array_array, groupArray(tuple(timestamp, uuid, `$session_id`, `$window_id`)) AS user_events, mapFromArrays(arrayMap(x -> x.2, user_events), user_events) AS user_events_map, arrayMap(matched_event_uuids_array -> arrayMap(event_uuid -> user_events_map[event_uuid], arrayDistinct(matched_event_uuids_array)), matched_event_uuids_array_array) AS matched_events_array, aggregation_target AS aggregation_target
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array, arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple, af_tuple.1 AS step_reached, plus(af_tuple.1, 1) AS steps, af_tuple.2 AS breakdown, af_tuple.3 AS timings, af_tuple.4 AS matched_event_uuids_array_array, groupArray(tuple(timestamp, uuid, `$session_id`, `$window_id`)) AS user_events, mapFromArrays(arrayMap(x -> x.2, user_events), user_events) AS user_events_map, arrayMap(matched_event_uuids_array -> arrayMap(event_uuid -> user_events_map[event_uuid], arrayDistinct(matched_event_uuids_array)), matched_event_uuids_array_array) AS matched_events_array, aggregation_target AS aggregation_target
FROM
(SELECT toTimeZone(e.timestamp, 'UTC') AS timestamp, if(not(empty(e__override.distinct_id)), e__override.person_id, e.person_id) AS aggregation_target, e.uuid AS uuid, e.`$session_id` AS `$session_id`, e.`$window_id` AS `$window_id`, if(equals(e.event, 'user signed up'), 1, 0) AS step_0, if(equals(e.event, 'paid'), 1, 0) AS step_1
FROM events AS e
@ -757,7 +757,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -818,7 +818,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -877,7 +877,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -931,7 +931,7 @@
FROM
(SELECT aggregation_target AS actor_id, matched_events_array[plus(step_reached, 1)] AS matching_events, (matched_events_array[1][1]).1 AS timestamp, nullIf((matched_events_array[2][1]).1, 0) AS final_timestamp, (matched_events_array[1][1]).1 AS first_timestamp, steps AS steps, final_timestamp, first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array, arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple, af_tuple.1 AS step_reached, plus(af_tuple.1, 1) AS steps, af_tuple.2 AS breakdown, af_tuple.3 AS timings, af_tuple.4 AS matched_event_uuids_array_array, groupArray(tuple(timestamp, uuid, `$session_id`, `$window_id`)) AS user_events, mapFromArrays(arrayMap(x -> x.2, user_events), user_events) AS user_events_map, arrayMap(matched_event_uuids_array -> arrayMap(event_uuid -> user_events_map[event_uuid], arrayDistinct(matched_event_uuids_array)), matched_event_uuids_array_array) AS matched_events_array, aggregation_target AS aggregation_target
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array, arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple, af_tuple.1 AS step_reached, plus(af_tuple.1, 1) AS steps, af_tuple.2 AS breakdown, af_tuple.3 AS timings, af_tuple.4 AS matched_event_uuids_array_array, groupArray(tuple(timestamp, uuid, `$session_id`, `$window_id`)) AS user_events, mapFromArrays(arrayMap(x -> x.2, user_events), user_events) AS user_events_map, arrayMap(matched_event_uuids_array -> arrayMap(event_uuid -> user_events_map[event_uuid], arrayDistinct(matched_event_uuids_array)), matched_event_uuids_array_array) AS matched_events_array, aggregation_target AS aggregation_target
FROM
(SELECT toTimeZone(e.timestamp, 'UTC') AS timestamp, if(not(empty(e__override.distinct_id)), e__override.person_id, e.person_id) AS aggregation_target, e.uuid AS uuid, e.`$session_id` AS `$session_id`, e.`$window_id` AS `$window_id`, if(equals(e.event, 'user signed up'), 1, 0) AS step_0, if(equals(e.event, 'paid'), 1, 0) AS step_1
FROM events AS e
@ -1004,7 +1004,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -1058,7 +1058,7 @@
FROM
(SELECT aggregation_target AS actor_id, matched_events_array[plus(step_reached, 1)] AS matching_events, (matched_events_array[1][1]).1 AS timestamp, nullIf((matched_events_array[2][1]).1, 0) AS final_timestamp, (matched_events_array[1][1]).1 AS first_timestamp, steps AS steps, final_timestamp, first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array, arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple, af_tuple.1 AS step_reached, plus(af_tuple.1, 1) AS steps, af_tuple.2 AS breakdown, af_tuple.3 AS timings, af_tuple.4 AS matched_event_uuids_array_array, groupArray(tuple(timestamp, uuid, `$session_id`, `$window_id`)) AS user_events, mapFromArrays(arrayMap(x -> x.2, user_events), user_events) AS user_events_map, arrayMap(matched_event_uuids_array -> arrayMap(event_uuid -> user_events_map[event_uuid], arrayDistinct(matched_event_uuids_array)), matched_event_uuids_array_array) AS matched_events_array, aggregation_target AS aggregation_target
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array, arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple, af_tuple.1 AS step_reached, plus(af_tuple.1, 1) AS steps, af_tuple.2 AS breakdown, af_tuple.3 AS timings, af_tuple.4 AS matched_event_uuids_array_array, groupArray(tuple(timestamp, uuid, `$session_id`, `$window_id`)) AS user_events, mapFromArrays(arrayMap(x -> x.2, user_events), user_events) AS user_events_map, arrayMap(matched_event_uuids_array -> arrayMap(event_uuid -> user_events_map[event_uuid], arrayDistinct(matched_event_uuids_array)), matched_event_uuids_array_array) AS matched_events_array, aggregation_target AS aggregation_target
FROM
(SELECT toTimeZone(e.timestamp, 'UTC') AS timestamp, if(not(empty(e__override.distinct_id)), e__override.person_id, e.person_id) AS aggregation_target, e.uuid AS uuid, e.`$session_id` AS `$session_id`, e.`$window_id` AS `$window_id`, if(equals(e.event, 'user signed up'), 1, 0) AS step_0, if(equals(e.event, 'paid'), 1, 0) AS step_1
FROM events AS e
@ -1131,7 +1131,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -1185,7 +1185,7 @@
FROM
(SELECT aggregation_target AS actor_id, matched_events_array[plus(step_reached, 1)] AS matching_events, (matched_events_array[1][1]).1 AS timestamp, nullIf((matched_events_array[2][1]).1, 0) AS final_timestamp, (matched_events_array[1][1]).1 AS first_timestamp, steps AS steps, final_timestamp, first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array, arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple, af_tuple.1 AS step_reached, plus(af_tuple.1, 1) AS steps, af_tuple.2 AS breakdown, af_tuple.3 AS timings, af_tuple.4 AS matched_event_uuids_array_array, groupArray(tuple(timestamp, uuid, `$session_id`, `$window_id`)) AS user_events, mapFromArrays(arrayMap(x -> x.2, user_events), user_events) AS user_events_map, arrayMap(matched_event_uuids_array -> arrayMap(event_uuid -> user_events_map[event_uuid], arrayDistinct(matched_event_uuids_array)), matched_event_uuids_array_array) AS matched_events_array, aggregation_target AS aggregation_target
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array, arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple, af_tuple.1 AS step_reached, plus(af_tuple.1, 1) AS steps, af_tuple.2 AS breakdown, af_tuple.3 AS timings, af_tuple.4 AS matched_event_uuids_array_array, groupArray(tuple(timestamp, uuid, `$session_id`, `$window_id`)) AS user_events, mapFromArrays(arrayMap(x -> x.2, user_events), user_events) AS user_events_map, arrayMap(matched_event_uuids_array -> arrayMap(event_uuid -> user_events_map[event_uuid], arrayDistinct(matched_event_uuids_array)), matched_event_uuids_array_array) AS matched_events_array, aggregation_target AS aggregation_target
FROM
(SELECT toTimeZone(e.timestamp, 'UTC') AS timestamp, if(not(empty(e__override.distinct_id)), e__override.person_id, e.person_id) AS aggregation_target, e.uuid AS uuid, e.`$session_id` AS `$session_id`, e.`$window_id` AS `$window_id`, if(equals(e.event, 'user signed up'), 1, 0) AS step_0, if(equals(e.event, 'paid'), 1, 0) AS step_1
FROM events AS e
@ -1258,7 +1258,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -1312,7 +1312,7 @@
FROM
(SELECT aggregation_target AS actor_id, matched_events_array[plus(step_reached, 1)] AS matching_events, (matched_events_array[1][1]).1 AS timestamp, nullIf((matched_events_array[2][1]).1, 0) AS final_timestamp, (matched_events_array[1][1]).1 AS first_timestamp, steps AS steps, final_timestamp, first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array, arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple, af_tuple.1 AS step_reached, plus(af_tuple.1, 1) AS steps, af_tuple.2 AS breakdown, af_tuple.3 AS timings, af_tuple.4 AS matched_event_uuids_array_array, groupArray(tuple(timestamp, uuid, `$session_id`, `$window_id`)) AS user_events, mapFromArrays(arrayMap(x -> x.2, user_events), user_events) AS user_events_map, arrayMap(matched_event_uuids_array -> arrayMap(event_uuid -> user_events_map[event_uuid], arrayDistinct(matched_event_uuids_array)), matched_event_uuids_array_array) AS matched_events_array, aggregation_target AS aggregation_target
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array, arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple, af_tuple.1 AS step_reached, plus(af_tuple.1, 1) AS steps, af_tuple.2 AS breakdown, af_tuple.3 AS timings, af_tuple.4 AS matched_event_uuids_array_array, groupArray(tuple(timestamp, uuid, `$session_id`, `$window_id`)) AS user_events, mapFromArrays(arrayMap(x -> x.2, user_events), user_events) AS user_events_map, arrayMap(matched_event_uuids_array -> arrayMap(event_uuid -> user_events_map[event_uuid], arrayDistinct(matched_event_uuids_array)), matched_event_uuids_array_array) AS matched_events_array, aggregation_target AS aggregation_target
FROM
(SELECT toTimeZone(e.timestamp, 'UTC') AS timestamp, if(not(empty(e__override.distinct_id)), e__override.person_id, e.person_id) AS aggregation_target, e.uuid AS uuid, e.`$session_id` AS `$session_id`, e.`$window_id` AS `$window_id`, if(equals(e.event, 'user signed up'), 1, 0) AS step_0, if(equals(e.event, 'paid'), 1, 0) AS step_1
FROM events AS e
@ -1387,7 +1387,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -1429,7 +1429,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -1483,7 +1483,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -1525,7 +1525,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -1574,7 +1574,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -1615,7 +1615,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -1666,7 +1666,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -1729,7 +1729,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -1792,7 +1792,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -1855,7 +1855,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -1916,7 +1916,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -1965,7 +1965,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -2024,7 +2024,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -2087,7 +2087,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -2148,7 +2148,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -2189,7 +2189,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -2240,7 +2240,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -2303,7 +2303,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -2366,7 +2366,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -2429,7 +2429,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -2490,7 +2490,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -2539,7 +2539,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -2598,7 +2598,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -2661,7 +2661,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -2725,7 +2725,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -2778,7 +2778,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -2828,7 +2828,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -2898,7 +2898,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -2968,7 +2968,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -3038,7 +3038,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -3110,7 +3110,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -3163,7 +3163,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -3215,7 +3215,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -3268,7 +3268,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -3318,7 +3318,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -3388,7 +3388,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -3458,7 +3458,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -3528,7 +3528,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -3600,7 +3600,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -3653,7 +3653,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -3705,7 +3705,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -3758,7 +3758,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -3808,7 +3808,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -3878,7 +3878,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -3948,7 +3948,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -4018,7 +4018,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -4090,7 +4090,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -4143,7 +4143,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -4195,7 +4195,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -4248,7 +4248,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -4298,7 +4298,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -4368,7 +4368,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -4438,7 +4438,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -4508,7 +4508,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -4580,7 +4580,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -4633,7 +4633,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -4685,7 +4685,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -4738,7 +4738,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -4788,7 +4788,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -4858,7 +4858,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -4928,7 +4928,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -4998,7 +4998,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -5070,7 +5070,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -5123,7 +5123,7 @@
first_timestamp
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,

View File

@ -9,7 +9,7 @@
matched_events_array[1] AS matching_events
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1), multiply(3, step_2)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(3, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(3, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -83,7 +83,7 @@
matched_events_array[2] AS matching_events
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1), multiply(3, step_2)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(3, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(3, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -157,7 +157,7 @@
matched_events_array[2] AS matching_events
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1), multiply(3, step_2)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(3, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(3, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,

View File

@ -9,7 +9,7 @@
matched_events_array[1] AS matching_events
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1), multiply(3, step_2)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(3, 1209600, 'first_touch', 'strict', [[]], arrayFilter((x, x2) -> not(and(empty(x.4), empty(x2.4), ifNull(equals(x.3, x2.3), isNull(x.3)
arrayJoin(aggregate_funnel_array_v2(3, 1209600, 'first_touch', 'strict', [[]], arrayFilter((x, x2) -> not(and(empty(x.4), empty(x2.4), ifNull(equals(x.3, x2.3), isNull(x.3)
and isNull(x2.3)), ifNull(greater(x.1, x2.1), 0))), events_array, arrayRotateRight(events_array, 1)))) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
@ -84,7 +84,7 @@
matched_events_array[2] AS matching_events
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1), multiply(3, step_2)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(3, 1209600, 'first_touch', 'strict', [[]], arrayFilter((x, x2) -> not(and(empty(x.4), empty(x2.4), ifNull(equals(x.3, x2.3), isNull(x.3)
arrayJoin(aggregate_funnel_array_v2(3, 1209600, 'first_touch', 'strict', [[]], arrayFilter((x, x2) -> not(and(empty(x.4), empty(x2.4), ifNull(equals(x.3, x2.3), isNull(x.3)
and isNull(x2.3)), ifNull(greater(x.1, x2.1), 0))), events_array, arrayRotateRight(events_array, 1)))) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
@ -159,7 +159,7 @@
matched_events_array[2] AS matching_events
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1), multiply(3, step_2)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(3, 1209600, 'first_touch', 'strict', [[]], arrayFilter((x, x2) -> not(and(empty(x.4), empty(x2.4), ifNull(equals(x.3, x2.3), isNull(x.3)
arrayJoin(aggregate_funnel_array_v2(3, 1209600, 'first_touch', 'strict', [[]], arrayFilter((x, x2) -> not(and(empty(x.4), empty(x2.4), ifNull(equals(x.3, x2.3), isNull(x.3)
and isNull(x2.3)), ifNull(greater(x.1, x2.1), 0))), events_array, arrayRotateRight(events_array, 1)))) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,

View File

@ -15,7 +15,7 @@
if(ifNull(less(row_number, 25), 0), breakdown, ['Other']) AS final_prop
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, prop, arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'strict', groupUniqArray(prop), arrayFilter((x, x2) -> not(and(empty(x.4), empty(x2.4), ifNull(equals(x.3, x2.3), isNull(x.3)
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'strict', groupUniqArray(prop), arrayFilter((x, x2) -> not(and(empty(x.4), empty(x2.4), ifNull(equals(x.3, x2.3), isNull(x.3)
and isNull(x2.3)), ifNull(greater(x.1, x2.1), 0))), events_array, arrayRotateRight(events_array, 1)))) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
@ -85,7 +85,7 @@
if(ifNull(less(row_number, 25), 0), breakdown, ['Other']) AS final_prop
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, prop, arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'step_1', 'strict', groupUniqArray(prop), arrayFilter((x, x2) -> not(and(empty(x.4), empty(x2.4), ifNull(equals(x.3, x2.3), isNull(x.3)
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'step_1', 'strict', groupUniqArray(prop), arrayFilter((x, x2) -> not(and(empty(x.4), empty(x2.4), ifNull(equals(x.3, x2.3), isNull(x.3)
and isNull(x2.3)), ifNull(greater(x.1, x2.1), 0))), events_array, arrayRotateRight(events_array, 1)))) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
@ -162,7 +162,7 @@
if(ifNull(less(row_number, 25), 0), breakdown, ['Other']) AS final_prop
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, prop, arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'strict', groupUniqArray(prop), arrayFilter((x, x2) -> not(and(empty(x.4), empty(x2.4), ifNull(equals(x.3, x2.3), isNull(x.3)
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'strict', groupUniqArray(prop), arrayFilter((x, x2) -> not(and(empty(x.4), empty(x2.4), ifNull(equals(x.3, x2.3), isNull(x.3)
and isNull(x2.3)), ifNull(greater(x.1, x2.1), 0))), events_array, arrayRotateRight(events_array, 1)))) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
@ -237,7 +237,7 @@
if(ifNull(less(row_number, 25), 0), breakdown, 'Other') AS final_prop
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, prop, arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1), multiply(3, step_2)])))) AS events_array,
arrayJoin(aggregate_funnel_v1(3, 1209600, 'first_touch', 'strict', groupUniqArray(prop), arrayFilter((x, x2) -> not(and(empty(x.4), empty(x2.4), ifNull(equals(x.3, x2.3), isNull(x.3)
arrayJoin(aggregate_funnel_v2(3, 1209600, 'first_touch', 'strict', groupUniqArray(prop), arrayFilter((x, x2) -> not(and(empty(x.4), empty(x2.4), ifNull(equals(x.3, x2.3), isNull(x.3)
and isNull(x2.3)), ifNull(greater(x.1, x2.1), 0))), events_array, arrayRotateRight(events_array, 1)))) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
@ -315,7 +315,7 @@
if(ifNull(less(row_number, 25), 0), breakdown, 'Other') AS final_prop
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, prop, arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1), multiply(3, step_2)])))) AS events_array,
arrayJoin(aggregate_funnel_v1(3, 1209600, 'first_touch', 'strict', groupUniqArray(prop), arrayFilter((x, x2) -> not(and(empty(x.4), empty(x2.4), ifNull(equals(x.3, x2.3), isNull(x.3)
arrayJoin(aggregate_funnel_v2(3, 1209600, 'first_touch', 'strict', groupUniqArray(prop), arrayFilter((x, x2) -> not(and(empty(x.4), empty(x2.4), ifNull(equals(x.3, x2.3), isNull(x.3)
and isNull(x2.3)), ifNull(greater(x.1, x2.1), 0))), events_array, arrayRotateRight(events_array, 1)))) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
@ -393,7 +393,7 @@
if(ifNull(less(row_number, 25), 0), breakdown, 'Other') AS final_prop
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, prop, arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1), multiply(3, step_2)])))) AS events_array,
arrayJoin(aggregate_funnel_v1(3, 1209600, 'first_touch', 'strict', groupUniqArray(prop), arrayFilter((x, x2) -> not(and(empty(x.4), empty(x2.4), ifNull(equals(x.3, x2.3), isNull(x.3)
arrayJoin(aggregate_funnel_v2(3, 1209600, 'first_touch', 'strict', groupUniqArray(prop), arrayFilter((x, x2) -> not(and(empty(x.4), empty(x2.4), ifNull(equals(x.3, x2.3), isNull(x.3)
and isNull(x2.3)), ifNull(greater(x.1, x2.1), 0))), events_array, arrayRotateRight(events_array, 1)))) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,

View File

@ -0,0 +1,520 @@
# serializer version: 1
# name: TestFunnelTrendsActors.test_funnel_trend_persons_returns_recordings
'''
SELECT persons.id,
persons.id AS id,
source.matching_events AS matching_events
FROM
(SELECT aggregation_target AS actor_id,
step_1_matching_events AS matching_events
FROM
(SELECT aggregation_target AS aggregation_target,
toStartOfDay(timestamp) AS entrance_period_start,
max(steps) AS steps_completed,
groupArray(10)(step_0_matching_event) AS step_0_matching_events,
groupArray(10)(step_1_matching_event) AS step_1_matching_events,
groupArray(10)(step_2_matching_event) AS step_2_matching_events,
groupArray(10)(final_matching_event) AS final_matching_events
FROM
(SELECT aggregation_target AS aggregation_target,
timestamp AS timestamp,
step_0 AS step_0,
latest_0 AS latest_0,
uuid_0 AS uuid_0,
`$session_id_0` AS `$session_id_0`,
`$window_id_0` AS `$window_id_0`,
step_1 AS step_1,
latest_1 AS latest_1,
uuid_1 AS uuid_1,
`$session_id_1` AS `$session_id_1`,
`$window_id_1` AS `$window_id_1`,
step_2 AS step_2,
latest_2 AS latest_2,
uuid_2 AS uuid_2,
`$session_id_2` AS `$session_id_2`,
`$window_id_2` AS `$window_id_2`,
if(and(ifNull(lessOrEquals(latest_0, latest_1), 0), ifNull(lessOrEquals(latest_1, plus(toTimeZone(latest_0, 'UTC'), toIntervalDay(14))), 0), ifNull(lessOrEquals(latest_1, latest_2), 0), ifNull(lessOrEquals(latest_2, plus(toTimeZone(latest_0, 'UTC'), toIntervalDay(14))), 0)), 3, if(and(ifNull(lessOrEquals(latest_0, latest_1), 0), ifNull(lessOrEquals(latest_1, plus(toTimeZone(latest_0, 'UTC'), toIntervalDay(14))), 0)), 2, 1)) AS steps,
if(and(isNotNull(latest_1), ifNull(lessOrEquals(latest_1, plus(toTimeZone(latest_0, 'UTC'), toIntervalDay(14))), 0)), dateDiff('second', latest_0, latest_1), NULL) AS step_1_conversion_time,
if(and(isNotNull(latest_2), ifNull(lessOrEquals(latest_2, plus(toTimeZone(latest_1, 'UTC'), toIntervalDay(14))), 0)), dateDiff('second', latest_1, latest_2), NULL) AS step_2_conversion_time,
tuple(latest_0, uuid_0, `$session_id_0`, `$window_id_0`) AS step_0_matching_event,
tuple(latest_1, uuid_1, `$session_id_1`, `$window_id_1`) AS step_1_matching_event,
tuple(latest_2, uuid_2, `$session_id_2`, `$window_id_2`) AS step_2_matching_event,
if(isNull(latest_0), tuple(NULL, NULL, NULL, NULL), if(isNull(latest_1), step_0_matching_event, if(isNull(latest_2), step_1_matching_event, step_2_matching_event))) AS final_matching_event
FROM
(SELECT aggregation_target AS aggregation_target,
timestamp AS timestamp,
step_0 AS step_0,
latest_0 AS latest_0,
uuid_0 AS uuid_0,
`$session_id_0` AS `$session_id_0`,
`$window_id_0` AS `$window_id_0`,
step_1 AS step_1,
latest_1 AS latest_1,
uuid_1 AS uuid_1,
`$session_id_1` AS `$session_id_1`,
`$window_id_1` AS `$window_id_1`,
step_2 AS step_2,
min(latest_2) OVER (PARTITION BY aggregation_target
ORDER BY timestamp DESC ROWS BETWEEN UNBOUNDED PRECEDING AND 0 PRECEDING) AS latest_2,
last_value(uuid_2) OVER (PARTITION BY aggregation_target
ORDER BY timestamp DESC ROWS BETWEEN UNBOUNDED PRECEDING AND 0 PRECEDING) AS uuid_2,
last_value(`$session_id_2`) OVER (PARTITION BY aggregation_target
ORDER BY timestamp DESC ROWS BETWEEN UNBOUNDED PRECEDING AND 0 PRECEDING) AS `$session_id_2`,
last_value(`$window_id_2`) OVER (PARTITION BY aggregation_target
ORDER BY timestamp DESC ROWS BETWEEN UNBOUNDED PRECEDING AND 0 PRECEDING) AS `$window_id_2`
FROM
(SELECT aggregation_target AS aggregation_target,
timestamp AS timestamp,
step_0 AS step_0,
latest_0 AS latest_0,
uuid_0 AS uuid_0,
`$session_id_0` AS `$session_id_0`,
`$window_id_0` AS `$window_id_0`,
step_1 AS step_1,
latest_1 AS latest_1,
uuid_1 AS uuid_1,
`$session_id_1` AS `$session_id_1`,
`$window_id_1` AS `$window_id_1`,
step_2 AS step_2,
if(ifNull(less(latest_2, latest_1), 0), NULL, latest_2) AS latest_2,
if(ifNull(less(latest_2, latest_1), 0), NULL, uuid_2) AS uuid_2,
if(ifNull(less(latest_2, latest_1), 0), NULL, `$session_id_2`) AS `$session_id_2`,
if(ifNull(less(latest_2, latest_1), 0), NULL, `$window_id_2`) AS `$window_id_2`
FROM
(SELECT aggregation_target AS aggregation_target,
timestamp AS timestamp,
step_0 AS step_0,
latest_0 AS latest_0,
uuid_0 AS uuid_0,
`$session_id_0` AS `$session_id_0`,
`$window_id_0` AS `$window_id_0`,
step_1 AS step_1,
min(latest_1) OVER (PARTITION BY aggregation_target
ORDER BY timestamp DESC ROWS BETWEEN UNBOUNDED PRECEDING AND 0 PRECEDING) AS latest_1,
last_value(uuid_1) OVER (PARTITION BY aggregation_target
ORDER BY timestamp DESC ROWS BETWEEN UNBOUNDED PRECEDING AND 0 PRECEDING) AS uuid_1,
last_value(`$session_id_1`) OVER (PARTITION BY aggregation_target
ORDER BY timestamp DESC ROWS BETWEEN UNBOUNDED PRECEDING AND 0 PRECEDING) AS `$session_id_1`,
last_value(`$window_id_1`) OVER (PARTITION BY aggregation_target
ORDER BY timestamp DESC ROWS BETWEEN UNBOUNDED PRECEDING AND 0 PRECEDING) AS `$window_id_1`,
step_2 AS step_2,
min(latest_2) OVER (PARTITION BY aggregation_target
ORDER BY timestamp DESC ROWS BETWEEN UNBOUNDED PRECEDING AND 0 PRECEDING) AS latest_2,
last_value(uuid_2) OVER (PARTITION BY aggregation_target
ORDER BY timestamp DESC ROWS BETWEEN UNBOUNDED PRECEDING AND 0 PRECEDING) AS uuid_2,
last_value(`$session_id_2`) OVER (PARTITION BY aggregation_target
ORDER BY timestamp DESC ROWS BETWEEN UNBOUNDED PRECEDING AND 0 PRECEDING) AS `$session_id_2`,
last_value(`$window_id_2`) OVER (PARTITION BY aggregation_target
ORDER BY timestamp DESC ROWS BETWEEN UNBOUNDED PRECEDING AND 0 PRECEDING) AS `$window_id_2`
FROM
(SELECT toTimeZone(e.timestamp, 'UTC') AS timestamp,
if(not(empty(e__override.distinct_id)), e__override.person_id, e.person_id) AS aggregation_target,
e.uuid AS uuid,
if(equals(e.event, 'step one'), 1, 0) AS step_0,
if(ifNull(equals(step_0, 1), 0), timestamp, NULL) AS latest_0,
if(ifNull(equals(step_0, 1), 0), uuid, NULL) AS uuid_0,
if(ifNull(equals(step_0, 1), 0), e.`$session_id`, NULL) AS `$session_id_0`,
if(ifNull(equals(step_0, 1), 0), e.`$window_id`, NULL) AS `$window_id_0`,
if(equals(e.event, 'step two'), 1, 0) AS step_1,
if(ifNull(equals(step_1, 1), 0), timestamp, NULL) AS latest_1,
if(ifNull(equals(step_1, 1), 0), uuid, NULL) AS uuid_1,
if(ifNull(equals(step_1, 1), 0), e.`$session_id`, NULL) AS `$session_id_1`,
if(ifNull(equals(step_1, 1), 0), e.`$window_id`, NULL) AS `$window_id_1`,
if(equals(e.event, 'step three'), 1, 0) AS step_2,
if(ifNull(equals(step_2, 1), 0), timestamp, NULL) AS latest_2,
if(ifNull(equals(step_2, 1), 0), uuid, NULL) AS uuid_2,
if(ifNull(equals(step_2, 1), 0), e.`$session_id`, NULL) AS `$session_id_2`,
if(ifNull(equals(step_2, 1), 0), e.`$window_id`, NULL) AS `$window_id_2`
FROM events AS e
LEFT OUTER JOIN
(SELECT argMax(person_distinct_id_overrides.person_id, person_distinct_id_overrides.version) AS person_id,
person_distinct_id_overrides.distinct_id AS distinct_id
FROM person_distinct_id_overrides
WHERE equals(person_distinct_id_overrides.team_id, 2)
GROUP BY person_distinct_id_overrides.distinct_id
HAVING ifNull(equals(argMax(person_distinct_id_overrides.is_deleted, person_distinct_id_overrides.version), 0), 0) SETTINGS optimize_aggregation_in_order=1) AS e__override ON equals(e.distinct_id, e__override.distinct_id)
WHERE and(equals(e.team_id, 2), and(and(greaterOrEquals(toTimeZone(e.timestamp, 'UTC'), toDateTime64('2021-05-01 00:00:00.000000', 6, 'UTC')), lessOrEquals(toTimeZone(e.timestamp, 'UTC'), toDateTime64('2021-05-07 23:59:59.999999', 6, 'UTC'))), in(e.event, tuple('step one', 'step three', 'step two'))), or(ifNull(equals(step_0, 1), 0), ifNull(equals(step_1, 1), 0), ifNull(equals(step_2, 1), 0)))))))
WHERE ifNull(equals(step_0, 1), 0))
WHERE ifNull(equals(entrance_period_start, toDateTime64('2021-05-01 00:00:00.000000', 6, 'UTC')), 0)
GROUP BY aggregation_target,
entrance_period_start)
WHERE ifNull(greaterOrEquals(steps_completed, 2), 0)
ORDER BY aggregation_target ASC) AS source
INNER JOIN
(SELECT person.id AS id
FROM person
WHERE equals(person.team_id, 2)
GROUP BY person.id
HAVING and(ifNull(equals(argMax(person.is_deleted, person.version), 0), 0), ifNull(less(argMax(toTimeZone(person.created_at, 'UTC'), person.version), plus(now64(6, 'UTC'), toIntervalDay(1))), 0)) SETTINGS optimize_aggregation_in_order=1) AS persons ON equals(persons.id, source.actor_id)
ORDER BY persons.id ASC
LIMIT 101
OFFSET 0 SETTINGS readonly=2,
max_execution_time=60,
allow_experimental_object_type=1,
format_csv_allow_double_quotes=0,
max_ast_elements=4000000,
max_expanded_ast_elements=4000000,
max_bytes_before_external_group_by=0,
allow_experimental_analyzer=1
'''
# ---
# name: TestFunnelTrendsActors.test_funnel_trend_persons_returns_recordings.1
'''
SELECT DISTINCT session_replay_events.session_id AS session_id
FROM session_replay_events
WHERE and(equals(session_replay_events.team_id, 2), ifNull(greaterOrEquals(toTimeZone(session_replay_events.min_first_timestamp, 'UTC'), minus(toDateTime64('2021-05-01 00:00:00.000000', 6, 'UTC'), toIntervalDay(21))), 0), in(session_replay_events.session_id, ['s1b']))
LIMIT 100 SETTINGS readonly=2,
max_execution_time=60,
allow_experimental_object_type=1,
format_csv_allow_double_quotes=0,
max_ast_elements=4000000,
max_expanded_ast_elements=4000000,
max_bytes_before_external_group_by=0
'''
# ---
# name: TestFunnelTrendsActors.test_funnel_trend_persons_with_drop_off
'''
SELECT persons.id,
persons.id AS id,
source.matching_events AS matching_events
FROM
(SELECT aggregation_target AS actor_id,
final_matching_events AS matching_events
FROM
(SELECT aggregation_target AS aggregation_target,
toStartOfDay(timestamp) AS entrance_period_start,
max(steps) AS steps_completed,
groupArray(10)(step_0_matching_event) AS step_0_matching_events,
groupArray(10)(step_1_matching_event) AS step_1_matching_events,
groupArray(10)(step_2_matching_event) AS step_2_matching_events,
groupArray(10)(final_matching_event) AS final_matching_events
FROM
(SELECT aggregation_target AS aggregation_target,
timestamp AS timestamp,
step_0 AS step_0,
latest_0 AS latest_0,
uuid_0 AS uuid_0,
`$session_id_0` AS `$session_id_0`,
`$window_id_0` AS `$window_id_0`,
step_1 AS step_1,
latest_1 AS latest_1,
uuid_1 AS uuid_1,
`$session_id_1` AS `$session_id_1`,
`$window_id_1` AS `$window_id_1`,
step_2 AS step_2,
latest_2 AS latest_2,
uuid_2 AS uuid_2,
`$session_id_2` AS `$session_id_2`,
`$window_id_2` AS `$window_id_2`,
if(and(ifNull(lessOrEquals(latest_0, latest_1), 0), ifNull(lessOrEquals(latest_1, plus(toTimeZone(latest_0, 'UTC'), toIntervalDay(14))), 0), ifNull(lessOrEquals(latest_1, latest_2), 0), ifNull(lessOrEquals(latest_2, plus(toTimeZone(latest_0, 'UTC'), toIntervalDay(14))), 0)), 3, if(and(ifNull(lessOrEquals(latest_0, latest_1), 0), ifNull(lessOrEquals(latest_1, plus(toTimeZone(latest_0, 'UTC'), toIntervalDay(14))), 0)), 2, 1)) AS steps,
if(and(isNotNull(latest_1), ifNull(lessOrEquals(latest_1, plus(toTimeZone(latest_0, 'UTC'), toIntervalDay(14))), 0)), dateDiff('second', latest_0, latest_1), NULL) AS step_1_conversion_time,
if(and(isNotNull(latest_2), ifNull(lessOrEquals(latest_2, plus(toTimeZone(latest_1, 'UTC'), toIntervalDay(14))), 0)), dateDiff('second', latest_1, latest_2), NULL) AS step_2_conversion_time,
tuple(latest_0, uuid_0, `$session_id_0`, `$window_id_0`) AS step_0_matching_event,
tuple(latest_1, uuid_1, `$session_id_1`, `$window_id_1`) AS step_1_matching_event,
tuple(latest_2, uuid_2, `$session_id_2`, `$window_id_2`) AS step_2_matching_event,
if(isNull(latest_0), tuple(NULL, NULL, NULL, NULL), if(isNull(latest_1), step_0_matching_event, if(isNull(latest_2), step_1_matching_event, step_2_matching_event))) AS final_matching_event
FROM
(SELECT aggregation_target AS aggregation_target,
timestamp AS timestamp,
step_0 AS step_0,
latest_0 AS latest_0,
uuid_0 AS uuid_0,
`$session_id_0` AS `$session_id_0`,
`$window_id_0` AS `$window_id_0`,
step_1 AS step_1,
latest_1 AS latest_1,
uuid_1 AS uuid_1,
`$session_id_1` AS `$session_id_1`,
`$window_id_1` AS `$window_id_1`,
step_2 AS step_2,
min(latest_2) OVER (PARTITION BY aggregation_target
ORDER BY timestamp DESC ROWS BETWEEN UNBOUNDED PRECEDING AND 0 PRECEDING) AS latest_2,
last_value(uuid_2) OVER (PARTITION BY aggregation_target
ORDER BY timestamp DESC ROWS BETWEEN UNBOUNDED PRECEDING AND 0 PRECEDING) AS uuid_2,
last_value(`$session_id_2`) OVER (PARTITION BY aggregation_target
ORDER BY timestamp DESC ROWS BETWEEN UNBOUNDED PRECEDING AND 0 PRECEDING) AS `$session_id_2`,
last_value(`$window_id_2`) OVER (PARTITION BY aggregation_target
ORDER BY timestamp DESC ROWS BETWEEN UNBOUNDED PRECEDING AND 0 PRECEDING) AS `$window_id_2`
FROM
(SELECT aggregation_target AS aggregation_target,
timestamp AS timestamp,
step_0 AS step_0,
latest_0 AS latest_0,
uuid_0 AS uuid_0,
`$session_id_0` AS `$session_id_0`,
`$window_id_0` AS `$window_id_0`,
step_1 AS step_1,
latest_1 AS latest_1,
uuid_1 AS uuid_1,
`$session_id_1` AS `$session_id_1`,
`$window_id_1` AS `$window_id_1`,
step_2 AS step_2,
if(ifNull(less(latest_2, latest_1), 0), NULL, latest_2) AS latest_2,
if(ifNull(less(latest_2, latest_1), 0), NULL, uuid_2) AS uuid_2,
if(ifNull(less(latest_2, latest_1), 0), NULL, `$session_id_2`) AS `$session_id_2`,
if(ifNull(less(latest_2, latest_1), 0), NULL, `$window_id_2`) AS `$window_id_2`
FROM
(SELECT aggregation_target AS aggregation_target,
timestamp AS timestamp,
step_0 AS step_0,
latest_0 AS latest_0,
uuid_0 AS uuid_0,
`$session_id_0` AS `$session_id_0`,
`$window_id_0` AS `$window_id_0`,
step_1 AS step_1,
min(latest_1) OVER (PARTITION BY aggregation_target
ORDER BY timestamp DESC ROWS BETWEEN UNBOUNDED PRECEDING AND 0 PRECEDING) AS latest_1,
last_value(uuid_1) OVER (PARTITION BY aggregation_target
ORDER BY timestamp DESC ROWS BETWEEN UNBOUNDED PRECEDING AND 0 PRECEDING) AS uuid_1,
last_value(`$session_id_1`) OVER (PARTITION BY aggregation_target
ORDER BY timestamp DESC ROWS BETWEEN UNBOUNDED PRECEDING AND 0 PRECEDING) AS `$session_id_1`,
last_value(`$window_id_1`) OVER (PARTITION BY aggregation_target
ORDER BY timestamp DESC ROWS BETWEEN UNBOUNDED PRECEDING AND 0 PRECEDING) AS `$window_id_1`,
step_2 AS step_2,
min(latest_2) OVER (PARTITION BY aggregation_target
ORDER BY timestamp DESC ROWS BETWEEN UNBOUNDED PRECEDING AND 0 PRECEDING) AS latest_2,
last_value(uuid_2) OVER (PARTITION BY aggregation_target
ORDER BY timestamp DESC ROWS BETWEEN UNBOUNDED PRECEDING AND 0 PRECEDING) AS uuid_2,
last_value(`$session_id_2`) OVER (PARTITION BY aggregation_target
ORDER BY timestamp DESC ROWS BETWEEN UNBOUNDED PRECEDING AND 0 PRECEDING) AS `$session_id_2`,
last_value(`$window_id_2`) OVER (PARTITION BY aggregation_target
ORDER BY timestamp DESC ROWS BETWEEN UNBOUNDED PRECEDING AND 0 PRECEDING) AS `$window_id_2`
FROM
(SELECT toTimeZone(e.timestamp, 'UTC') AS timestamp,
if(not(empty(e__override.distinct_id)), e__override.person_id, e.person_id) AS aggregation_target,
e.uuid AS uuid,
if(equals(e.event, 'step one'), 1, 0) AS step_0,
if(ifNull(equals(step_0, 1), 0), timestamp, NULL) AS latest_0,
if(ifNull(equals(step_0, 1), 0), uuid, NULL) AS uuid_0,
if(ifNull(equals(step_0, 1), 0), e.`$session_id`, NULL) AS `$session_id_0`,
if(ifNull(equals(step_0, 1), 0), e.`$window_id`, NULL) AS `$window_id_0`,
if(equals(e.event, 'step two'), 1, 0) AS step_1,
if(ifNull(equals(step_1, 1), 0), timestamp, NULL) AS latest_1,
if(ifNull(equals(step_1, 1), 0), uuid, NULL) AS uuid_1,
if(ifNull(equals(step_1, 1), 0), e.`$session_id`, NULL) AS `$session_id_1`,
if(ifNull(equals(step_1, 1), 0), e.`$window_id`, NULL) AS `$window_id_1`,
if(equals(e.event, 'step three'), 1, 0) AS step_2,
if(ifNull(equals(step_2, 1), 0), timestamp, NULL) AS latest_2,
if(ifNull(equals(step_2, 1), 0), uuid, NULL) AS uuid_2,
if(ifNull(equals(step_2, 1), 0), e.`$session_id`, NULL) AS `$session_id_2`,
if(ifNull(equals(step_2, 1), 0), e.`$window_id`, NULL) AS `$window_id_2`
FROM events AS e
LEFT OUTER JOIN
(SELECT argMax(person_distinct_id_overrides.person_id, person_distinct_id_overrides.version) AS person_id,
person_distinct_id_overrides.distinct_id AS distinct_id
FROM person_distinct_id_overrides
WHERE equals(person_distinct_id_overrides.team_id, 2)
GROUP BY person_distinct_id_overrides.distinct_id
HAVING ifNull(equals(argMax(person_distinct_id_overrides.is_deleted, person_distinct_id_overrides.version), 0), 0) SETTINGS optimize_aggregation_in_order=1) AS e__override ON equals(e.distinct_id, e__override.distinct_id)
WHERE and(equals(e.team_id, 2), and(and(greaterOrEquals(toTimeZone(e.timestamp, 'UTC'), toDateTime64('2021-05-01 00:00:00.000000', 6, 'UTC')), lessOrEquals(toTimeZone(e.timestamp, 'UTC'), toDateTime64('2021-05-07 23:59:59.999999', 6, 'UTC'))), in(e.event, tuple('step one', 'step three', 'step two'))), or(ifNull(equals(step_0, 1), 0), ifNull(equals(step_1, 1), 0), ifNull(equals(step_2, 1), 0)))))))
WHERE ifNull(equals(step_0, 1), 0))
WHERE ifNull(equals(entrance_period_start, toDateTime64('2021-05-01 00:00:00.000000', 6, 'UTC')), 0)
GROUP BY aggregation_target,
entrance_period_start)
WHERE and(ifNull(greaterOrEquals(steps_completed, 1), 0), ifNull(less(steps_completed, 3), 0))
ORDER BY aggregation_target ASC) AS source
INNER JOIN
(SELECT person.id AS id
FROM person
WHERE equals(person.team_id, 2)
GROUP BY person.id
HAVING and(ifNull(equals(argMax(person.is_deleted, person.version), 0), 0), ifNull(less(argMax(toTimeZone(person.created_at, 'UTC'), person.version), plus(now64(6, 'UTC'), toIntervalDay(1))), 0)) SETTINGS optimize_aggregation_in_order=1) AS persons ON equals(persons.id, source.actor_id)
ORDER BY persons.id ASC
LIMIT 101
OFFSET 0 SETTINGS readonly=2,
max_execution_time=60,
allow_experimental_object_type=1,
format_csv_allow_double_quotes=0,
max_ast_elements=4000000,
max_expanded_ast_elements=4000000,
max_bytes_before_external_group_by=0,
allow_experimental_analyzer=1
'''
# ---
# name: TestFunnelTrendsActors.test_funnel_trend_persons_with_drop_off.1
'''
SELECT DISTINCT session_replay_events.session_id AS session_id
FROM session_replay_events
WHERE and(equals(session_replay_events.team_id, 2), ifNull(greaterOrEquals(toTimeZone(session_replay_events.min_first_timestamp, 'UTC'), minus(toDateTime64('2021-05-01 00:00:00.000000', 6, 'UTC'), toIntervalDay(21))), 0), in(session_replay_events.session_id, ['s1a']))
LIMIT 100 SETTINGS readonly=2,
max_execution_time=60,
allow_experimental_object_type=1,
format_csv_allow_double_quotes=0,
max_ast_elements=4000000,
max_expanded_ast_elements=4000000,
max_bytes_before_external_group_by=0
'''
# ---
# name: TestFunnelTrendsActors.test_funnel_trend_persons_with_no_to_step
'''
SELECT persons.id,
persons.id AS id,
source.matching_events AS matching_events
FROM
(SELECT aggregation_target AS actor_id,
final_matching_events AS matching_events
FROM
(SELECT aggregation_target AS aggregation_target,
toStartOfDay(timestamp) AS entrance_period_start,
max(steps) AS steps_completed,
groupArray(10)(step_0_matching_event) AS step_0_matching_events,
groupArray(10)(step_1_matching_event) AS step_1_matching_events,
groupArray(10)(step_2_matching_event) AS step_2_matching_events,
groupArray(10)(final_matching_event) AS final_matching_events
FROM
(SELECT aggregation_target AS aggregation_target,
timestamp AS timestamp,
step_0 AS step_0,
latest_0 AS latest_0,
uuid_0 AS uuid_0,
`$session_id_0` AS `$session_id_0`,
`$window_id_0` AS `$window_id_0`,
step_1 AS step_1,
latest_1 AS latest_1,
uuid_1 AS uuid_1,
`$session_id_1` AS `$session_id_1`,
`$window_id_1` AS `$window_id_1`,
step_2 AS step_2,
latest_2 AS latest_2,
uuid_2 AS uuid_2,
`$session_id_2` AS `$session_id_2`,
`$window_id_2` AS `$window_id_2`,
if(and(ifNull(lessOrEquals(latest_0, latest_1), 0), ifNull(lessOrEquals(latest_1, plus(toTimeZone(latest_0, 'UTC'), toIntervalDay(14))), 0), ifNull(lessOrEquals(latest_1, latest_2), 0), ifNull(lessOrEquals(latest_2, plus(toTimeZone(latest_0, 'UTC'), toIntervalDay(14))), 0)), 3, if(and(ifNull(lessOrEquals(latest_0, latest_1), 0), ifNull(lessOrEquals(latest_1, plus(toTimeZone(latest_0, 'UTC'), toIntervalDay(14))), 0)), 2, 1)) AS steps,
if(and(isNotNull(latest_1), ifNull(lessOrEquals(latest_1, plus(toTimeZone(latest_0, 'UTC'), toIntervalDay(14))), 0)), dateDiff('second', latest_0, latest_1), NULL) AS step_1_conversion_time,
if(and(isNotNull(latest_2), ifNull(lessOrEquals(latest_2, plus(toTimeZone(latest_1, 'UTC'), toIntervalDay(14))), 0)), dateDiff('second', latest_1, latest_2), NULL) AS step_2_conversion_time,
tuple(latest_0, uuid_0, `$session_id_0`, `$window_id_0`) AS step_0_matching_event,
tuple(latest_1, uuid_1, `$session_id_1`, `$window_id_1`) AS step_1_matching_event,
tuple(latest_2, uuid_2, `$session_id_2`, `$window_id_2`) AS step_2_matching_event,
if(isNull(latest_0), tuple(NULL, NULL, NULL, NULL), if(isNull(latest_1), step_0_matching_event, if(isNull(latest_2), step_1_matching_event, step_2_matching_event))) AS final_matching_event
FROM
(SELECT aggregation_target AS aggregation_target,
timestamp AS timestamp,
step_0 AS step_0,
latest_0 AS latest_0,
uuid_0 AS uuid_0,
`$session_id_0` AS `$session_id_0`,
`$window_id_0` AS `$window_id_0`,
step_1 AS step_1,
latest_1 AS latest_1,
uuid_1 AS uuid_1,
`$session_id_1` AS `$session_id_1`,
`$window_id_1` AS `$window_id_1`,
step_2 AS step_2,
min(latest_2) OVER (PARTITION BY aggregation_target
ORDER BY timestamp DESC ROWS BETWEEN UNBOUNDED PRECEDING AND 0 PRECEDING) AS latest_2,
last_value(uuid_2) OVER (PARTITION BY aggregation_target
ORDER BY timestamp DESC ROWS BETWEEN UNBOUNDED PRECEDING AND 0 PRECEDING) AS uuid_2,
last_value(`$session_id_2`) OVER (PARTITION BY aggregation_target
ORDER BY timestamp DESC ROWS BETWEEN UNBOUNDED PRECEDING AND 0 PRECEDING) AS `$session_id_2`,
last_value(`$window_id_2`) OVER (PARTITION BY aggregation_target
ORDER BY timestamp DESC ROWS BETWEEN UNBOUNDED PRECEDING AND 0 PRECEDING) AS `$window_id_2`
FROM
(SELECT aggregation_target AS aggregation_target,
timestamp AS timestamp,
step_0 AS step_0,
latest_0 AS latest_0,
uuid_0 AS uuid_0,
`$session_id_0` AS `$session_id_0`,
`$window_id_0` AS `$window_id_0`,
step_1 AS step_1,
latest_1 AS latest_1,
uuid_1 AS uuid_1,
`$session_id_1` AS `$session_id_1`,
`$window_id_1` AS `$window_id_1`,
step_2 AS step_2,
if(ifNull(less(latest_2, latest_1), 0), NULL, latest_2) AS latest_2,
if(ifNull(less(latest_2, latest_1), 0), NULL, uuid_2) AS uuid_2,
if(ifNull(less(latest_2, latest_1), 0), NULL, `$session_id_2`) AS `$session_id_2`,
if(ifNull(less(latest_2, latest_1), 0), NULL, `$window_id_2`) AS `$window_id_2`
FROM
(SELECT aggregation_target AS aggregation_target,
timestamp AS timestamp,
step_0 AS step_0,
latest_0 AS latest_0,
uuid_0 AS uuid_0,
`$session_id_0` AS `$session_id_0`,
`$window_id_0` AS `$window_id_0`,
step_1 AS step_1,
min(latest_1) OVER (PARTITION BY aggregation_target
ORDER BY timestamp DESC ROWS BETWEEN UNBOUNDED PRECEDING AND 0 PRECEDING) AS latest_1,
last_value(uuid_1) OVER (PARTITION BY aggregation_target
ORDER BY timestamp DESC ROWS BETWEEN UNBOUNDED PRECEDING AND 0 PRECEDING) AS uuid_1,
last_value(`$session_id_1`) OVER (PARTITION BY aggregation_target
ORDER BY timestamp DESC ROWS BETWEEN UNBOUNDED PRECEDING AND 0 PRECEDING) AS `$session_id_1`,
last_value(`$window_id_1`) OVER (PARTITION BY aggregation_target
ORDER BY timestamp DESC ROWS BETWEEN UNBOUNDED PRECEDING AND 0 PRECEDING) AS `$window_id_1`,
step_2 AS step_2,
min(latest_2) OVER (PARTITION BY aggregation_target
ORDER BY timestamp DESC ROWS BETWEEN UNBOUNDED PRECEDING AND 0 PRECEDING) AS latest_2,
last_value(uuid_2) OVER (PARTITION BY aggregation_target
ORDER BY timestamp DESC ROWS BETWEEN UNBOUNDED PRECEDING AND 0 PRECEDING) AS uuid_2,
last_value(`$session_id_2`) OVER (PARTITION BY aggregation_target
ORDER BY timestamp DESC ROWS BETWEEN UNBOUNDED PRECEDING AND 0 PRECEDING) AS `$session_id_2`,
last_value(`$window_id_2`) OVER (PARTITION BY aggregation_target
ORDER BY timestamp DESC ROWS BETWEEN UNBOUNDED PRECEDING AND 0 PRECEDING) AS `$window_id_2`
FROM
(SELECT toTimeZone(e.timestamp, 'UTC') AS timestamp,
if(not(empty(e__override.distinct_id)), e__override.person_id, e.person_id) AS aggregation_target,
e.uuid AS uuid,
if(equals(e.event, 'step one'), 1, 0) AS step_0,
if(ifNull(equals(step_0, 1), 0), timestamp, NULL) AS latest_0,
if(ifNull(equals(step_0, 1), 0), uuid, NULL) AS uuid_0,
if(ifNull(equals(step_0, 1), 0), e.`$session_id`, NULL) AS `$session_id_0`,
if(ifNull(equals(step_0, 1), 0), e.`$window_id`, NULL) AS `$window_id_0`,
if(equals(e.event, 'step two'), 1, 0) AS step_1,
if(ifNull(equals(step_1, 1), 0), timestamp, NULL) AS latest_1,
if(ifNull(equals(step_1, 1), 0), uuid, NULL) AS uuid_1,
if(ifNull(equals(step_1, 1), 0), e.`$session_id`, NULL) AS `$session_id_1`,
if(ifNull(equals(step_1, 1), 0), e.`$window_id`, NULL) AS `$window_id_1`,
if(equals(e.event, 'step three'), 1, 0) AS step_2,
if(ifNull(equals(step_2, 1), 0), timestamp, NULL) AS latest_2,
if(ifNull(equals(step_2, 1), 0), uuid, NULL) AS uuid_2,
if(ifNull(equals(step_2, 1), 0), e.`$session_id`, NULL) AS `$session_id_2`,
if(ifNull(equals(step_2, 1), 0), e.`$window_id`, NULL) AS `$window_id_2`
FROM events AS e
LEFT OUTER JOIN
(SELECT argMax(person_distinct_id_overrides.person_id, person_distinct_id_overrides.version) AS person_id,
person_distinct_id_overrides.distinct_id AS distinct_id
FROM person_distinct_id_overrides
WHERE equals(person_distinct_id_overrides.team_id, 2)
GROUP BY person_distinct_id_overrides.distinct_id
HAVING ifNull(equals(argMax(person_distinct_id_overrides.is_deleted, person_distinct_id_overrides.version), 0), 0) SETTINGS optimize_aggregation_in_order=1) AS e__override ON equals(e.distinct_id, e__override.distinct_id)
WHERE and(equals(e.team_id, 2), and(and(greaterOrEquals(toTimeZone(e.timestamp, 'UTC'), toDateTime64('2021-05-01 00:00:00.000000', 6, 'UTC')), lessOrEquals(toTimeZone(e.timestamp, 'UTC'), toDateTime64('2021-05-07 23:59:59.999999', 6, 'UTC'))), in(e.event, tuple('step one', 'step three', 'step two'))), or(ifNull(equals(step_0, 1), 0), ifNull(equals(step_1, 1), 0), ifNull(equals(step_2, 1), 0)))))))
WHERE ifNull(equals(step_0, 1), 0))
WHERE ifNull(equals(entrance_period_start, toDateTime64('2021-05-01 00:00:00.000000', 6, 'UTC')), 0)
GROUP BY aggregation_target,
entrance_period_start)
WHERE ifNull(greaterOrEquals(steps_completed, 3), 0)
ORDER BY aggregation_target ASC) AS source
INNER JOIN
(SELECT person.id AS id
FROM person
WHERE equals(person.team_id, 2)
GROUP BY person.id
HAVING and(ifNull(equals(argMax(person.is_deleted, person.version), 0), 0), ifNull(less(argMax(toTimeZone(person.created_at, 'UTC'), person.version), plus(now64(6, 'UTC'), toIntervalDay(1))), 0)) SETTINGS optimize_aggregation_in_order=1) AS persons ON equals(persons.id, source.actor_id)
ORDER BY persons.id ASC
LIMIT 101
OFFSET 0 SETTINGS readonly=2,
max_execution_time=60,
allow_experimental_object_type=1,
format_csv_allow_double_quotes=0,
max_ast_elements=4000000,
max_expanded_ast_elements=4000000,
max_bytes_before_external_group_by=0,
allow_experimental_analyzer=1
'''
# ---
# name: TestFunnelTrendsActors.test_funnel_trend_persons_with_no_to_step.1
'''
SELECT DISTINCT session_replay_events.session_id AS session_id
FROM session_replay_events
WHERE and(equals(session_replay_events.team_id, 2), ifNull(greaterOrEquals(toTimeZone(session_replay_events.min_first_timestamp, 'UTC'), minus(toDateTime64('2021-05-01 00:00:00.000000', 6, 'UTC'), toIntervalDay(21))), 0), in(session_replay_events.session_id, ['s1c']))
LIMIT 100 SETTINGS readonly=2,
max_execution_time=60,
allow_experimental_object_type=1,
format_csv_allow_double_quotes=0,
max_ast_elements=4000000,
max_expanded_ast_elements=4000000,
max_bytes_before_external_group_by=0
'''
# ---

View File

@ -0,0 +1,217 @@
# serializer version: 1
# name: TestFunnelTrendsActorsUDF.test_funnel_trend_persons_returns_recordings
'''
SELECT persons.id,
persons.id AS id,
source.matching_events AS matching_events
FROM
(SELECT aggregation_target AS actor_id,
matching_events AS matching_events
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), toUInt64(toDateTime(toStartOfDay(timestamp), 'UTC')), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_trends_v2(0, 2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
toTimeZone(toDateTime(toUInt64(af_tuple.1), 'UTC'), 'UTC') AS entrance_period_start,
af_tuple.2 AS success_bool,
af_tuple.3 AS breakdown,
groupArray(tuple(timestamp, uuid, `$session_id`, `$window_id`)) AS user_events,
mapFromArrays(arrayMap(x -> x.2, user_events), user_events) AS user_events_map,
[user_events_map[af_tuple.4]] AS matching_events,
aggregation_target AS aggregation_target
FROM
(SELECT toTimeZone(e.timestamp, 'UTC') AS timestamp,
if(not(empty(e__override.distinct_id)), e__override.person_id, e.person_id) AS aggregation_target,
e.uuid AS uuid,
e.`$session_id` AS `$session_id`,
e.`$window_id` AS `$window_id`,
if(equals(e.event, 'step one'), 1, 0) AS step_0,
if(equals(e.event, 'step two'), 1, 0) AS step_1,
if(equals(e.event, 'step three'), 1, 0) AS step_2
FROM events AS e
LEFT OUTER JOIN
(SELECT argMax(person_distinct_id_overrides.person_id, person_distinct_id_overrides.version) AS person_id,
person_distinct_id_overrides.distinct_id AS distinct_id
FROM person_distinct_id_overrides
WHERE equals(person_distinct_id_overrides.team_id, 2)
GROUP BY person_distinct_id_overrides.distinct_id
HAVING ifNull(equals(argMax(person_distinct_id_overrides.is_deleted, person_distinct_id_overrides.version), 0), 0) SETTINGS optimize_aggregation_in_order=1) AS e__override ON equals(e.distinct_id, e__override.distinct_id)
WHERE and(equals(e.team_id, 2), and(and(greaterOrEquals(toTimeZone(e.timestamp, 'UTC'), toDateTime64('2021-05-01 00:00:00.000000', 6, 'UTC')), lessOrEquals(toTimeZone(e.timestamp, 'UTC'), toDateTime64('2021-05-07 23:59:59.999999', 6, 'UTC'))), in(e.event, tuple('step one', 'step three', 'step two'))), or(ifNull(equals(step_0, 1), 0), ifNull(equals(step_1, 1), 0), ifNull(equals(step_2, 1), 0))))
GROUP BY aggregation_target SETTINGS date_time_output_format='iso',
date_time_input_format='best_effort')
WHERE and(ifNull(equals(success_bool, 1), 0), ifNull(equals(entrance_period_start, toDateTime64('2021-05-01 00:00:00.000000', 6, 'UTC')), 0))
ORDER BY aggregation_target ASC) AS source
INNER JOIN
(SELECT person.id AS id
FROM person
WHERE equals(person.team_id, 2)
GROUP BY person.id
HAVING and(ifNull(equals(argMax(person.is_deleted, person.version), 0), 0), ifNull(less(argMax(toTimeZone(person.created_at, 'UTC'), person.version), plus(now64(6, 'UTC'), toIntervalDay(1))), 0)) SETTINGS optimize_aggregation_in_order=1) AS persons ON equals(persons.id, source.actor_id)
ORDER BY persons.id ASC
LIMIT 101
OFFSET 0 SETTINGS readonly=2,
max_execution_time=60,
allow_experimental_object_type=1,
format_csv_allow_double_quotes=0,
max_ast_elements=4000000,
max_expanded_ast_elements=4000000,
max_bytes_before_external_group_by=0,
allow_experimental_analyzer=1
'''
# ---
# name: TestFunnelTrendsActorsUDF.test_funnel_trend_persons_returns_recordings.1
'''
SELECT DISTINCT session_replay_events.session_id AS session_id
FROM session_replay_events
WHERE and(equals(session_replay_events.team_id, 2), ifNull(greaterOrEquals(toTimeZone(session_replay_events.min_first_timestamp, 'UTC'), minus(toDateTime64('2021-05-01 00:00:00.000000', 6, 'UTC'), toIntervalDay(21))), 0), in(session_replay_events.session_id, ['s1b']))
LIMIT 100 SETTINGS readonly=2,
max_execution_time=60,
allow_experimental_object_type=1,
format_csv_allow_double_quotes=0,
max_ast_elements=4000000,
max_expanded_ast_elements=4000000,
max_bytes_before_external_group_by=0
'''
# ---
# name: TestFunnelTrendsActorsUDF.test_funnel_trend_persons_with_drop_off
'''
SELECT persons.id,
persons.id AS id,
source.matching_events AS matching_events
FROM
(SELECT aggregation_target AS actor_id,
matching_events AS matching_events
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), toUInt64(toDateTime(toStartOfDay(timestamp), 'UTC')), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1), multiply(3, step_2)])))) AS events_array,
arrayJoin(aggregate_funnel_array_trends_v2(0, 3, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
toTimeZone(toDateTime(toUInt64(af_tuple.1), 'UTC'), 'UTC') AS entrance_period_start,
af_tuple.2 AS success_bool,
af_tuple.3 AS breakdown,
groupArray(tuple(timestamp, uuid, `$session_id`, `$window_id`)) AS user_events,
mapFromArrays(arrayMap(x -> x.2, user_events), user_events) AS user_events_map,
[user_events_map[af_tuple.4]] AS matching_events,
aggregation_target AS aggregation_target
FROM
(SELECT toTimeZone(e.timestamp, 'UTC') AS timestamp,
if(not(empty(e__override.distinct_id)), e__override.person_id, e.person_id) AS aggregation_target,
e.uuid AS uuid,
e.`$session_id` AS `$session_id`,
e.`$window_id` AS `$window_id`,
if(equals(e.event, 'step one'), 1, 0) AS step_0,
if(equals(e.event, 'step two'), 1, 0) AS step_1,
if(equals(e.event, 'step three'), 1, 0) AS step_2
FROM events AS e
LEFT OUTER JOIN
(SELECT argMax(person_distinct_id_overrides.person_id, person_distinct_id_overrides.version) AS person_id,
person_distinct_id_overrides.distinct_id AS distinct_id
FROM person_distinct_id_overrides
WHERE equals(person_distinct_id_overrides.team_id, 2)
GROUP BY person_distinct_id_overrides.distinct_id
HAVING ifNull(equals(argMax(person_distinct_id_overrides.is_deleted, person_distinct_id_overrides.version), 0), 0) SETTINGS optimize_aggregation_in_order=1) AS e__override ON equals(e.distinct_id, e__override.distinct_id)
WHERE and(equals(e.team_id, 2), and(and(greaterOrEquals(toTimeZone(e.timestamp, 'UTC'), toDateTime64('2021-05-01 00:00:00.000000', 6, 'UTC')), lessOrEquals(toTimeZone(e.timestamp, 'UTC'), toDateTime64('2021-05-07 23:59:59.999999', 6, 'UTC'))), in(e.event, tuple('step one', 'step three', 'step two'))), or(ifNull(equals(step_0, 1), 0), ifNull(equals(step_1, 1), 0), ifNull(equals(step_2, 1), 0))))
GROUP BY aggregation_target SETTINGS date_time_output_format='iso',
date_time_input_format='best_effort')
WHERE and(ifNull(notEquals(success_bool, 1), 1), ifNull(equals(entrance_period_start, toDateTime64('2021-05-01 00:00:00.000000', 6, 'UTC')), 0))
ORDER BY aggregation_target ASC) AS source
INNER JOIN
(SELECT person.id AS id
FROM person
WHERE equals(person.team_id, 2)
GROUP BY person.id
HAVING and(ifNull(equals(argMax(person.is_deleted, person.version), 0), 0), ifNull(less(argMax(toTimeZone(person.created_at, 'UTC'), person.version), plus(now64(6, 'UTC'), toIntervalDay(1))), 0)) SETTINGS optimize_aggregation_in_order=1) AS persons ON equals(persons.id, source.actor_id)
ORDER BY persons.id ASC
LIMIT 101
OFFSET 0 SETTINGS readonly=2,
max_execution_time=60,
allow_experimental_object_type=1,
format_csv_allow_double_quotes=0,
max_ast_elements=4000000,
max_expanded_ast_elements=4000000,
max_bytes_before_external_group_by=0,
allow_experimental_analyzer=1
'''
# ---
# name: TestFunnelTrendsActorsUDF.test_funnel_trend_persons_with_drop_off.1
'''
SELECT DISTINCT session_replay_events.session_id AS session_id
FROM session_replay_events
WHERE and(equals(session_replay_events.team_id, 2), ifNull(greaterOrEquals(toTimeZone(session_replay_events.min_first_timestamp, 'UTC'), minus(toDateTime64('2021-05-01 00:00:00.000000', 6, 'UTC'), toIntervalDay(21))), 0), in(session_replay_events.session_id, ['s1a']))
LIMIT 100 SETTINGS readonly=2,
max_execution_time=60,
allow_experimental_object_type=1,
format_csv_allow_double_quotes=0,
max_ast_elements=4000000,
max_expanded_ast_elements=4000000,
max_bytes_before_external_group_by=0
'''
# ---
# name: TestFunnelTrendsActorsUDF.test_funnel_trend_persons_with_no_to_step
'''
SELECT persons.id,
persons.id AS id,
source.matching_events AS matching_events
FROM
(SELECT aggregation_target AS actor_id,
matching_events AS matching_events
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), toUInt64(toDateTime(toStartOfDay(timestamp), 'UTC')), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1), multiply(3, step_2)])))) AS events_array,
arrayJoin(aggregate_funnel_array_trends_v2(0, 3, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
toTimeZone(toDateTime(toUInt64(af_tuple.1), 'UTC'), 'UTC') AS entrance_period_start,
af_tuple.2 AS success_bool,
af_tuple.3 AS breakdown,
groupArray(tuple(timestamp, uuid, `$session_id`, `$window_id`)) AS user_events,
mapFromArrays(arrayMap(x -> x.2, user_events), user_events) AS user_events_map,
[user_events_map[af_tuple.4]] AS matching_events,
aggregation_target AS aggregation_target
FROM
(SELECT toTimeZone(e.timestamp, 'UTC') AS timestamp,
if(not(empty(e__override.distinct_id)), e__override.person_id, e.person_id) AS aggregation_target,
e.uuid AS uuid,
e.`$session_id` AS `$session_id`,
e.`$window_id` AS `$window_id`,
if(equals(e.event, 'step one'), 1, 0) AS step_0,
if(equals(e.event, 'step two'), 1, 0) AS step_1,
if(equals(e.event, 'step three'), 1, 0) AS step_2
FROM events AS e
LEFT OUTER JOIN
(SELECT argMax(person_distinct_id_overrides.person_id, person_distinct_id_overrides.version) AS person_id,
person_distinct_id_overrides.distinct_id AS distinct_id
FROM person_distinct_id_overrides
WHERE equals(person_distinct_id_overrides.team_id, 2)
GROUP BY person_distinct_id_overrides.distinct_id
HAVING ifNull(equals(argMax(person_distinct_id_overrides.is_deleted, person_distinct_id_overrides.version), 0), 0) SETTINGS optimize_aggregation_in_order=1) AS e__override ON equals(e.distinct_id, e__override.distinct_id)
WHERE and(equals(e.team_id, 2), and(and(greaterOrEquals(toTimeZone(e.timestamp, 'UTC'), toDateTime64('2021-05-01 00:00:00.000000', 6, 'UTC')), lessOrEquals(toTimeZone(e.timestamp, 'UTC'), toDateTime64('2021-05-07 23:59:59.999999', 6, 'UTC'))), in(e.event, tuple('step one', 'step three', 'step two'))), or(ifNull(equals(step_0, 1), 0), ifNull(equals(step_1, 1), 0), ifNull(equals(step_2, 1), 0))))
GROUP BY aggregation_target SETTINGS date_time_output_format='iso',
date_time_input_format='best_effort')
WHERE and(ifNull(equals(success_bool, 1), 0), ifNull(equals(entrance_period_start, toDateTime64('2021-05-01 00:00:00.000000', 6, 'UTC')), 0))
ORDER BY aggregation_target ASC) AS source
INNER JOIN
(SELECT person.id AS id
FROM person
WHERE equals(person.team_id, 2)
GROUP BY person.id
HAVING and(ifNull(equals(argMax(person.is_deleted, person.version), 0), 0), ifNull(less(argMax(toTimeZone(person.created_at, 'UTC'), person.version), plus(now64(6, 'UTC'), toIntervalDay(1))), 0)) SETTINGS optimize_aggregation_in_order=1) AS persons ON equals(persons.id, source.actor_id)
ORDER BY persons.id ASC
LIMIT 101
OFFSET 0 SETTINGS readonly=2,
max_execution_time=60,
allow_experimental_object_type=1,
format_csv_allow_double_quotes=0,
max_ast_elements=4000000,
max_expanded_ast_elements=4000000,
max_bytes_before_external_group_by=0,
allow_experimental_analyzer=1
'''
# ---
# name: TestFunnelTrendsActorsUDF.test_funnel_trend_persons_with_no_to_step.1
'''
SELECT DISTINCT session_replay_events.session_id AS session_id
FROM session_replay_events
WHERE and(equals(session_replay_events.team_id, 2), ifNull(greaterOrEquals(toTimeZone(session_replay_events.min_first_timestamp, 'UTC'), minus(toDateTime64('2021-05-01 00:00:00.000000', 6, 'UTC'), toIntervalDay(21))), 0), in(session_replay_events.session_id, ['s1c']))
LIMIT 100 SETTINGS readonly=2,
max_execution_time=60,
allow_experimental_object_type=1,
format_csv_allow_double_quotes=0,
max_ast_elements=4000000,
max_expanded_ast_elements=4000000,
max_bytes_before_external_group_by=0
'''
# ---

View File

@ -7,14 +7,16 @@
if(ifNull(greater(reached_from_step_count, 0), 0), round(multiply(divide(reached_to_step_count, reached_from_step_count), 100), 2), 0) AS conversion_rate,
data.breakdown AS prop
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), toUInt64(toDateTime(toStartOfDay(timestamp), 'UTC')), [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1), multiply(3, step_2)])))) AS events_array,
arrayJoin(aggregate_funnel_array_trends_v1(0, 3, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), toUInt64(toDateTime(toStartOfDay(timestamp), 'UTC')), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1), multiply(3, step_2)])))) AS events_array,
arrayJoin(aggregate_funnel_array_trends_v2(0, 3, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
toTimeZone(toDateTime(toUInt64(af_tuple.1), 'UTC'), 'UTC') AS entrance_period_start,
af_tuple.2 AS success_bool,
af_tuple.3 AS breakdown
af_tuple.3 AS breakdown,
aggregation_target AS aggregation_target
FROM
(SELECT toTimeZone(e.timestamp, 'UTC') AS timestamp,
if(not(empty(e__override.distinct_id)), e__override.person_id, e.person_id) AS aggregation_target,
e.uuid AS uuid,
if(equals(e.event, 'step one'), 1, 0) AS step_0,
if(equals(e.event, 'step two'), 1, 0) AS step_1,
if(equals(e.event, 'step three'), 1, 0) AS step_2
@ -53,14 +55,16 @@
if(ifNull(greater(reached_from_step_count, 0), 0), round(multiply(divide(reached_to_step_count, reached_from_step_count), 100), 2), 0) AS conversion_rate,
data.breakdown AS prop
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), toUInt64(toDateTime(toStartOfDay(timestamp), 'US/Pacific')), [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1), multiply(3, step_2)])))) AS events_array,
arrayJoin(aggregate_funnel_array_trends_v1(0, 3, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), toUInt64(toDateTime(toStartOfDay(timestamp), 'US/Pacific')), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1), multiply(3, step_2)])))) AS events_array,
arrayJoin(aggregate_funnel_array_trends_v2(0, 3, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
toTimeZone(toDateTime(toUInt64(af_tuple.1), 'US/Pacific'), 'US/Pacific') AS entrance_period_start,
af_tuple.2 AS success_bool,
af_tuple.3 AS breakdown
af_tuple.3 AS breakdown,
aggregation_target AS aggregation_target
FROM
(SELECT toTimeZone(e.timestamp, 'US/Pacific') AS timestamp,
if(not(empty(e__override.distinct_id)), e__override.person_id, e.person_id) AS aggregation_target,
e.uuid AS uuid,
if(equals(e.event, 'step one'), 1, 0) AS step_0,
if(equals(e.event, 'step two'), 1, 0) AS step_1,
if(equals(e.event, 'step three'), 1, 0) AS step_2
@ -99,14 +103,16 @@
if(ifNull(greater(reached_from_step_count, 0), 0), round(multiply(divide(reached_to_step_count, reached_from_step_count), 100), 2), 0) AS conversion_rate,
data.breakdown AS prop
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), toUInt64(toDateTime(toStartOfWeek(timestamp, 0), 'UTC')), [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1), multiply(3, step_2)])))) AS events_array,
arrayJoin(aggregate_funnel_array_trends_v1(0, 3, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), toUInt64(toDateTime(toStartOfWeek(timestamp, 0), 'UTC')), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1), multiply(3, step_2)])))) AS events_array,
arrayJoin(aggregate_funnel_array_trends_v2(0, 3, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
toTimeZone(toDateTime(toUInt64(af_tuple.1), 'UTC'), 'UTC') AS entrance_period_start,
af_tuple.2 AS success_bool,
af_tuple.3 AS breakdown
af_tuple.3 AS breakdown,
aggregation_target AS aggregation_target
FROM
(SELECT toTimeZone(e.timestamp, 'UTC') AS timestamp,
if(not(empty(e__override.distinct_id)), e__override.person_id, e.person_id) AS aggregation_target,
e.uuid AS uuid,
if(equals(e.event, 'step one'), 1, 0) AS step_0,
if(equals(e.event, 'step two'), 1, 0) AS step_1,
if(equals(e.event, 'step three'), 1, 0) AS step_2

View File

@ -20,7 +20,7 @@
breakdown AS final_prop
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1), multiply(3, step_2)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(3, 15, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(3, 15, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -69,7 +69,7 @@
(SELECT aggregation_target AS actor_id
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1), multiply(3, step_2)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(3, 15, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(3, 15, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -146,7 +146,7 @@
breakdown AS final_prop
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1), multiply(3, step_2)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(3, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(3, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -221,7 +221,7 @@
breakdown AS final_prop
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -283,7 +283,7 @@
breakdown AS final_prop
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1), multiply(3, step_2)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(3, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(3, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -343,7 +343,7 @@
(SELECT aggregation_target AS actor_id
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1), multiply(3, step_2)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(3, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(3, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -411,7 +411,7 @@
(SELECT aggregation_target AS actor_id
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1), multiply(3, step_2)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(3, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(3, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -479,7 +479,7 @@
(SELECT aggregation_target AS actor_id
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1), multiply(3, step_2)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(3, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(3, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -562,7 +562,7 @@
breakdown AS final_prop
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -619,7 +619,7 @@
breakdown AS final_prop
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, [], arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', [[]], events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -673,7 +673,7 @@
if(ifNull(less(row_number, 25), 0), breakdown, ['Other']) AS final_prop
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, prop, arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', groupUniqArray(prop), events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', groupUniqArray(prop), events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -742,7 +742,7 @@
if(ifNull(less(row_number, 25), 0), breakdown, ['Other']) AS final_prop
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, prop, arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'step_1', 'ordered', groupUniqArray(prop), events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'step_1', 'ordered', groupUniqArray(prop), events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -818,7 +818,7 @@
if(ifNull(less(row_number, 25), 0), breakdown, ['Other']) AS final_prop
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, prop, arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1)])))) AS events_array,
arrayJoin(aggregate_funnel_array_v1(2, 1209600, 'first_touch', 'ordered', groupUniqArray(prop), events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_array_v2(2, 1209600, 'first_touch', 'ordered', groupUniqArray(prop), events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -892,7 +892,7 @@
if(ifNull(less(row_number, 25), 0), breakdown, 'Other') AS final_prop
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, prop, arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1), multiply(3, step_2)])))) AS events_array,
arrayJoin(aggregate_funnel_v1(3, 1209600, 'first_touch', 'ordered', groupUniqArray(prop), events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_v2(3, 1209600, 'first_touch', 'ordered', groupUniqArray(prop), events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -969,7 +969,7 @@
if(ifNull(less(row_number, 25), 0), breakdown, 'Other') AS final_prop
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, prop, arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1), multiply(3, step_2)])))) AS events_array,
arrayJoin(aggregate_funnel_v1(3, 1209600, 'first_touch', 'ordered', groupUniqArray(prop), events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_v2(3, 1209600, 'first_touch', 'ordered', groupUniqArray(prop), events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,
@ -1046,7 +1046,7 @@
if(ifNull(less(row_number, 25), 0), breakdown, 'Other') AS final_prop
FROM
(SELECT arraySort(t -> t.1, groupArray(tuple(accurateCastOrNull(timestamp, 'Float64'), uuid, prop, arrayFilter(x -> ifNull(notEquals(x, 0), 1), [multiply(1, step_0), multiply(2, step_1), multiply(3, step_2)])))) AS events_array,
arrayJoin(aggregate_funnel_v1(3, 1209600, 'first_touch', 'ordered', groupUniqArray(prop), events_array)) AS af_tuple,
arrayJoin(aggregate_funnel_v2(3, 1209600, 'first_touch', 'ordered', groupUniqArray(prop), events_array)) AS af_tuple,
af_tuple.1 AS step_reached,
plus(af_tuple.1, 1) AS steps,
af_tuple.2 AS breakdown,

View File

@ -31,7 +31,9 @@ filters = {
@freeze_time("2021-05-01")
class TestFunnelTrendsPersons(ClickhouseTestMixin, APIBaseTest):
class BaseTestFunnelTrendsActors(ClickhouseTestMixin, APIBaseTest):
__test__ = False
@snapshot_clickhouse_queries
def test_funnel_trend_persons_returns_recordings(self):
persons = journeys_for(
@ -169,3 +171,7 @@ class TestFunnelTrendsPersons(ClickhouseTestMixin, APIBaseTest):
[next(iter(results[0][2]))["session_id"]],
["s1a"],
)
class TestFunnelTrendsActors(BaseTestFunnelTrendsActors):
__test__ = True

View File

@ -0,0 +1,12 @@
from unittest.mock import Mock, patch
from posthog.hogql_queries.insights.funnels.test.test_funnel_trends_actors import BaseTestFunnelTrendsActors
@patch(
"posthoganalytics.feature_enabled",
new=Mock(side_effect=lambda key, *args, **kwargs: key == "insight-funnels-use-udf-trends"),
)
class TestFunnelTrendsActorsUDF(BaseTestFunnelTrendsActors):
__test__ = True

View File

@ -45,16 +45,23 @@ def get_funnel_actor_class(funnelsFilter: FunnelsFilter, use_udf=False):
FunnelStrictActors,
FunnelUnorderedActors,
FunnelTrendsActors,
FunnelTrendsUDF,
)
if funnelsFilter.funnelVizType == FunnelVizType.TRENDS:
return FunnelTrendsActors
if funnelsFilter.funnelOrderType == StepOrderValue.UNORDERED:
return FunnelUnorderedActors
if funnelsFilter.funnelVizType == FunnelVizType.TRENDS:
if use_udf:
return FunnelTrendsUDF
return FunnelTrendsActors
if use_udf:
return FunnelUDF
if funnelsFilter.funnelOrderType == StepOrderValue.STRICT:
return FunnelStrictActors
return FunnelActors

View File

@ -2,6 +2,7 @@ import argparse
import os
import shutil
import datetime
import re
import xml.etree.ElementTree as ET
from xml import etree
@ -12,7 +13,10 @@ from xml import etree
# 4. Land a version of the posthog repo with the updated `user_scripts` folder from the new branch (make sure this PR doesn't include changes to this file with the new version)
# 5. Run the `copy_udfs_to_clickhouse` action in the `posthog_cloud_infra` repo to deploy the `user_scripts` folder to clickhouse
# 6. After that deploy goes out, it is safe to land and deploy the full changes to the `posthog` repo
UDF_VERSION = 1 # Last modified by: @aspicer, 2024-10-14
UDF_VERSION = 2 # Last modified by: @aspicer, 2024-10-16
# Clean up all versions less than this
EARLIEST_UDF_VERSION = 1
CLICKHOUSE_XML_FILENAME = "user_defined_function.xml"
ACTIVE_XML_CONFIG = "../../docker/clickhouse/user_defined_function.xml"
@ -47,6 +51,14 @@ def prepare_version(force=False):
last_version_xml = ET.parse(ACTIVE_XML_CONFIG)
last_version_root = last_version_xml.getroot()
# Remove old versions from last_version
for function in list(last_version_root):
name = function.find("name")
match = re.search(r"_v(\d+)$", name.text)
if match is None or int(match.group(1)) < EARLIEST_UDF_VERSION:
last_version_root.remove(function)
# We want to update the name and the command to include the version, and add it to last version
for function in list(base_xml.getroot()):
name = function.find("name")

View File

@ -1,592 +1,6 @@
<functions>
<!-- Version: v1. Generated at: 2024-10-15T06:47:07.870397+00:00
<!-- Version: v2. Generated at: 2024-10-17T05:08:53.836354+00:00
This file is autogenerated by udf_versioner.py. Do not edit this, only edit the version at docker/clickhouse/user_defined_function.xml--><function>
<type>executable_pool</type>
<name>aggregate_funnel</name>
<return_type>Array(Tuple(Int8, Nullable(String), Array(Float64), Array(Array(UUID))))</return_type>
<return_name>result</return_name>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt64</type>
<name>conversion_window_limit</name>
</argument>
<argument>
<type>String</type>
<name>breakdown_attribution_type</name>
</argument>
<argument>
<type>String</type>
<name>funnel_order_type</name>
</argument>
<argument>
<type>Array(Nullable(String))</type>
<name>prop_vals</name>
</argument>
<argument>
<type>Array(Tuple(Nullable(Float64), UUID, Nullable(String), Array(Int8)))</type>
<name>value</name>
</argument>
<format>JSONEachRow</format>
<command>aggregate_funnel steps</command>
<lifetime>600</lifetime>
</function>
<function>
<type>executable_pool</type>
<name>aggregate_funnel_cohort</name>
<return_type>Array(Tuple(Int8, UInt64, Array(Float64), Array(Array(UUID))))</return_type>
<return_name>result</return_name>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt64</type>
<name>conversion_window_limit</name>
</argument>
<argument>
<type>String</type>
<name>breakdown_attribution_type</name>
</argument>
<argument>
<type>String</type>
<name>funnel_order_type</name>
</argument>
<argument>
<type>Array(UInt64)</type>
<name>prop_vals</name>
</argument>
<argument>
<type>Array(Tuple(Nullable(Float64), UUID, UInt64, Array(Int8)))</type>
<name>value</name>
</argument>
<format>JSONEachRow</format>
<command>aggregate_funnel steps</command>
<lifetime>600</lifetime>
</function>
<function>
<type>executable_pool</type>
<name>aggregate_funnel_array</name>
<return_type>Array(Tuple(Int8, Array(String), Array(Float64), Array(Array(UUID))))</return_type>
<return_name>result</return_name>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt64</type>
<name>conversion_window_limit</name>
</argument>
<argument>
<type>String</type>
<name>breakdown_attribution_type</name>
</argument>
<argument>
<type>String</type>
<name>funnel_order_type</name>
</argument>
<argument>
<type>Array(Array(String))</type>
<name>prop_vals</name>
</argument>
<argument>
<type>Array(Tuple(Nullable(Float64), UUID, Array(String), Array(Int8)))</type>
<name>value</name>
</argument>
<format>JSONEachRow</format>
<command>aggregate_funnel steps</command>
<lifetime>600</lifetime>
</function>
<function>
<type>executable_pool</type>
<name>aggregate_funnel_test</name>
<return_type>String</return_type>
<return_name>result</return_name>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt64</type>
<name>conversion_window_limit</name>
</argument>
<argument>
<type>String</type>
<name>breakdown_attribution_type</name>
</argument>
<argument>
<type>String</type>
<name>funnel_order_type</name>
</argument>
<argument>
<type>Array(Array(String))</type>
<name>prop_vals</name>
</argument>
<argument>
<type>Array(Tuple(Nullable(Float64), UUID, Nullable(String), Array(Int8)))</type>
<name>value</name>
</argument>
<format>JSONEachRow</format>
<command>aggregate_funnel_test.py</command>
<lifetime>600</lifetime>
</function>
<function>
<type>executable_pool</type>
<name>aggregate_funnel_trends</name>
<return_type>Array(Tuple(UInt64, Int8, Nullable(String)))</return_type>
<return_name>result</return_name>
<argument>
<type>UInt8</type>
<name>from_step</name>
</argument>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt64</type>
<name>conversion_window_limit</name>
</argument>
<argument>
<type>String</type>
<name>breakdown_attribution_type</name>
</argument>
<argument>
<type>String</type>
<name>funnel_order_type</name>
</argument>
<argument>
<type>Array(Nullable(String))</type>
<name>prop_vals</name>
</argument>
<argument>
<type>Array(Tuple(Nullable(Float64), UInt64, Nullable(String), Array(Int8)))</type>
<name>value</name>
</argument>
<format>JSONEachRow</format>
<command>aggregate_funnel trends</command>
<lifetime>600</lifetime>
</function>
<function>
<type>executable_pool</type>
<name>aggregate_funnel_array_trends</name>
<return_type>Array(Tuple(UInt64, Int8, Array(String)))</return_type>
<return_name>result</return_name>
<argument>
<type>UInt8</type>
<name>from_step</name>
</argument>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt64</type>
<name>conversion_window_limit</name>
</argument>
<argument>
<type>String</type>
<name>breakdown_attribution_type</name>
</argument>
<argument>
<type>String</type>
<name>funnel_order_type</name>
</argument>
<argument>
<type>Array(Array(String))</type>
<name>prop_vals</name>
</argument>
<argument>
<type>Array(Tuple(Nullable(Float64), UInt64, Array(String), Array(Int8)))</type>
<name>value</name>
</argument>
<format>JSONEachRow</format>
<command>aggregate_funnel trends</command>
<lifetime>600</lifetime>
</function>
<function>
<type>executable_pool</type>
<name>aggregate_funnel_cohort_trends</name>
<return_type>Array(Tuple(UInt64, Int8, UInt64))</return_type>
<return_name>result</return_name>
<argument>
<type>UInt8</type>
<name>from_step</name>
</argument>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt64</type>
<name>conversion_window_limit</name>
</argument>
<argument>
<type>String</type>
<name>breakdown_attribution_type</name>
</argument>
<argument>
<type>String</type>
<name>funnel_order_type</name>
</argument>
<argument>
<type>Array(UInt64)</type>
<name>prop_vals</name>
</argument>
<argument>
<type>Array(Tuple(Nullable(Float64), UInt64, UInt64, Array(Int8)))</type>
<name>value</name>
</argument>
<format>JSONEachRow</format>
<command>aggregate_funnel trends</command>
<lifetime>600</lifetime>
</function>
<function>
<type>executable_pool</type>
<name>aggregate_funnel_array_trends_test</name>
<return_type>String</return_type>
<return_name>result</return_name>
<argument>
<type>UInt8</type>
<name>from_step</name>
</argument>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt64</type>
<name>conversion_window_limit</name>
</argument>
<argument>
<type>String</type>
<name>breakdown_attribution_type</name>
</argument>
<argument>
<type>String</type>
<name>funnel_order_type</name>
</argument>
<argument>
<type>Array(Array(String))</type>
<name>prop_vals</name>
</argument>
<argument>
<type>Array(Tuple(Nullable(Float64), UInt64, Array(String), Array(Int8)))</type>
<name>value</name>
</argument>
<format>JSONEachRow</format>
<command>aggregate_funnel_array_trends_test.py</command>
<lifetime>600</lifetime>
</function>
<function>
<type>executable_pool</type>
<name>aggregate_funnel_v0</name>
<return_type>Array(Tuple(Int8, Nullable(String), Array(Float64), Array(Array(UUID))))</return_type>
<return_name>result</return_name>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt64</type>
<name>conversion_window_limit</name>
</argument>
<argument>
<type>String</type>
<name>breakdown_attribution_type</name>
</argument>
<argument>
<type>String</type>
<name>funnel_order_type</name>
</argument>
<argument>
<type>Array(Nullable(String))</type>
<name>prop_vals</name>
</argument>
<argument>
<type>Array(Tuple(Nullable(Float64), UUID, Nullable(String), Array(Int8)))</type>
<name>value</name>
</argument>
<format>JSONEachRow</format>
<command>v0/aggregate_funnel steps</command>
<lifetime>600</lifetime>
</function>
<function>
<type>executable_pool</type>
<name>aggregate_funnel_cohort_v0</name>
<return_type>Array(Tuple(Int8, UInt64, Array(Float64), Array(Array(UUID))))</return_type>
<return_name>result</return_name>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt64</type>
<name>conversion_window_limit</name>
</argument>
<argument>
<type>String</type>
<name>breakdown_attribution_type</name>
</argument>
<argument>
<type>String</type>
<name>funnel_order_type</name>
</argument>
<argument>
<type>Array(UInt64)</type>
<name>prop_vals</name>
</argument>
<argument>
<type>Array(Tuple(Nullable(Float64), UUID, UInt64, Array(Int8)))</type>
<name>value</name>
</argument>
<format>JSONEachRow</format>
<command>v0/aggregate_funnel steps</command>
<lifetime>600</lifetime>
</function>
<function>
<type>executable_pool</type>
<name>aggregate_funnel_array_v0</name>
<return_type>Array(Tuple(Int8, Array(String), Array(Float64), Array(Array(UUID))))</return_type>
<return_name>result</return_name>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt64</type>
<name>conversion_window_limit</name>
</argument>
<argument>
<type>String</type>
<name>breakdown_attribution_type</name>
</argument>
<argument>
<type>String</type>
<name>funnel_order_type</name>
</argument>
<argument>
<type>Array(Array(String))</type>
<name>prop_vals</name>
</argument>
<argument>
<type>Array(Tuple(Nullable(Float64), UUID, Array(String), Array(Int8)))</type>
<name>value</name>
</argument>
<format>JSONEachRow</format>
<command>v0/aggregate_funnel steps</command>
<lifetime>600</lifetime>
</function>
<function>
<type>executable_pool</type>
<name>aggregate_funnel_test_v0</name>
<return_type>String</return_type>
<return_name>result</return_name>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt64</type>
<name>conversion_window_limit</name>
</argument>
<argument>
<type>String</type>
<name>breakdown_attribution_type</name>
</argument>
<argument>
<type>String</type>
<name>funnel_order_type</name>
</argument>
<argument>
<type>Array(Array(String))</type>
<name>prop_vals</name>
</argument>
<argument>
<type>Array(Tuple(Nullable(Float64), UUID, Nullable(String), Array(Int8)))</type>
<name>value</name>
</argument>
<format>JSONEachRow</format>
<command>v0/aggregate_funnel_test.py</command>
<lifetime>600</lifetime>
</function>
<function>
<type>executable_pool</type>
<name>aggregate_funnel_trends_v0</name>
<return_type>Array(Tuple(UInt64, Int8, Nullable(String)))</return_type>
<return_name>result</return_name>
<argument>
<type>UInt8</type>
<name>from_step</name>
</argument>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt64</type>
<name>conversion_window_limit</name>
</argument>
<argument>
<type>String</type>
<name>breakdown_attribution_type</name>
</argument>
<argument>
<type>String</type>
<name>funnel_order_type</name>
</argument>
<argument>
<type>Array(Nullable(String))</type>
<name>prop_vals</name>
</argument>
<argument>
<type>Array(Tuple(Nullable(Float64), UInt64, Nullable(String), Array(Int8)))</type>
<name>value</name>
</argument>
<format>JSONEachRow</format>
<command>v0/aggregate_funnel trends</command>
<lifetime>600</lifetime>
</function>
<function>
<type>executable_pool</type>
<name>aggregate_funnel_array_trends_v0</name>
<return_type>Array(Tuple(UInt64, Int8, Array(String)))</return_type>
<return_name>result</return_name>
<argument>
<type>UInt8</type>
<name>from_step</name>
</argument>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt64</type>
<name>conversion_window_limit</name>
</argument>
<argument>
<type>String</type>
<name>breakdown_attribution_type</name>
</argument>
<argument>
<type>String</type>
<name>funnel_order_type</name>
</argument>
<argument>
<type>Array(Array(String))</type>
<name>prop_vals</name>
</argument>
<argument>
<type>Array(Tuple(Nullable(Float64), UInt64, Array(String), Array(Int8)))</type>
<name>value</name>
</argument>
<format>JSONEachRow</format>
<command>v0/aggregate_funnel trends</command>
<lifetime>600</lifetime>
</function>
<function>
<type>executable_pool</type>
<name>aggregate_funnel_cohort_trends_v0</name>
<return_type>Array(Tuple(UInt64, Int8, UInt64))</return_type>
<return_name>result</return_name>
<argument>
<type>UInt8</type>
<name>from_step</name>
</argument>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt64</type>
<name>conversion_window_limit</name>
</argument>
<argument>
<type>String</type>
<name>breakdown_attribution_type</name>
</argument>
<argument>
<type>String</type>
<name>funnel_order_type</name>
</argument>
<argument>
<type>Array(UInt64)</type>
<name>prop_vals</name>
</argument>
<argument>
<type>Array(Tuple(Nullable(Float64), UInt64, UInt64, Array(Int8)))</type>
<name>value</name>
</argument>
<format>JSONEachRow</format>
<command>v0/aggregate_funnel trends</command>
<lifetime>600</lifetime>
</function>
<function>
<type>executable_pool</type>
<name>aggregate_funnel_array_trends_test_v0</name>
<return_type>String</return_type>
<return_name>result</return_name>
<argument>
<type>UInt8</type>
<name>from_step</name>
</argument>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt64</type>
<name>conversion_window_limit</name>
</argument>
<argument>
<type>String</type>
<name>breakdown_attribution_type</name>
</argument>
<argument>
<type>String</type>
<name>funnel_order_type</name>
</argument>
<argument>
<type>Array(Array(String))</type>
<name>prop_vals</name>
</argument>
<argument>
<type>Array(Tuple(Nullable(Float64), UInt64, Array(String), Array(Int8)))</type>
<name>value</name>
</argument>
<format>JSONEachRow</format>
<command>v0/aggregate_funnel_array_trends_test.py</command>
<lifetime>600</lifetime>
</function>
<function>
<type>executable_pool</type>
<name>aggregate_funnel_v1</name>
<return_type>Array(Tuple(Int8, Nullable(String), Array(Float64), Array(Array(UUID))))</return_type>
@ -879,4 +293,297 @@ This file is autogenerated by udf_versioner.py. Do not edit this, only edit the
<command>v1/aggregate_funnel_array_trends_test.py</command>
<lifetime>600</lifetime>
</function>
<function>
<type>executable_pool</type>
<name>aggregate_funnel_v2</name>
<return_type>Array(Tuple(Int8, Nullable(String), Array(Float64), Array(Array(UUID))))</return_type>
<return_name>result</return_name>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt64</type>
<name>conversion_window_limit</name>
</argument>
<argument>
<type>String</type>
<name>breakdown_attribution_type</name>
</argument>
<argument>
<type>String</type>
<name>funnel_order_type</name>
</argument>
<argument>
<type>Array(Nullable(String))</type>
<name>prop_vals</name>
</argument>
<argument>
<type>Array(Tuple(Nullable(Float64), UUID, Nullable(String), Array(Int8)))</type>
<name>value</name>
</argument>
<format>JSONEachRow</format>
<command>v2/aggregate_funnel steps</command>
<lifetime>600</lifetime>
</function>
<function>
<type>executable_pool</type>
<name>aggregate_funnel_cohort_v2</name>
<return_type>Array(Tuple(Int8, UInt64, Array(Float64), Array(Array(UUID))))</return_type>
<return_name>result</return_name>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt64</type>
<name>conversion_window_limit</name>
</argument>
<argument>
<type>String</type>
<name>breakdown_attribution_type</name>
</argument>
<argument>
<type>String</type>
<name>funnel_order_type</name>
</argument>
<argument>
<type>Array(UInt64)</type>
<name>prop_vals</name>
</argument>
<argument>
<type>Array(Tuple(Nullable(Float64), UUID, UInt64, Array(Int8)))</type>
<name>value</name>
</argument>
<format>JSONEachRow</format>
<command>v2/aggregate_funnel steps</command>
<lifetime>600</lifetime>
</function>
<function>
<type>executable_pool</type>
<name>aggregate_funnel_array_v2</name>
<return_type>Array(Tuple(Int8, Array(String), Array(Float64), Array(Array(UUID))))</return_type>
<return_name>result</return_name>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt64</type>
<name>conversion_window_limit</name>
</argument>
<argument>
<type>String</type>
<name>breakdown_attribution_type</name>
</argument>
<argument>
<type>String</type>
<name>funnel_order_type</name>
</argument>
<argument>
<type>Array(Array(String))</type>
<name>prop_vals</name>
</argument>
<argument>
<type>Array(Tuple(Nullable(Float64), UUID, Array(String), Array(Int8)))</type>
<name>value</name>
</argument>
<format>JSONEachRow</format>
<command>v2/aggregate_funnel steps</command>
<lifetime>600</lifetime>
</function>
<function>
<type>executable_pool</type>
<name>aggregate_funnel_test_v2</name>
<return_type>String</return_type>
<return_name>result</return_name>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt64</type>
<name>conversion_window_limit</name>
</argument>
<argument>
<type>String</type>
<name>breakdown_attribution_type</name>
</argument>
<argument>
<type>String</type>
<name>funnel_order_type</name>
</argument>
<argument>
<type>Array(Array(String))</type>
<name>prop_vals</name>
</argument>
<argument>
<type>Array(Tuple(Nullable(Float64), UUID, Nullable(String), Array(Int8)))</type>
<name>value</name>
</argument>
<format>JSONEachRow</format>
<command>v2/aggregate_funnel_test.py</command>
<lifetime>600</lifetime>
</function>
<function>
<type>executable_pool</type>
<name>aggregate_funnel_trends_v2</name>
<return_type>Array(Tuple(UInt64, Int8, Nullable(String), UUID))</return_type>
<return_name>result</return_name>
<argument>
<type>UInt8</type>
<name>from_step</name>
</argument>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt64</type>
<name>conversion_window_limit</name>
</argument>
<argument>
<type>String</type>
<name>breakdown_attribution_type</name>
</argument>
<argument>
<type>String</type>
<name>funnel_order_type</name>
</argument>
<argument>
<type>Array(Nullable(String))</type>
<name>prop_vals</name>
</argument>
<argument>
<type>Array(Tuple(Nullable(Float64), UInt64, UUID, Nullable(String), Array(Int8)))</type>
<name>value</name>
</argument>
<format>JSONEachRow</format>
<command>v2/aggregate_funnel trends</command>
<lifetime>600</lifetime>
</function>
<function>
<type>executable_pool</type>
<name>aggregate_funnel_array_trends_v2</name>
<return_type>Array(Tuple(UInt64, Int8, Array(String), UUID))</return_type>
<return_name>result</return_name>
<argument>
<type>UInt8</type>
<name>from_step</name>
</argument>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt64</type>
<name>conversion_window_limit</name>
</argument>
<argument>
<type>String</type>
<name>breakdown_attribution_type</name>
</argument>
<argument>
<type>String</type>
<name>funnel_order_type</name>
</argument>
<argument>
<type>Array(Array(String))</type>
<name>prop_vals</name>
</argument>
<argument>
<type>Array(Tuple(Nullable(Float64), UInt64, UUID, Array(String), Array(Int8)))</type>
<name>value</name>
</argument>
<format>JSONEachRow</format>
<command>v2/aggregate_funnel trends</command>
<lifetime>600</lifetime>
</function>
<function>
<type>executable_pool</type>
<name>aggregate_funnel_cohort_trends_v2</name>
<return_type>Array(Tuple(UInt64, Int8, UInt64, UUID))</return_type>
<return_name>result</return_name>
<argument>
<type>UInt8</type>
<name>from_step</name>
</argument>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt64</type>
<name>conversion_window_limit</name>
</argument>
<argument>
<type>String</type>
<name>breakdown_attribution_type</name>
</argument>
<argument>
<type>String</type>
<name>funnel_order_type</name>
</argument>
<argument>
<type>Array(UInt64)</type>
<name>prop_vals</name>
</argument>
<argument>
<type>Array(Tuple(Nullable(Float64), UInt64, UUID, UInt64, Array(Int8)))</type>
<name>value</name>
</argument>
<format>JSONEachRow</format>
<command>v2/aggregate_funnel trends</command>
<lifetime>600</lifetime>
</function>
<function>
<type>executable_pool</type>
<name>aggregate_funnel_array_trends_test_v2</name>
<return_type>String</return_type>
<return_name>result</return_name>
<argument>
<type>UInt8</type>
<name>from_step</name>
</argument>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt64</type>
<name>conversion_window_limit</name>
</argument>
<argument>
<type>String</type>
<name>breakdown_attribution_type</name>
</argument>
<argument>
<type>String</type>
<name>funnel_order_type</name>
</argument>
<argument>
<type>Array(Array(String))</type>
<name>prop_vals</name>
</argument>
<argument>
<type>Array(Tuple(Nullable(Float64), UInt64, UUID, Array(String), Array(Int8)))</type>
<name>value</name>
</argument>
<format>JSONEachRow</format>
<command>v2/aggregate_funnel_array_trends_test.py</command>
<lifetime>600</lifetime>
</function>
</functions>

View File

@ -1,9 +0,0 @@
#!/bin/sh
DIR_NAME=$(dirname "$0")
case $( uname -m ) in
aarch64) $DIR_NAME/aggregate_funnel_aarch64 "$@";;
*) $DIR_NAME/aggregate_funnel_x86_64 "$@";;
esac

View File

@ -1,9 +0,0 @@
#!/usr/bin/python3
import sys
from aggregate_funnel_trends import parse_args, calculate_funnel_trends_from_user_events
if __name__ == "__main__":
for line in sys.stdin:
calculate_funnel_trends_from_user_events(*parse_args(line))
sys.stdout.flush()

View File

@ -1,13 +0,0 @@
#!/usr/bin/python3
import sys
import json
if __name__ == "__main__":
for line in sys.stdin:
try:
print(json.dumps({"result": line})) # noqa: T201
# calculate_funnel_trends_from_user_events(*parse_args(line))
except Exception as e:
print(json.dumps({"result": json.dumps(str(e))}), end="\n") # noqa: T201
sys.stdout.flush()

View File

@ -1,9 +0,0 @@
#!/usr/bin/python3
import sys
from aggregate_funnel_trends import parse_args, calculate_funnel_trends_from_user_events
if __name__ == "__main__":
for line in sys.stdin:
calculate_funnel_trends_from_user_events(*parse_args(line))
sys.stdout.flush()

View File

@ -1,14 +0,0 @@
#!/usr/bin/python3
import json
import sys
import traceback
if __name__ == "__main__":
for line in sys.stdin:
try:
# calculate_funnel_from_user_events(*parse_args(line))
print(json.dumps({"result": line})) # noqa: T201
except Exception as e:
print(json.dumps({"result": json.dumps(str(e) + traceback.format_exc())}), end="\n") # noqa: T201
sys.stdout.flush()

View File

@ -1,132 +0,0 @@
#!/usr/bin/python3
import sys
from dataclasses import dataclass, replace
from typing import Any, Union
from collections.abc import Sequence
import json
def parse_args(line):
args = json.loads(line)
return [
int(args["from_step"]),
int(args["num_steps"]),
int(args["conversion_window_limit"]),
str(args["breakdown_attribution_type"]),
str(args["funnel_order_type"]),
args["prop_vals"], # Array(Array(String))
args["value"], # Array(Tuple(Nullable(Float64), Nullable(DateTime), Array(String), Array(Int8)))
]
@dataclass(frozen=True)
class EnteredTimestamp:
timestamp: Any
timings: Any
# each one can be multiple steps here
# it only matters when they entered the funnel - you can propagate the time from the previous step when you update
# This function is defined for Clickhouse in user_defined_functions.xml along with types
# num_steps is the total number of steps in the funnel
# conversion_window_limit is in seconds
# events is a array of tuples of (timestamp, breakdown, [steps])
# steps is an array of integers which represent the steps that this event qualifies for. it looks like [1,3,5,6].
# negative integers represent an exclusion on that step. each event is either all exclusions or all steps.
def calculate_funnel_trends_from_user_events(
from_step: int,
num_steps: int,
conversion_window_limit_seconds: int,
breakdown_attribution_type: str,
funnel_order_type: str,
prop_vals: list[Any],
events: Sequence[tuple[float, int, Union[list[str], int, str], list[int]]],
):
default_entered_timestamp = EnteredTimestamp(0, [])
# If the attribution mode is a breakdown step, set this to the integer that represents that step
breakdown_step = int(breakdown_attribution_type[5:]) if breakdown_attribution_type.startswith("step_") else None
# Results is a map of start intervals to success or failure. If an interval isn't here, it means the
# user didn't enter
results = {}
# We call this for each possible breakdown value.
def loop_prop_val(prop_val):
# we need to track every distinct entry into the funnel through to the end
filtered_events = (
(
(timestamp, interval_start, breakdown, steps)
for (timestamp, interval_start, breakdown, steps) in events
if breakdown == prop_val
)
if breakdown_attribution_type == "all_events"
else events
)
interval_start_to_entered_timestamps = {}
for timestamp, interval_start, breakdown, steps in filtered_events:
for step in reversed(steps):
exclusion = False
if step < 0:
exclusion = True
step = -step
# Special code to handle the first step
# Potential Optimization: we could skip tracking here if the user has already completed the funnel for this interval
if step == 1:
if interval_start not in interval_start_to_entered_timestamps and interval_start not in results:
entered_timestamp = [default_entered_timestamp] * (num_steps + 1)
# Set the interval start at 0, which is what we want to return if this works.
# For strict funnels, we need to track if the "from_step" has been hit
# Abuse the timings field on the 0th index entered_timestamp to have the elt True if we have
entered_timestamp[0] = EnteredTimestamp(interval_start, [True] if from_step == 0 else [])
entered_timestamp[1] = EnteredTimestamp(timestamp, [timestamp])
interval_start_to_entered_timestamps[interval_start] = entered_timestamp
# list_of_entered_timestamps.append(entered_timestamp)
else:
for entered_timestamp in interval_start_to_entered_timestamps.values():
in_match_window = (
timestamp - entered_timestamp[step - 1].timestamp <= conversion_window_limit_seconds
)
already_reached_this_step_with_same_entered_timestamp = (
entered_timestamp[step].timestamp == entered_timestamp[step - 1].timestamp
)
if in_match_window and not already_reached_this_step_with_same_entered_timestamp:
if exclusion:
# this is a complete failure, exclude this person, don't print anything, don't count
return False
is_unmatched_step_attribution = (
breakdown_step is not None and step == breakdown_step - 1 and prop_val != breakdown
)
if not is_unmatched_step_attribution:
entered_timestamp[step] = replace(
entered_timestamp[step - 1],
timings=[*entered_timestamp[step - 1].timings, timestamp],
)
# check if we have hit the goal. if we have, remove it from the list and add it to the successful_timestamps
if entered_timestamp[num_steps].timestamp > 0:
results[entered_timestamp[0].timestamp] = (1, prop_val)
# If we have hit the from_step threshold, record it (abuse the timings field)
elif step == from_step + 1:
entered_timestamp[0].timings.append(True)
# At the end of the event, clear all steps that weren't done by that event
if funnel_order_type == "strict":
for entered_timestamp in interval_start_to_entered_timestamps.values():
for i in range(1, len(entered_timestamp)):
if i not in steps:
entered_timestamp[i] = default_entered_timestamp
# At this point, everything left in entered_timestamps is a failure, if it has made it to from_step
for entered_timestamp in interval_start_to_entered_timestamps.values():
if entered_timestamp[0].timestamp not in results and len(entered_timestamp[0].timings) > 0:
results[entered_timestamp[0].timestamp] = (-1, prop_val)
[loop_prop_val(prop_val) for prop_val in prop_vals]
result = [(interval_start, success_bool, prop_val) for interval_start, (success_bool, prop_val) in results.items()]
print(json.dumps({"result": result}), end="\n") # noqa: T201
if __name__ == "__main__":
for line in sys.stdin:
calculate_funnel_trends_from_user_events(*parse_args(line))
sys.stdout.flush()

View File

@ -1,589 +0,0 @@
<functions>
<!-- Version: v0. Generated at: 2024-10-10T09:56:46.897403+00:00
This file is autogenerated by udf_versioner.py. Do not edit this, only edit the version at docker/clickhouse/user_defined_function.xml--><function>
<type>executable_pool</type>
<name>aggregate_funnel</name>
<return_type>Array(Tuple(Int8, Nullable(String), Array(Float64), Array(Array(UUID))))</return_type>
<return_name>result</return_name>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt64</type>
<name>conversion_window_limit</name>
</argument>
<argument>
<type>String</type>
<name>breakdown_attribution_type</name>
</argument>
<argument>
<type>String</type>
<name>funnel_order_type</name>
</argument>
<argument>
<type>Array(Nullable(String))</type>
<name>prop_vals</name>
</argument>
<argument>
<type>Array(Tuple(Nullable(Float64), UUID, Nullable(String), Array(Int8)))</type>
<name>value</name>
</argument>
<format>JSONEachRow</format>
<command>aggregate_funnel steps</command>
<lifetime>600</lifetime>
</function>
<function>
<type>executable_pool</type>
<name>aggregate_funnel_cohort</name>
<return_type>Array(Tuple(Int8, UInt64, Array(Float64), Array(Array(UUID))))</return_type>
<return_name>result</return_name>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt64</type>
<name>conversion_window_limit</name>
</argument>
<argument>
<type>String</type>
<name>breakdown_attribution_type</name>
</argument>
<argument>
<type>String</type>
<name>funnel_order_type</name>
</argument>
<argument>
<type>Array(UInt64)</type>
<name>prop_vals</name>
</argument>
<argument>
<type>Array(Tuple(Nullable(Float64), UUID, UInt64, Array(Int8)))</type>
<name>value</name>
</argument>
<format>JSONEachRow</format>
<command>aggregate_funnel steps</command>
<lifetime>600</lifetime>
</function>
<function>
<type>executable_pool</type>
<name>aggregate_funnel_array</name>
<return_type>Array(Tuple(Int8, Array(String), Array(Float64), Array(Array(UUID))))</return_type>
<return_name>result</return_name>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt64</type>
<name>conversion_window_limit</name>
</argument>
<argument>
<type>String</type>
<name>breakdown_attribution_type</name>
</argument>
<argument>
<type>String</type>
<name>funnel_order_type</name>
</argument>
<argument>
<type>Array(Array(String))</type>
<name>prop_vals</name>
</argument>
<argument>
<type>Array(Tuple(Nullable(Float64), UUID, Array(String), Array(Int8)))</type>
<name>value</name>
</argument>
<format>JSONEachRow</format>
<command>aggregate_funnel steps</command>
<lifetime>600</lifetime>
</function>
<function>
<type>executable_pool</type>
<name>aggregate_funnel_test</name>
<return_type>String</return_type>
<return_name>result</return_name>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt64</type>
<name>conversion_window_limit</name>
</argument>
<argument>
<type>String</type>
<name>breakdown_attribution_type</name>
</argument>
<argument>
<type>String</type>
<name>funnel_order_type</name>
</argument>
<argument>
<type>Array(Array(String))</type>
<name>prop_vals</name>
</argument>
<argument>
<type>Array(Tuple(Nullable(Float64), UUID, Nullable(String), Array(Int8)))</type>
<name>value</name>
</argument>
<format>JSONEachRow</format>
<command>aggregate_funnel_test.py</command>
<lifetime>600</lifetime>
</function>
<function>
<type>executable_pool</type>
<name>aggregate_funnel_trends</name>
<return_type>Array(Tuple(UInt64, Int8, Nullable(String)))</return_type>
<return_name>result</return_name>
<argument>
<type>UInt8</type>
<name>from_step</name>
</argument>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt64</type>
<name>conversion_window_limit</name>
</argument>
<argument>
<type>String</type>
<name>breakdown_attribution_type</name>
</argument>
<argument>
<type>String</type>
<name>funnel_order_type</name>
</argument>
<argument>
<type>Array(Nullable(String))</type>
<name>prop_vals</name>
</argument>
<argument>
<type>Array(Tuple(Nullable(Float64), UInt64, Nullable(String), Array(Int8)))</type>
<name>value</name>
</argument>
<format>JSONEachRow</format>
<command>aggregate_funnel trends</command>
<lifetime>600</lifetime>
</function>
<function>
<type>executable_pool</type>
<name>aggregate_funnel_array_trends</name>
<return_type>Array(Tuple(UInt64, Int8, Array(String)))</return_type>
<return_name>result</return_name>
<argument>
<type>UInt8</type>
<name>from_step</name>
</argument>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt64</type>
<name>conversion_window_limit</name>
</argument>
<argument>
<type>String</type>
<name>breakdown_attribution_type</name>
</argument>
<argument>
<type>String</type>
<name>funnel_order_type</name>
</argument>
<argument>
<type>Array(Array(String))</type>
<name>prop_vals</name>
</argument>
<argument>
<type>Array(Tuple(Nullable(Float64), UInt64, Array(String), Array(Int8)))</type>
<name>value</name>
</argument>
<format>JSONEachRow</format>
<command>aggregate_funnel trends</command>
<lifetime>600</lifetime>
</function>
<function>
<type>executable_pool</type>
<name>aggregate_funnel_cohort_trends</name>
<return_type>Array(Tuple(UInt64, Int8, UInt64))</return_type>
<return_name>result</return_name>
<argument>
<type>UInt8</type>
<name>from_step</name>
</argument>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt64</type>
<name>conversion_window_limit</name>
</argument>
<argument>
<type>String</type>
<name>breakdown_attribution_type</name>
</argument>
<argument>
<type>String</type>
<name>funnel_order_type</name>
</argument>
<argument>
<type>Array(UInt64)</type>
<name>prop_vals</name>
</argument>
<argument>
<type>Array(Tuple(Nullable(Float64), UInt64, UInt64, Array(Int8)))</type>
<name>value</name>
</argument>
<format>JSONEachRow</format>
<command>aggregate_funnel trends</command>
<lifetime>600</lifetime>
</function>
<function>
<type>executable_pool</type>
<name>aggregate_funnel_array_trends_test</name>
<return_type>String</return_type>
<return_name>result</return_name>
<argument>
<type>UInt8</type>
<name>from_step</name>
</argument>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt64</type>
<name>conversion_window_limit</name>
</argument>
<argument>
<type>String</type>
<name>breakdown_attribution_type</name>
</argument>
<argument>
<type>String</type>
<name>funnel_order_type</name>
</argument>
<argument>
<type>Array(Array(String))</type>
<name>prop_vals</name>
</argument>
<argument>
<type>Array(Tuple(Nullable(Float64), UInt64, Array(String), Array(Int8)))</type>
<name>value</name>
</argument>
<format>JSONEachRow</format>
<command>aggregate_funnel_array_trends_test.py</command>
<lifetime>600</lifetime>
</function>
<function>
<type>executable_pool</type>
<name>aggregate_funnel_v0</name>
<return_type>Array(Tuple(Int8, Nullable(String), Array(Float64), Array(Array(UUID))))</return_type>
<return_name>result</return_name>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt64</type>
<name>conversion_window_limit</name>
</argument>
<argument>
<type>String</type>
<name>breakdown_attribution_type</name>
</argument>
<argument>
<type>String</type>
<name>funnel_order_type</name>
</argument>
<argument>
<type>Array(Nullable(String))</type>
<name>prop_vals</name>
</argument>
<argument>
<type>Array(Tuple(Nullable(Float64), UUID, Nullable(String), Array(Int8)))</type>
<name>value</name>
</argument>
<format>JSONEachRow</format>
<command>v0/aggregate_funnel steps</command>
<lifetime>600</lifetime>
</function>
<function>
<type>executable_pool</type>
<name>aggregate_funnel_cohort_v0</name>
<return_type>Array(Tuple(Int8, UInt64, Array(Float64), Array(Array(UUID))))</return_type>
<return_name>result</return_name>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt64</type>
<name>conversion_window_limit</name>
</argument>
<argument>
<type>String</type>
<name>breakdown_attribution_type</name>
</argument>
<argument>
<type>String</type>
<name>funnel_order_type</name>
</argument>
<argument>
<type>Array(UInt64)</type>
<name>prop_vals</name>
</argument>
<argument>
<type>Array(Tuple(Nullable(Float64), UUID, UInt64, Array(Int8)))</type>
<name>value</name>
</argument>
<format>JSONEachRow</format>
<command>v0/aggregate_funnel steps</command>
<lifetime>600</lifetime>
</function>
<function>
<type>executable_pool</type>
<name>aggregate_funnel_array_v0</name>
<return_type>Array(Tuple(Int8, Array(String), Array(Float64), Array(Array(UUID))))</return_type>
<return_name>result</return_name>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt64</type>
<name>conversion_window_limit</name>
</argument>
<argument>
<type>String</type>
<name>breakdown_attribution_type</name>
</argument>
<argument>
<type>String</type>
<name>funnel_order_type</name>
</argument>
<argument>
<type>Array(Array(String))</type>
<name>prop_vals</name>
</argument>
<argument>
<type>Array(Tuple(Nullable(Float64), UUID, Array(String), Array(Int8)))</type>
<name>value</name>
</argument>
<format>JSONEachRow</format>
<command>v0/aggregate_funnel steps</command>
<lifetime>600</lifetime>
</function>
<function>
<type>executable_pool</type>
<name>aggregate_funnel_test_v0</name>
<return_type>String</return_type>
<return_name>result</return_name>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt64</type>
<name>conversion_window_limit</name>
</argument>
<argument>
<type>String</type>
<name>breakdown_attribution_type</name>
</argument>
<argument>
<type>String</type>
<name>funnel_order_type</name>
</argument>
<argument>
<type>Array(Array(String))</type>
<name>prop_vals</name>
</argument>
<argument>
<type>Array(Tuple(Nullable(Float64), UUID, Nullable(String), Array(Int8)))</type>
<name>value</name>
</argument>
<format>JSONEachRow</format>
<command>v0/aggregate_funnel_test.py</command>
<lifetime>600</lifetime>
</function>
<function>
<type>executable_pool</type>
<name>aggregate_funnel_trends_v0</name>
<return_type>Array(Tuple(UInt64, Int8, Nullable(String)))</return_type>
<return_name>result</return_name>
<argument>
<type>UInt8</type>
<name>from_step</name>
</argument>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt64</type>
<name>conversion_window_limit</name>
</argument>
<argument>
<type>String</type>
<name>breakdown_attribution_type</name>
</argument>
<argument>
<type>String</type>
<name>funnel_order_type</name>
</argument>
<argument>
<type>Array(Nullable(String))</type>
<name>prop_vals</name>
</argument>
<argument>
<type>Array(Tuple(Nullable(Float64), UInt64, Nullable(String), Array(Int8)))</type>
<name>value</name>
</argument>
<format>JSONEachRow</format>
<command>v0/aggregate_funnel trends</command>
<lifetime>600</lifetime>
</function>
<function>
<type>executable_pool</type>
<name>aggregate_funnel_array_trends_v0</name>
<return_type>Array(Tuple(UInt64, Int8, Array(String)))</return_type>
<return_name>result</return_name>
<argument>
<type>UInt8</type>
<name>from_step</name>
</argument>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt64</type>
<name>conversion_window_limit</name>
</argument>
<argument>
<type>String</type>
<name>breakdown_attribution_type</name>
</argument>
<argument>
<type>String</type>
<name>funnel_order_type</name>
</argument>
<argument>
<type>Array(Array(String))</type>
<name>prop_vals</name>
</argument>
<argument>
<type>Array(Tuple(Nullable(Float64), UInt64, Array(String), Array(Int8)))</type>
<name>value</name>
</argument>
<format>JSONEachRow</format>
<command>v0/aggregate_funnel trends</command>
<lifetime>600</lifetime>
</function>
<function>
<type>executable_pool</type>
<name>aggregate_funnel_cohort_trends_v0</name>
<return_type>Array(Tuple(UInt64, Int8, UInt64))</return_type>
<return_name>result</return_name>
<argument>
<type>UInt8</type>
<name>from_step</name>
</argument>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt64</type>
<name>conversion_window_limit</name>
</argument>
<argument>
<type>String</type>
<name>breakdown_attribution_type</name>
</argument>
<argument>
<type>String</type>
<name>funnel_order_type</name>
</argument>
<argument>
<type>Array(UInt64)</type>
<name>prop_vals</name>
</argument>
<argument>
<type>Array(Tuple(Nullable(Float64), UInt64, UInt64, Array(Int8)))</type>
<name>value</name>
</argument>
<format>JSONEachRow</format>
<command>v0/aggregate_funnel trends</command>
<lifetime>600</lifetime>
</function>
<function>
<type>executable_pool</type>
<name>aggregate_funnel_array_trends_test_v0</name>
<return_type>String</return_type>
<return_name>result</return_name>
<argument>
<type>UInt8</type>
<name>from_step</name>
</argument>
<argument>
<type>UInt8</type>
<name>num_steps</name>
</argument>
<argument>
<type>UInt64</type>
<name>conversion_window_limit</name>
</argument>
<argument>
<type>String</type>
<name>breakdown_attribution_type</name>
</argument>
<argument>
<type>String</type>
<name>funnel_order_type</name>
</argument>
<argument>
<type>Array(Array(String))</type>
<name>prop_vals</name>
</argument>
<argument>
<type>Array(Tuple(Nullable(Float64), UInt64, Array(String), Array(Int8)))</type>
<name>value</name>
</argument>
<format>JSONEachRow</format>
<command>v0/aggregate_funnel_array_trends_test.py</command>
<lifetime>600</lifetime>
</function>
</functions>