Files
notifications-api/tests/app/service/test_statistics_rest.py
Rebecca Law 0675f09afb Need to be able to query the notification statistics for the right number of days.
If the request is for the big numbers on the activity page, then we need to use the number right number of days.
Added an end point to get the data retention for the service and notification type, which is needed on the activity page to say how long the report is available for.
2018-07-23 09:56:04 +01:00

323 lines
12 KiB
Python

import uuid
from datetime import datetime
import pytest
from freezegun import freeze_time
from app.celery.scheduled_tasks import daily_stats_template_usage_by_month
from app.models import (
EMAIL_TYPE,
SMS_TYPE,
LETTER_TYPE,
PRECOMPILED_TEMPLATE_NAME,
KEY_TYPE_TEST,
KEY_TYPE_TEAM,
KEY_TYPE_NORMAL,
)
from tests.app.db import (
create_service,
create_template,
create_notification,
create_ft_notification_status
)
@freeze_time('2017-11-11 02:00')
def test_get_template_usage_by_month_returns_correct_data(
admin_request,
sample_template
):
create_notification(sample_template, created_at=datetime(2016, 4, 1), status='created')
create_notification(sample_template, created_at=datetime(2017, 4, 1), status='sending')
create_notification(sample_template, created_at=datetime(2017, 4, 1), status='permanent-failure')
create_notification(sample_template, created_at=datetime(2017, 4, 1), status='temporary-failure')
daily_stats_template_usage_by_month()
create_notification(sample_template, created_at=datetime.utcnow())
resp_json = admin_request.get(
'service.get_monthly_template_usage',
service_id=sample_template.service_id,
year=2017
)
resp_json = resp_json['stats']
assert len(resp_json) == 2
assert resp_json[0]["template_id"] == str(sample_template.id)
assert resp_json[0]["name"] == sample_template.name
assert resp_json[0]["type"] == sample_template.template_type
assert resp_json[0]["month"] == 4
assert resp_json[0]["year"] == 2017
assert resp_json[0]["count"] == 3
assert resp_json[1]["template_id"] == str(sample_template.id)
assert resp_json[1]["name"] == sample_template.name
assert resp_json[1]["type"] == sample_template.template_type
assert resp_json[1]["month"] == 11
assert resp_json[1]["year"] == 2017
assert resp_json[1]["count"] == 1
@freeze_time('2017-11-11 02:00')
def test_get_template_usage_by_month_returns_no_data(admin_request, sample_template):
create_notification(sample_template, created_at=datetime(2016, 4, 1), status='created')
daily_stats_template_usage_by_month()
create_notification(sample_template, created_at=datetime.utcnow())
resp_json = admin_request.get(
'service.get_monthly_template_usage',
service_id=sample_template.service_id,
year=2015
)
assert resp_json['stats'] == []
@freeze_time('2017-11-11 02:00')
def test_get_template_usage_by_month_returns_two_templates(admin_request, sample_template, sample_service):
template_one = create_template(
sample_service,
template_type=LETTER_TYPE,
template_name=PRECOMPILED_TEMPLATE_NAME,
hidden=True
)
create_notification(template_one, created_at=datetime(2017, 4, 1), status='created')
create_notification(sample_template, created_at=datetime(2017, 4, 1), status='sending')
create_notification(sample_template, created_at=datetime(2017, 4, 1), status='permanent-failure')
create_notification(sample_template, created_at=datetime(2017, 4, 1), status='temporary-failure')
daily_stats_template_usage_by_month()
create_notification(sample_template, created_at=datetime.utcnow())
resp_json = admin_request.get(
'service.get_monthly_template_usage',
service_id=sample_template.service_id,
year=2017
)
resp_json = sorted(resp_json['stats'], key=lambda k: (k['year'], k['month'], k['count']))
assert len(resp_json) == 3
assert resp_json[0]["template_id"] == str(template_one.id)
assert resp_json[0]["name"] == template_one.name
assert resp_json[0]["type"] == template_one.template_type
assert resp_json[0]["month"] == 4
assert resp_json[0]["year"] == 2017
assert resp_json[0]["count"] == 1
assert resp_json[0]["is_precompiled_letter"] is True
assert resp_json[1]["template_id"] == str(sample_template.id)
assert resp_json[1]["name"] == sample_template.name
assert resp_json[1]["type"] == sample_template.template_type
assert resp_json[1]["month"] == 4
assert resp_json[1]["year"] == 2017
assert resp_json[1]["count"] == 3
assert resp_json[1]["is_precompiled_letter"] is False
assert resp_json[2]["template_id"] == str(sample_template.id)
assert resp_json[2]["name"] == sample_template.name
assert resp_json[2]["type"] == sample_template.template_type
assert resp_json[2]["month"] == 11
assert resp_json[2]["year"] == 2017
assert resp_json[2]["count"] == 1
assert resp_json[2]["is_precompiled_letter"] is False
@pytest.mark.parametrize('today_only, limit_days, stats', [
(False, 7, {'requested': 2, 'delivered': 1, 'failed': 0}),
(True, 7, {'requested': 1, 'delivered': 0, 'failed': 0})
], ids=['seven_days', 'today'])
def test_get_service_notification_statistics(admin_request, sample_template, today_only, limit_days, stats):
with freeze_time('2000-01-01T12:00:00'):
create_notification(sample_template, status='delivered')
with freeze_time('2000-01-02T12:00:00'):
create_notification(sample_template, status='created')
resp = admin_request.get(
'service.get_service_notification_statistics',
service_id=sample_template.service_id,
today_only=today_only,
limit_days=limit_days
)
assert set(resp['data'].keys()) == {SMS_TYPE, EMAIL_TYPE, LETTER_TYPE}
assert resp['data'][SMS_TYPE] == stats
def test_get_service_notification_statistics_with_unknown_service(admin_request):
resp = admin_request.get(
'service.get_service_notification_statistics',
service_id=uuid.uuid4(),
limit_days=7
)
assert resp['data'] == {
SMS_TYPE: {'requested': 0, 'delivered': 0, 'failed': 0},
EMAIL_TYPE: {'requested': 0, 'delivered': 0, 'failed': 0},
LETTER_TYPE: {'requested': 0, 'delivered': 0, 'failed': 0},
}
@pytest.mark.parametrize('kwargs, expected_json', [
({'year': 'baz'}, {'message': 'Year must be a number', 'result': 'error'}),
({}, {'message': 'Year must be a number', 'result': 'error'}),
])
def test_get_monthly_notification_stats_returns_errors(admin_request, sample_service, kwargs, expected_json):
response = admin_request.get(
'service.get_monthly_notification_stats',
service_id=sample_service.id,
_expected_status=400,
**kwargs
)
assert response == expected_json
def test_get_monthly_notification_stats_returns_404_if_no_service(admin_request):
response = admin_request.get(
'service.get_monthly_notification_stats',
service_id=uuid.uuid4(),
_expected_status=404,
)
assert response == {'message': 'No result found', 'result': 'error'}
def test_get_monthly_notification_stats_returns_empty_stats_with_correct_dates(admin_request, sample_service):
response = admin_request.get(
'service.get_monthly_notification_stats',
service_id=sample_service.id,
year=2016
)
assert len(response['data']) == 12
keys = [
'2016-04', '2016-05', '2016-06', '2016-07', '2016-08', '2016-09', '2016-10', '2016-11', '2016-12',
'2017-01', '2017-02', '2017-03'
]
assert sorted(response['data'].keys()) == keys
for val in response['data'].values():
assert val == {'sms': {}, 'email': {}, 'letter': {}}
def test_get_monthly_notification_stats_returns_stats(admin_request, sample_service):
sms_t1 = create_template(sample_service)
sms_t2 = create_template(sample_service)
email_template = create_template(sample_service, template_type=EMAIL_TYPE)
create_ft_notification_status(datetime(2016, 6, 1), template=sms_t1)
create_ft_notification_status(datetime(2016, 6, 2), template=sms_t1)
create_ft_notification_status(datetime(2016, 7, 1), template=sms_t1)
create_ft_notification_status(datetime(2016, 7, 1), template=sms_t2)
create_ft_notification_status(datetime(2016, 7, 1), template=sms_t1, notification_status='created')
create_ft_notification_status(datetime(2016, 7, 1), template=email_template)
response = admin_request.get(
'service.get_monthly_notification_stats',
service_id=sample_service.id,
year=2016
)
assert len(response['data']) == 12
assert response['data']['2016-06'] == {
'sms': {
# it combines the two days
'delivered': 2
},
'email': {},
'letter': {}
}
assert response['data']['2016-07'] == {
# it combines the two template types
'sms': {
'created': 1,
'delivered': 2,
},
'email': {
'delivered': 1
},
'letter': {}
}
@freeze_time('2016-06-05 12:00:00')
def test_get_monthly_notification_stats_combines_todays_data_and_historic_stats(admin_request, sample_template):
create_ft_notification_status(datetime(2016, 5, 1), template=sample_template, count=1)
create_ft_notification_status(datetime(2016, 6, 1), template=sample_template, notification_status='created', count=2) # noqa
create_notification(sample_template, created_at=datetime(2016, 6, 5), status='created')
create_notification(sample_template, created_at=datetime(2016, 6, 5), status='delivered')
# this doesn't get returned in the stats because it is old - it should be in ft_notification_status by now
create_notification(sample_template, created_at=datetime(2016, 6, 4), status='sending')
response = admin_request.get(
'service.get_monthly_notification_stats',
service_id=sample_template.service_id,
year=2016
)
assert len(response['data']) == 3 # apr, may, jun
assert response['data']['2016-05'] == {
'sms': {
'delivered': 1
},
'email': {},
'letter': {}
}
assert response['data']['2016-06'] == {
'sms': {
# combines the stats from the historic ft_notification_status and the current notifications
'created': 3,
'delivered': 1,
},
'email': {},
'letter': {}
}
def test_get_monthly_notification_stats_ignores_test_keys(admin_request, sample_service):
create_ft_notification_status(datetime(2016, 6, 1), service=sample_service, key_type=KEY_TYPE_NORMAL, count=1)
create_ft_notification_status(datetime(2016, 6, 1), service=sample_service, key_type=KEY_TYPE_TEAM, count=2)
create_ft_notification_status(datetime(2016, 6, 1), service=sample_service, key_type=KEY_TYPE_TEST, count=4)
response = admin_request.get('service.get_monthly_notification_stats', service_id=sample_service.id, year=2016)
assert response['data']['2016-06']['sms'] == {'delivered': 3}
def test_get_monthly_notification_stats_checks_dates(admin_request, sample_service):
t = create_template(sample_service)
create_ft_notification_status(datetime(2016, 3, 31), template=t, notification_status='created')
create_ft_notification_status(datetime(2016, 4, 1), template=t, notification_status='sending')
create_ft_notification_status(datetime(2017, 3, 31), template=t, notification_status='delivered')
create_ft_notification_status(datetime(2017, 4, 11), template=t, notification_status='permanent-failure')
response = admin_request.get('service.get_monthly_notification_stats', service_id=sample_service.id, year=2016)
assert '2016-03' not in response['data']
assert '2017-04' not in response['data']
assert response['data']['2016-04']['sms'] == {'sending': 1}
assert response['data']['2017-03']['sms'] == {'delivered': 1}
def test_get_monthly_notification_stats_only_gets_for_one_service(admin_request, notify_db_session):
services = [create_service(), create_service(service_name="2")]
templates = [create_template(services[0]), create_template(services[1])]
create_ft_notification_status(datetime(2016, 6, 1), template=templates[0], notification_status='created')
create_ft_notification_status(datetime(2016, 6, 1), template=templates[1], notification_status='delivered')
response = admin_request.get('service.get_monthly_notification_stats', service_id=services[0].id, year=2016)
assert response['data']['2016-06'] == {
'sms': {'created': 1},
'email': {},
'letter': {}
}