Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: weekly digest #26337

Open
wants to merge 2 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
200 changes: 193 additions & 7 deletions posthog/tasks/test/test_usage_report.py
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
from datetime import datetime
from datetime import datetime, timedelta
from typing import Any
from unittest.mock import ANY, MagicMock, Mock, call, patch
from uuid import uuid4
Expand All @@ -23,12 +23,18 @@
from posthog.models.app_metrics2.sql import TRUNCATE_APP_METRICS2_TABLE_SQL
from posthog.models.dashboard import Dashboard
from posthog.models.event.util import create_event
from posthog.models.event_definition import EventDefinition
from posthog.models.experiment import Experiment
from posthog.models.feature_flag import FeatureFlag
from posthog.models.feedback.survey import Survey
from posthog.models.group.util import create_group
from posthog.models.group_type_mapping import GroupTypeMapping
from posthog.models.plugin import PluginConfig
from posthog.models.sharing_configuration import SharingConfiguration
from posthog.schema import EventsQuery
from posthog.session_recordings.models.session_recording_playlist import (
SessionRecordingPlaylist,
)
from posthog.session_recordings.queries.test.session_replay_sql import (
produce_replay_summary,
)
Expand All @@ -49,6 +55,7 @@
APIBaseTest,
ClickhouseDestroyTablesMixin,
ClickhouseTestMixin,
QueryMatchingTest,
_create_event,
_create_person,
also_test_with_materialized_columns,
Expand Down Expand Up @@ -139,7 +146,7 @@


@freeze_time("2022-01-10T00:01:00Z")
class UsageReport(APIBaseTest, ClickhouseTestMixin, ClickhouseDestroyTablesMixin):
class UsageReport(APIBaseTest, ClickhouseTestMixin, ClickhouseDestroyTablesMixin, QueryMatchingTest):
def setUp(self) -> None:
super().setUp()

Expand Down Expand Up @@ -807,6 +814,10 @@
mock_posthog = MagicMock()
mock_client.return_value = mock_posthog

# # make a dashboard for the team created within the last 7 days
# with freeze_time("2022-01-08T00:01:00Z"):
# Dashboard.objects.create(name="Test Dashboard", team=self.team)

all_reports = self._test_usage_report()
with self.settings(SITE_URL="http://test.posthog.com"):
send_all_org_usage_reports()
Expand Down Expand Up @@ -835,6 +846,181 @@
mock_posthog.capture.assert_has_calls(calls, any_order=True)


@freeze_time("2024-01-01T00:01:00Z") # A Monday
class TestWeeklyDigestReport(ClickhouseDestroyTablesMixin, APIBaseTest):
def setUp(self) -> None:
super().setUp()
self.distinct_id = str(uuid4())
self.one_week_ago = now() - timedelta(days=7)

@patch("posthog.tasks.usage_report.Client")
def test_weekly_digest_report(self, mock_client: MagicMock) -> None:
# Create test data from "last week"
with freeze_time(self.one_week_ago):
# Create a dashboard
dashboard = Dashboard.objects.create(
team=self.team,
name="Test Dashboard",
created_at=now(),
)

# Create an event definition
event_definition = EventDefinition.objects.create(
team=self.team,
name="Test Event",
created_at=now(),
)

# Create a playlist
playlist = SessionRecordingPlaylist.objects.create(
team=self.team,
name="Test Playlist",
created_at=now(),
)

# Create experiments
# this flag should not be included in the digest
flag_for_launched_experiment = FeatureFlag.objects.create(
team=self.team,
name="Feature Flag for Experiment My experiment 1",
key="flag-for-launched-experiment",
created_at=now(),
)
launched_experiment = Experiment.objects.create(
team=self.team,
name="Launched Experiment",
created_at=now(),
start_date=now(),
feature_flag=flag_for_launched_experiment,
)

# this flag should not e included in the digest
flag_for_completed_experiment = FeatureFlag.objects.create(
team=self.team,
name="Feature Flag for Experiment My experiment 2",
key="feature-flag-for-completed-experiment",
created_at=now(),
)
completed_experiment = Experiment.objects.create(
team=self.team,
name="Completed Experiment",
created_at=now(),
start_date=now() - timedelta(days=2),
end_date=now(),
feature_flag=flag_for_completed_experiment,
)

