Exemplo n.º 1
0
    def _calculate_trends(self, filter: Filter,
                          team: Team) -> List[Dict[str, Any]]:
        # format default dates

        if not filter._date_from:
            filter._date_from = relative_date_parse("-7d")
        if not filter._date_to:
            filter._date_to = timezone.now()

        result = []
        for entity in filter.entities:
            if filter.compare:
                compare_filter = determine_compared_filter(filter=filter)
                entity_result = self._serialize_entity(entity, filter, team)
                entity_result = convert_to_comparison(
                    entity_result, filter,
                    "{} - {}".format(entity.name, "current"))
                result.extend(entity_result)
                previous_entity_result = self._serialize_entity(
                    entity, compare_filter, team)
                previous_entity_result = convert_to_comparison(
                    previous_entity_result, filter,
                    "{} - {}".format(entity.name, "previous"))
                result.extend(previous_entity_result)
            else:
                entity_result = self._serialize_entity(entity, filter, team)
                result.extend(entity_result)

        return result
Exemplo n.º 2
0
    def calculate_list(self, filter: Filter, team: Team, limit: int,
                       offset: int):
        filters, params = parse_prop_clauses("uuid", filter.properties, team)

        if not filter._date_from:
            filter._date_from = timezone.now().replace(hour=0,
                                                       minute=0,
                                                       second=0,
                                                       microsecond=0)
        if not filter._date_to and filter.date_from:
            filter._date_to = filter.date_from + relativedelta(days=1)

        date_from, date_to = parse_timestamps(filter)
        params = {
            **params, "team_id": team.pk,
            "limit": limit,
            "offset": offset
        }
        query = SESSION_SQL.format(
            date_from=date_from,
            date_to=date_to,
            filters="{}".format(filters) if filter.properties else "",
            sessions_limit="LIMIT %(offset)s, %(limit)s",
        )
        query_result = sync_execute(query, params)
        result = self._parse_list_results(query_result)

        self._add_person_properties(team, result)

        return result
Exemplo n.º 3
0
    def calculate_paths(self, filter: Filter, team: Team):

        # format default dates
        if not filter._date_from:
            filter._date_from = relative_date_parse("-7d")
        if not filter._date_to:
            filter._date_to = timezone.now()

        parsed_date_from, parsed_date_to = parse_timestamps(filter=filter)
        event, path_type, start_comparator = self._determine_path_type(filter.path_type if filter else None)

        prop_filters, prop_filter_params = parse_prop_clauses("uuid", filter.properties, team)

        # Step 0. Event culling subexpression for step 1.
        # Make an expression that removes events in a session that are definitely unused.
        # For example the 4th, 5th, etc row after a "new_session = 1" or "marked_session_start = 1" row gets removed
        excess_row_filter = "("
        for i in range(4):
            if i > 0:
                excess_row_filter += " or "
            excess_row_filter += "neighbor(new_session, {}, 0) = 1".format(-i)
            if filter and filter.start_point:
                excess_row_filter += " or neighbor(marked_session_start, {}, 0) = 1".format(-i)
        excess_row_filter += ")"

        paths_query = PATHS_QUERY_FINAL.format(
            event_query="event = %(event)s"
            if event
            else "event NOT IN ('$autocapture', '$pageview', '$identify', '$pageleave', '$screen')",
            path_type=path_type,
            parsed_date_from=parsed_date_from,
            parsed_date_to=parsed_date_to,
            filters=prop_filters if filter.properties else "",
            marked_session_start="{} = %(start_point)s".format(start_comparator)
            if filter and filter.start_point
            else "new_session",
            excess_row_filter=excess_row_filter,
            select_elements_chain=", events.elements_chain as elements_chain" if event == AUTOCAPTURE_EVENT else "",
            group_by_elements_chain=", events.elements_chain" if event == AUTOCAPTURE_EVENT else "",
        )

        params: Dict = {
            "team_id": team.pk,
            "property": "$current_url",
            "event": event,
            "start_point": filter.start_point,
        }
        params = {**params, **prop_filter_params}

        rows = sync_execute(paths_query, params)

        resp: List[Dict[str, str]] = []
        for row in rows:
            resp.append(
                {"source": row[0], "source_id": row[1], "target": row[2], "target_id": row[3], "value": row[4],}
            )

        resp = sorted(resp, key=lambda x: x["value"], reverse=True)
        return resp
    def _calculate_stickiness(self, filter: Filter, team: Team) -> List[Dict[str, Any]]:
        if not filter._date_from:
            filter._date_from = relative_date_parse("-7d")
        if not filter._date_to:
            filter._date_to = timezone.now()

        result = []

        for entity in filter.entities:
            if entity.type == TREND_FILTER_TYPE_ACTIONS:
                entity.name = Action.objects.only("name").get(team=team, pk=entity.id).name
            entity_result = self._serialize_entity(entity, filter, team)
            result.extend(entity_result)

        return result
