mirror of
https://github.com/GSA/notifications-admin.git
synced 2026-08-17 13:09:42 -04:00
Merge pull request #1362 from alphagov/letter-delivery-estimates
Add function to estimate letter delivery date
This commit is contained in:
@@ -7,7 +7,6 @@ from time import monotonic
|
||||
|
||||
import dateutil
|
||||
import itertools
|
||||
import pytz
|
||||
import ago
|
||||
from flask import (
|
||||
Flask,
|
||||
@@ -55,6 +54,8 @@ from app.notify_client.organisations_client import OrganisationsClient
|
||||
from app.notify_client.models import AnonymousUser
|
||||
from app.notify_client.letter_jobs_client import LetterJobsClient
|
||||
|
||||
from app.utils import gmt_timezones
|
||||
|
||||
login_manager = LoginManager()
|
||||
csrf = CsrfProtect()
|
||||
|
||||
@@ -212,12 +213,6 @@ def syntax_highlight_json(code):
|
||||
return Markup(highlight(code, JavascriptLexer(), HtmlFormatter(noclasses=True)))
|
||||
|
||||
|
||||
def gmt_timezones(date):
|
||||
date = dateutil.parser.parse(date)
|
||||
forced_utc = date.replace(tzinfo=pytz.utc)
|
||||
return forced_utc.astimezone(pytz.timezone('Europe/London'))
|
||||
|
||||
|
||||
def format_datetime(date):
|
||||
return '{} at {}'.format(
|
||||
format_date(date),
|
||||
|
||||
40
app/utils.py
40
app/utils.py
@@ -1,10 +1,13 @@
|
||||
import re
|
||||
import csv
|
||||
import pytz
|
||||
from io import StringIO
|
||||
from os import path
|
||||
from functools import wraps
|
||||
import unicodedata
|
||||
from collections import namedtuple
|
||||
from datetime import datetime, timedelta, timezone
|
||||
from dateutil import parser
|
||||
|
||||
import dateutil
|
||||
import ago
|
||||
@@ -324,3 +327,40 @@ def get_time_left(created_at):
|
||||
|
||||
def email_or_sms_not_enabled(template_type, permissions):
|
||||
return (template_type in ['email', 'sms']) and (template_type not in permissions)
|
||||
|
||||
|
||||
def get_letter_timings(upload_time):
|
||||
|
||||
LetterTimings = namedtuple(
|
||||
'LetterTimings',
|
||||
'printed_by, is_printed, earliest_delivery, latest_delivery'
|
||||
)
|
||||
|
||||
# shift anything after 5pm to the next day
|
||||
processing_day = gmt_timezones(upload_time) + timedelta(hours=(7))
|
||||
|
||||
print_day, earliest_delivery, latest_delivery = (
|
||||
processing_day + timedelta(days=days)
|
||||
for days in {
|
||||
'Wednesday': (1, 3, 5),
|
||||
'Thursday': (1, 4, 5),
|
||||
'Friday': (3, 5, 6),
|
||||
'Saturday': (2, 4, 5),
|
||||
}.get(processing_day.strftime('%A'), (1, 3, 4))
|
||||
)
|
||||
|
||||
printed_by = print_day.astimezone(pytz.timezone('Europe/London')).replace(hour=15, minute=0)
|
||||
now = datetime.utcnow().replace(tzinfo=pytz.timezone('Europe/London'))
|
||||
|
||||
return LetterTimings(
|
||||
printed_by=printed_by,
|
||||
is_printed=(now > printed_by),
|
||||
earliest_delivery=earliest_delivery,
|
||||
latest_delivery=latest_delivery,
|
||||
)
|
||||
|
||||
|
||||
def gmt_timezones(date):
|
||||
date = dateutil.parser.parse(date)
|
||||
forced_utc = date.replace(tzinfo=pytz.utc)
|
||||
return forced_utc.astimezone(pytz.timezone('Europe/London'))
|
||||
|
||||
@@ -5,13 +5,15 @@ from csv import DictReader
|
||||
import pytest
|
||||
|
||||
from collections import OrderedDict
|
||||
from freezegun import freeze_time
|
||||
|
||||
from app.utils import (
|
||||
email_safe,
|
||||
generate_notifications_csv,
|
||||
generate_previous_dict,
|
||||
generate_next_dict,
|
||||
Spreadsheet
|
||||
Spreadsheet,
|
||||
get_letter_timings,
|
||||
)
|
||||
|
||||
from tests import notification_json, single_notification_json
|
||||
@@ -154,3 +156,137 @@ def test_generate_notifications_csv_calls_twice_if_next_link(mocker):
|
||||
# mock_calls[0][2] is the kwargs from first call
|
||||
assert mock_get_notifications.mock_calls[0][2]['page'] == 1
|
||||
assert mock_get_notifications.mock_calls[1][2]['page'] == 2
|
||||
|
||||
|
||||
@freeze_time('2017-07-14 14:59:59') # Friday, before print deadline
|
||||
@pytest.mark.parametrize('upload_time, expected_print_time, is_printed, expected_earliest, expected_latest', [
|
||||
|
||||
# BST
|
||||
# ==================================================================
|
||||
# First thing Monday
|
||||
(
|
||||
'2017-07-10 00:00:01',
|
||||
'Tuesday 15:00',
|
||||
True,
|
||||
'Thursday 2017-07-13',
|
||||
'Friday 2017-07-14'
|
||||
),
|
||||
# Monday at 16:59 BST
|
||||
(
|
||||
'2017-07-10 15:59:59',
|
||||
'Tuesday 15:00',
|
||||
True,
|
||||
'Thursday 2017-07-13',
|
||||
'Friday 2017-07-14'
|
||||
),
|
||||
# Monday at 17:00 BST
|
||||
(
|
||||
'2017-07-10 16:00:01',
|
||||
'Wednesday 15:00',
|
||||
True,
|
||||
'Friday 2017-07-14',
|
||||
'Saturday 2017-07-15'
|
||||
),
|
||||
# Tuesday before 17:00 BST
|
||||
(
|
||||
'2017-07-11 12:00:00',
|
||||
'Wednesday 15:00',
|
||||
True,
|
||||
'Friday 2017-07-14',
|
||||
'Saturday 2017-07-15'
|
||||
),
|
||||
# Wednesday before 17:00 BST
|
||||
(
|
||||
'2017-07-12 12:00:00',
|
||||
'Thursday 15:00',
|
||||
True,
|
||||
'Saturday 2017-07-15',
|
||||
'Monday 2017-07-17'
|
||||
),
|
||||
# Thursday before 17:00 BST
|
||||
(
|
||||
'2017-07-13 12:00:00',
|
||||
'Friday 15:00',
|
||||
True, # WRONG
|
||||
'Monday 2017-07-17',
|
||||
'Tuesday 2017-07-18'
|
||||
),
|
||||
# Friday anytime
|
||||
(
|
||||
'2017-07-14 00:00:00',
|
||||
'Monday 15:00',
|
||||
False,
|
||||
'Wednesday 2017-07-19',
|
||||
'Thursday 2017-07-20'
|
||||
),
|
||||
(
|
||||
'2017-07-14 12:00:00',
|
||||
'Monday 15:00',
|
||||
False,
|
||||
'Wednesday 2017-07-19',
|
||||
'Thursday 2017-07-20'
|
||||
),
|
||||
(
|
||||
'2017-07-14 22:00:00',
|
||||
'Monday 15:00',
|
||||
False,
|
||||
'Wednesday 2017-07-19',
|
||||
'Thursday 2017-07-20'
|
||||
),
|
||||
# Saturday anytime
|
||||
(
|
||||
'2017-07-14 12:00:00',
|
||||
'Monday 15:00',
|
||||
False,
|
||||
'Wednesday 2017-07-19',
|
||||
'Thursday 2017-07-20'
|
||||
),
|
||||
# Sunday before 1700 BST
|
||||
(
|
||||
'2017-07-15 15:59:59',
|
||||
'Monday 15:00',
|
||||
False,
|
||||
'Wednesday 2017-07-19',
|
||||
'Thursday 2017-07-20'
|
||||
),
|
||||
# Sunday after 17:00 BST
|
||||
(
|
||||
'2017-07-16 16:00:01',
|
||||
'Tuesday 15:00',
|
||||
False,
|
||||
'Thursday 2017-07-20',
|
||||
'Friday 2017-07-21'
|
||||
),
|
||||
|
||||
# GMT
|
||||
# ==================================================================
|
||||
# Monday at 16:59 GMT
|
||||
(
|
||||
'2017-01-02 16:59:59',
|
||||
'Tuesday 15:00',
|
||||
True,
|
||||
'Thursday 2017-01-05',
|
||||
'Friday 2017-01-06',
|
||||
),
|
||||
# Monday at 17:00 GMT
|
||||
(
|
||||
'2017-01-02 17:00:01',
|
||||
'Wednesday 15:00',
|
||||
True,
|
||||
'Friday 2017-01-06',
|
||||
'Saturday 2017-01-07',
|
||||
),
|
||||
|
||||
])
|
||||
def test_get_estimated_delivery_date_for_letter(
|
||||
upload_time,
|
||||
expected_print_time,
|
||||
is_printed,
|
||||
expected_earliest,
|
||||
expected_latest,
|
||||
):
|
||||
timings = get_letter_timings(upload_time)
|
||||
assert timings.printed_by.strftime('%A %H:%M') == expected_print_time
|
||||
assert timings.is_printed == is_printed
|
||||
assert timings.earliest_delivery.strftime('%A %Y-%m-%d') == expected_earliest
|
||||
assert timings.latest_delivery.strftime('%A %Y-%m-%d') == expected_latest
|
||||
|
||||
Reference in New Issue
Block a user