# Create external data source
external_data_source = ExternalDataSource.objects.create(
team=self.team,
source_id="test_source",
connection_id="test_connection",
status="completed",
source_type="Stripe",
created_at=now(),
)

# Create a survey
# this flag should not be included in the digest since it's generated for the survey
flag_for_survey = FeatureFlag.objects.create(
team=self.team,
name="Targeting flag for survey My survey",
key="feature-flag-for-survey",
created_at=now(),
)
survey = Survey.objects.create(
team=self.team,
name="Test Survey",
description="Test Description",
created_at=now(),
start_date=now(),
targeting_flag=flag_for_survey,
)

# Create a feature flag
feature_flag = FeatureFlag.objects.create(
team=self.team,
name="Test Flag",
key="test-flag",
created_at=now(),
)

# Run the usage report task
mock_posthog = MagicMock()
mock_client.return_value = mock_posthog

period = get_previous_day()
period_start, period_end = period
_get_all_org_reports(period_start, period_end)

# Check that the capture event was called with the correct data
calls = mock_posthog.capture.call_args_list
weekly_digest_call = next(call for call in calls if call[0][1] == "weekly digest report")
properties = weekly_digest_call[0][2]

expected_properties = {
"team_id": self.team.id,
"team_name": self.team.name,
"scope": "machine",
"new_dashboards_in_last_7_days": [
{
"name": "Test Dashboard",
"id": dashboard.id,
}
],
"new_event_definitions_in_last_7_days": [
{
"name": "Test Event",
"id": event_definition.id,
}
],
"new_playlists_created_in_last_7_days": [
{
"name": "Test Playlist",
"id": playlist.short_id,
}
],
"new_experiments_launched_in_last_7_days": [
{
"name": "Launched Experiment",
"id": launched_experiment.id,
"start_date": launched_experiment.start_date.isoformat(),

Check failure on line 987 in posthog/tasks/test/test_usage_report.py

View workflow job for this annotation

GitHub Actions / Python code quality checks

Item "None" of "datetime | None" has no attribute "isoformat"
}
],
"new_experiments_completed_in_last_7_days": [
{
"name": "Completed Experiment",
"id": completed_experiment.id,
"start_date": completed_experiment.start_date.isoformat(),

Check failure on line 994 in posthog/tasks/test/test_usage_report.py

View workflow job for this annotation

GitHub Actions / Python code quality checks

Item "None" of "datetime | None" has no attribute "isoformat"
"end_date": completed_experiment.end_date.isoformat(),

Check failure on line 995 in posthog/tasks/test/test_usage_report.py

View workflow job for this annotation

GitHub Actions / Python code quality checks

Item "None" of "datetime | None" has no attribute "isoformat"
}
],
"new_external_data_sources_connected_in_last_7_days": [
{
"source_type": "Stripe",
"id": external_data_source.id,
}
],
"new_surveys_launched_in_last_7_days": [
{
"name": "Test Survey",
"id": survey.id,
"start_date": survey.start_date.isoformat(),

Check failure on line 1008 in posthog/tasks/test/test_usage_report.py

View workflow job for this annotation

GitHub Actions / Python code quality checks

Item "None" of "datetime | None" has no attribute "isoformat"
"description": "Test Description",
}
],
"new_feature_flags_created_in_last_7_days": [
{
"name": "Test Flag",
"id": feature_flag.id,
"key": "test-flag",
}
],
}

assert properties == expected_properties


@freeze_time("2022-01-09T00:01:00Z")
class ReplayUsageReport(APIBaseTest, ClickhouseTestMixin, ClickhouseDestroyTablesMixin):
@also_test_with_materialized_columns(event_properties=["$lib"], verify_no_jsonextract=False)
Expand Down Expand Up @@ -1553,11 +1739,11 @@
mock_posthog = MagicMock()
mock_client.return_value = mock_posthog
capture_event(
mock_client,
"test event",
organization.id,
{"prop1": "val1"},
"2021-10-10T23:01:00.00Z",
pha_client=mock_client,
name="test event",
organization_id=organization.id,
properties={"prop1": "val1"},
timestamp="2021-10-10T23:01:00.00Z",
)
assert mock_client.capture.call_args[1]["timestamp"] == datetime(2021, 10, 10, 23, 1, tzinfo=tzutc())

Expand Down
Loading
Loading