Exemplo n.º 5
0
    def calculate_retention(self, filter: Filter, team: Team,
                            total_intervals: int) -> List[Dict[str, Any]]:

        period = filter.period or "Day"

        tdelta, trunc_func, t1 = self._determineTimedelta(
            total_intervals, period)

        filter._date_to = ((filter.date_to if filter.date_to else now()) +
                           t1).isoformat()

        if period == "Hour":
            date_to = filter.date_to if filter.date_to else now()
            date_from = date_to - tdelta
        else:
            date_to = (filter.date_to if filter.date_to else now()).replace(
                hour=0, minute=0, second=0, microsecond=0)
            date_from = date_to - tdelta

        filter._date_from = date_from.isoformat()
        filter._date_to = date_to.isoformat()

        prop_filters, prop_filter_params = parse_prop_clauses(
            filter.properties, team)

        target_query = ""
        target_params: Dict = {}

        target_entity = (Entity({
            "id": "$pageview",
            "type": TREND_FILTER_TYPE_EVENTS
        }) if not filter.target_entity else filter.target_entity)
        if target_entity.type == TREND_FILTER_TYPE_ACTIONS:
            action = Action.objects.get(pk=target_entity.id)
            action_query, target_params = format_action_filter(action,
                                                               use_loop=True)
            target_query = "AND e.uuid IN ({})".format(action_query)
        elif target_entity.type == TREND_FILTER_TYPE_EVENTS:
            target_query = "AND e.event = %(target_event)s"
            target_params = {"target_event": target_entity.id}

        result = sync_execute(
            RETENTION_SQL.format(
                target_query=target_query,
                filters="{filters}".format(
                    filters=prop_filters) if filter.properties else "",
                trunc_func=trunc_func,
            ),
            {
                "team_id":
                team.pk,
                "start_date":
                date_from.strftime("%Y-%m-%d{}".format(
                    " %H:%M:%S" if filter.period == "Hour" else " 00:00:00")),
                "end_date":
                date_to.strftime("%Y-%m-%d{}".format(
                    " %H:%M:%S" if filter.period == "Hour" else " 00:00:00")),
                **prop_filter_params,
                **target_params,
                "period":
                period,
            },
        )

        result_dict = {}

        for res in result:
            result_dict.update({
                (res[0], res[1]): {
                    "count": res[2],
                    "people": []
                }
            })

        if period == "Week":
            date_from = date_from - timedelta(days=date_from.isoweekday() % 7)

        parsed = [{
            "values": [
                result_dict.get((first_day, day), {
                    "count": 0,
                    "people": []
                }) for day in range(total_intervals - first_day)
            ],
            "label":
            "{} {}".format(period, first_day),
            "date":
            (date_from + self._determineTimedelta(first_day, period)[0]),
        } for first_day in range(total_intervals)]

        return parsed
Exemplo n.º 6
0
 def _set_default_dates(self, filter: Filter, team_id: int) -> None:
     if not filter._date_from:
         filter._date_from = relative_date_parse("-7d")
     if not filter._date_to:
         filter._date_to = timezone.now()