aboutsummaryrefslogtreecommitdiff
path: root/tests/models/thl/test_user_streak.py
blob: 72efd058feff965d54bae2790a9658c61083ec10 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
from datetime import datetime, timedelta
from zoneinfo import ZoneInfo

import pytest
from pydantic import ValidationError

from generalresearch.models.thl.user_streak import (
    UserStreak,
    StreakPeriod,
    StreakFulfillment,
    StreakState,
)


def test_user_streak_empty_fail():
    us = UserStreak(
        period=StreakPeriod.DAY,
        fulfillment=StreakFulfillment.COMPLETE,
        country_iso="us",
        user_id=1,
        last_fulfilled_period_start=None,
        current_streak=0,
        longest_streak=0,
        state=StreakState.BROKEN,
    )
    assert us.time_remaining_in_period is None

    with pytest.raises(
        ValidationError, match="StreakState.BROKEN but current_streak not 0"
    ):
        UserStreak(
            period=StreakPeriod.DAY,
            fulfillment=StreakFulfillment.COMPLETE,
            country_iso="us",
            user_id=1,
            last_fulfilled_period_start=None,
            current_streak=1,
            longest_streak=0,
            state=StreakState.BROKEN,
        )

    with pytest.raises(
        ValidationError, match="Current streak can't be longer than longest streak"
    ):
        UserStreak(
            period=StreakPeriod.DAY,
            fulfillment=StreakFulfillment.COMPLETE,
            country_iso="us",
            user_id=1,
            last_fulfilled_period_start=None,
            current_streak=1,
            longest_streak=0,
            state=StreakState.ACTIVE,
        )


def test_user_streak_remaining():
    us = UserStreak(
        period=StreakPeriod.DAY,
        fulfillment=StreakFulfillment.COMPLETE,
        country_iso="us",
        user_id=1,
        last_fulfilled_period_start=None,
        current_streak=1,
        longest_streak=1,
        state=StreakState.AT_RISK,
    )
    now = datetime.now(tz=ZoneInfo("America/New_York"))
    end_of_today = now.replace(hour=0, minute=0, second=0, microsecond=0) + timedelta(
        days=1
    )
    print(f"{now.isoformat()=}, {end_of_today.isoformat()=}")
    expected = (end_of_today - now).total_seconds()
    assert us.time_remaining_in_period.total_seconds() == pytest.approx(expected, abs=1)


def test_user_streak_remaining_month():
    us = UserStreak(
        period=StreakPeriod.MONTH,
        fulfillment=StreakFulfillment.COMPLETE,
        country_iso="us",
        user_id=1,
        last_fulfilled_period_start=None,
        current_streak=1,
        longest_streak=1,
        state=StreakState.AT_RISK,
    )
    now = datetime.now(tz=ZoneInfo("America/New_York"))
    end_of_month = (
        now.replace(day=1, hour=0, minute=0, second=0, microsecond=0)
        + timedelta(days=32)
    ).replace(day=1)
    print(f"{now.isoformat()=}, {end_of_month.isoformat()=}")
    expected = (end_of_month - now).total_seconds()
    assert us.time_remaining_in_period.total_seconds() == pytest.approx(expected, abs=1)
    print(us.time_remaining_in_period)