コード例 #1
0
ファイル: test_reporting_tasks.py プロジェクト: trodjr/notify
def test_create_nightly_billing_update_when_record_exists(
        notify_db,
        notify_db_session,
        sample_service,
        sample_template,
        mocker):

    mocker.patch('app.celery.reporting_tasks.get_rate', side_effect=mocker_get_rate)

    sample_notification(
        notify_db,
        notify_db_session,
        created_at=datetime.now() - timedelta(days=1),
        service=sample_service,
        template=sample_template,
        status='delivered',
        sent_by=None,
        international=False,
        rate_multiplier=1.0,
        billable_units=1,
    )

    records = FactBilling.query.all()
    assert len(records) == 0

    create_nightly_billing()
    records = FactBilling.query.order_by(FactBilling.aet_date).all()

    assert len(records) == 1
    assert records[0].aet_date == date(2018, 1, 14)

    # run again, make sure create_nightly_billing updates with no error
    create_nightly_billing()
    assert len(records) == 1
コード例 #2
0
def test_create_nightly_billing_letter(notify_db, notify_db_session,
                                       sample_service, sample_letter_template,
                                       mocker):
    yesterday = datetime.now() - timedelta(days=1)

    mocker.patch('app.dao.fact_billing_dao.get_rate',
                 side_effect=mocker_get_rate)

    sample_notification(
        notify_db,
        notify_db_session,
        created_at=yesterday,
        service=sample_service,
        template=sample_letter_template,
        status='delivered',
        sent_by='dvla',
        international=False,
        rate_multiplier=2.0,
        billable_units=2,
    )

    records = FactBilling.query.all()
    assert len(records) == 0
    # Celery expects the arguments to be a string or primitive type.
    yesterday_str = datetime.strftime(yesterday, "%Y-%m-%d")
    create_nightly_billing(yesterday_str)
    records = FactBilling.query.order_by('rate_multiplier').all()
    assert len(records) == 1
    record = records[0]
    assert record.notification_type == LETTER_TYPE
    assert record.bst_date == datetime.date(yesterday)
    assert record.rate == Decimal(2.1)
    assert record.billable_units == 2
    assert record.rate_multiplier == 2.0
コード例 #3
0
ファイル: test_reporting_tasks.py プロジェクト: trodjr/notify
def test_create_nightly_billing_letter(
        notify_db,
        notify_db_session,
        sample_service,
        sample_letter_template,
        mocker):
    yesterday = datetime.utcnow() - timedelta(days=1)

    mocker.patch('app.celery.reporting_tasks.get_rate', side_effect=mocker_get_rate)

    sample_notification(
        notify_db,
        notify_db_session,
        created_at=yesterday,
        service=sample_service,
        template=sample_letter_template,
        status='delivered',
        sent_by='dvla',
        international=False,
        rate_multiplier=2.0,
        billable_units=2,
    )

    records = FactBilling.query.all()
    assert len(records) == 0

    create_nightly_billing()
    records = FactBilling.query.order_by('rate_multiplier').all()
    assert len(records) == 1
    record = records[0]
    assert record.notification_type == LETTER_TYPE
    assert record.aet_date == datetime.date(convert_utc_to_aet(yesterday))
    assert record.rate == Decimal(2.1)
    assert record.billable_units == 2
    assert record.rate_multiplier == 2.0
コード例 #4
0
def test_create_nightly_billing_null_sent_by_sms(notify_db, notify_db_session,
                                                 sample_service,
                                                 sample_template, mocker):
    yesterday = datetime.utcnow() - timedelta(days=1)

    mocker.patch('app.celery.reporting_tasks.get_rate',
                 side_effect=mocker_get_rate)

    sample_notification(
        notify_db,
        notify_db_session,
        created_at=yesterday,
        service=sample_service,
        template=sample_template,
        status='delivered',
        sent_by=None,
        international=False,
        rate_multiplier=1.0,
        billable_units=1,
    )

    records = FactBilling.query.all()
    assert len(records) == 0

    create_nightly_billing()
    records = FactBilling.query.all()

    assert len(records) == 1
    record = records[0]
    assert record.aet_date == datetime.date(convert_utc_to_aet(yesterday))
    assert record.rate == Decimal(1.33)
    assert record.billable_units == 1
    assert record.rate_multiplier == 1
    assert record.provider == 'unknown'
コード例 #5
0
def test_template_usage_should_ignore_test_keys(
        notify_db,
        notify_db_session,
        sample_team_api_key,
        sample_test_api_key
):
    sms = sample_template(notify_db, notify_db_session)

    one_minute_ago = datetime.utcnow() - timedelta(minutes=1)
    two_minutes_ago = datetime.utcnow() - timedelta(minutes=2)

    team_key = sample_notification(
        notify_db,
        notify_db_session,
        created_at=two_minutes_ago,
        template=sms,
        api_key_id=sample_team_api_key.id,
        key_type=KEY_TYPE_TEAM)
    sample_notification(
        notify_db,
        notify_db_session,
        created_at=one_minute_ago,
        template=sms,
        api_key_id=sample_test_api_key.id,
        key_type=KEY_TYPE_TEST)

    results = dao_get_last_template_usage(sms.id)
    assert results.id == team_key.id
コード例 #6
0
def test_create_nightly_billing_consolidate_from_3_days_delta(
        notify_db, notify_db_session, sample_service, sample_template, mocker):

    mocker.patch('app.dao.fact_billing_dao.get_rate',
                 side_effect=mocker_get_rate)

    # create records from 11th to 15th
    for i in range(0, 11):
        sample_notification(
            notify_db,
            notify_db_session,
            created_at=datetime.now() - timedelta(days=i),
            service=sample_service,
            template=sample_template,
            status='delivered',
            sent_by=None,
            international=False,
            rate_multiplier=1.0,
            billable_units=1,
        )

    notification = Notification.query.order_by(Notification.created_at).all()
    assert datetime.date(notification[0].created_at) == date(2018, 1, 5)

    records = FactBilling.query.all()
    assert len(records) == 0

    create_nightly_billing()
    records = FactBilling.query.order_by(FactBilling.bst_date).all()

    assert len(records) == 10
    assert records[0].bst_date == date(2018, 1, 5)
    assert records[-1].bst_date == date(2018, 1, 14)
コード例 #7
0
def test_update_status_of_notifications_after_timeout(notify_api,
                                                      notify_db,
                                                      notify_db_session,
                                                      sample_service,
                                                      sample_template,
                                                      mmg_provider):
    with notify_api.test_request_context():
        not1 = sample_notification(
            notify_db,
            notify_db_session,
            service=sample_service,
            template=sample_template,
            status='sending',
            created_at=datetime.utcnow() - timedelta(
                seconds=current_app.config.get('SENDING_NOTIFICATIONS_TIMEOUT_PERIOD') + 10))
        not2 = sample_notification(
            notify_db,
            notify_db_session,
            service=sample_service,
            template=sample_template,
            status='created',
            created_at=datetime.utcnow() - timedelta(
                seconds=current_app.config.get('SENDING_NOTIFICATIONS_TIMEOUT_PERIOD') + 10))
        not3 = sample_notification(
            notify_db,
            notify_db_session,
            service=sample_service,
            template=sample_template,
            status='pending',
            created_at=datetime.utcnow() - timedelta(
                seconds=current_app.config.get('SENDING_NOTIFICATIONS_TIMEOUT_PERIOD') + 10))
        timeout_notifications()
        assert not1.status == 'temporary-failure'
        assert not2.status == 'technical-failure'
        assert not3.status == 'temporary-failure'
コード例 #8
0
def test_should_not_delete_failed_notifications_before_seven_days(notify_db, notify_db_session):
    should_delete = datetime.utcnow() - timedelta(days=8)
    do_not_delete = datetime.utcnow() - timedelta(days=7)
    sample_notification(notify_db, notify_db_session, created_at=should_delete, status="failed",
                        to_field="should_delete")
    sample_notification(notify_db, notify_db_session, created_at=do_not_delete, status="failed",
                        to_field="do_not_delete")
    assert len(Notification.query.all()) == 2
    delete_notifications_created_more_than_a_week_ago('failed')
    assert len(Notification.query.all()) == 1
    assert Notification.query.first().to == 'do_not_delete'
コード例 #9
0
ファイル: test_reporting_tasks.py プロジェクト: trodjr/notify
def test_create_nightly_billing_sms_rate_multiplier(
        notify_db,
        notify_db_session,
        sample_service,
        sample_template,
        mocker,
        second_rate,
        records_num,
        billable_units,
        multiplier):

    yesterday = datetime.utcnow() - timedelta(days=1)

    mocker.patch('app.celery.reporting_tasks.get_rate', side_effect=mocker_get_rate)

    # These are sms notifications
    sample_notification(
        notify_db,
        notify_db_session,
        created_at=yesterday,
        service=sample_service,
        template=sample_template,
        status='delivered',
        sent_by='mmg',
        international=False,
        rate_multiplier=1.0,
        billable_units=1,
    )
    sample_notification(
        notify_db,
        notify_db_session,
        created_at=yesterday,
        service=sample_service,
        template=sample_template,
        status='delivered',
        sent_by='mmg',
        international=False,
        rate_multiplier=second_rate,
        billable_units=1,
    )

    records = FactBilling.query.all()
    assert len(records) == 0

    create_nightly_billing()
    records = FactBilling.query.order_by('rate_multiplier').all()
    assert len(records) == records_num

    for i, record in enumerate(records):
        assert record.aet_date == datetime.date(convert_utc_to_aet(yesterday))
        assert record.rate == Decimal(1.33)
        assert record.billable_units == billable_units
        assert record.rate_multiplier == multiplier[i]
コード例 #10
0
def test_get_all_notifications_for_job(notify_db, notify_db_session, sample_job):
    for i in range(0, 5):
        try:
            sample_notification(notify_db,
                                notify_db_session,
                                service=sample_job.service,
                                template=sample_job.template,
                                job=sample_job)
        except IntegrityError:
            pass

    notifications_from_db = get_notifications_for_job(sample_job.service.id, sample_job.id).items
    assert len(notifications_from_db) == 5
コード例 #11
0
ファイル: test_reporting_tasks.py プロジェクト: trodjr/notify
def test_create_nightly_billing_use_aet(
        notify_db,
        notify_db_session,
        sample_service,
        sample_template,
        mocker):

    mocker.patch('app.celery.reporting_tasks.get_rate', side_effect=mocker_get_rate)

    sample_notification(
        notify_db,
        notify_db_session,
        created_at=datetime(2018, 10, 6, 14, 30),  # 07/10/2018 00:30:00 AEDT
        service=sample_service,
        template=sample_template,
        status='delivered',
        sent_by=None,
        international=False,
        rate_multiplier=1.0,
        billable_units=1,
    )

    sample_notification(
        notify_db,
        notify_db_session,
        created_at=datetime(2018, 10, 7, 13, 30),  # 08/10/2018 00:30:00 AEDT
        service=sample_service,
        template=sample_template,
        status='delivered',
        sent_by=None,
        international=False,
        rate_multiplier=1.0,
        billable_units=1,
    )

    notifications = Notification.query.order_by(Notification.created_at).all()
    assert len(notifications) == 2
    records = FactBilling.query.all()
    assert len(records) == 0

    create_nightly_billing()
    records = FactBilling.query.order_by(FactBilling.aet_date).all()

    assert len(records) == 2
    # The first record's aet_date is 06/10/2018. This is because the current
    # time is 2018-10-09T13:30:00 UTC, and 3 days earlier than that is
    # 2018-10-06T13:30:00 UTC which is 06/10/2018 23:30:00 AEST. This falls
    # outside of daylight savings time and so the aet_date is the 6th, not the
    # 7th.
    assert records[0].aet_date == date(2018, 10, 6)
    assert records[-1].aet_date == date(2018, 10, 8)
コード例 #12
0
def test_get_notifications_with_a_team_api_key_type(
        notify_db,
        notify_db_session,
        sample_service,
        sample_job,
        sample_api_key,
        sample_team_api_key,
        sample_test_api_key
):
    sample_notification(
        notify_db, notify_db_session, created_at=datetime.utcnow(), job=sample_job
    )
    sample_notification(
        notify_db, notify_db_session, created_at=datetime.utcnow(), api_key_id=sample_api_key.id,
        key_type=sample_api_key.key_type
    )
    sample_notification(
        notify_db, notify_db_session, created_at=datetime.utcnow(), api_key_id=sample_team_api_key.id,
        key_type=sample_team_api_key.key_type
    )
    sample_notification(
        notify_db, notify_db_session, created_at=datetime.utcnow(), api_key_id=sample_test_api_key.id,
        key_type=sample_test_api_key.key_type
    )

    # only those created with team API key, no jobs
    all_notifications = get_notifications_for_service(sample_service.id, limit_days=1, key_type=KEY_TYPE_TEAM).items
    assert len(all_notifications) == 1

    # only those created with team API key, no jobs, even when requested
    all_notifications = get_notifications_for_service(sample_service.id, limit_days=1, include_jobs=True,
                                                      key_type=KEY_TYPE_TEAM).items
    assert len(all_notifications) == 1
コード例 #13
0
def test_get_template_statistics_for_service(notify_db, notify_db_session, notify_api, sample_service):
    sms = sample_template(notify_db, notify_db_session, service=sample_service)
    email = sample_email_template(notify_db, notify_db_session, service=sample_service)
    today = datetime.now()
    sample_notification(notify_db, notify_db_session, created_at=today, service=sample_service, template=sms)
    sample_notification(notify_db, notify_db_session, created_at=today, service=sample_service, template=sms)
    sample_notification(notify_db, notify_db_session, created_at=today, service=sample_service, template=email)
    sample_notification(notify_db, notify_db_session, created_at=today, service=sample_service, template=email)

    with notify_api.test_request_context():
        with notify_api.test_client() as client:
            auth_header = create_authorization_header()

            response = client.get(
                '/service/{}/template-statistics'.format(sample_service.id),
                headers=[('Content-Type', 'application/json'), auth_header]
            )

            assert response.status_code == 200
            json_resp = json.loads(response.get_data(as_text=True))
            assert len(json_resp['data']) == 2
            assert json_resp['data'][0]['count'] == 2
            assert json_resp['data'][0]['template_id'] == str(email.id)
            assert json_resp['data'][0]['template_name'] == email.name
            assert json_resp['data'][0]['template_type'] == email.template_type
            assert json_resp['data'][1]['count'] == 2
            assert json_resp['data'][1]['template_id'] == str(sms.id)
            assert json_resp['data'][1]['template_name'] == sms.name
            assert json_resp['data'][1]['template_type'] == sms.template_type
コード例 #14
0
def test_create_nightly_billing_different_sent_by(notify_db, notify_db_session,
                                                  sample_service,
                                                  sample_template,
                                                  sample_email_template,
                                                  mocker):
    yesterday = datetime.now() - timedelta(days=1)

    mocker.patch('app.dao.fact_billing_dao.get_rate',
                 side_effect=mocker_get_rate)

    # These are sms notifications
    sample_notification(
        notify_db,
        notify_db_session,
        created_at=yesterday,
        service=sample_service,
        template=sample_template,
        status='delivered',
        sent_by='mmg',
        international=False,
        rate_multiplier=1.0,
        billable_units=1,
    )
    sample_notification(
        notify_db,
        notify_db_session,
        created_at=yesterday,
        service=sample_service,
        template=sample_template,
        status='delivered',
        sent_by='firetext',
        international=False,
        rate_multiplier=1.0,
        billable_units=1,
    )

    records = FactBilling.query.all()
    assert len(records) == 0

    # Celery expects the arguments to be a string or primitive type.
    yesterday_str = datetime.strftime(yesterday, "%Y-%m-%d")
    create_nightly_billing(yesterday_str)
    records = FactBilling.query.order_by('rate_multiplier').all()

    assert len(records) == 2
    for i, record in enumerate(records):
        assert record.bst_date == datetime.date(yesterday)
        assert record.rate == Decimal(1.33)
        assert record.billable_units == 1
        assert record.rate_multiplier == 1.0
コード例 #15
0
def test_create_nightly_billing_different_templates(
        notify_db, notify_db_session, sample_service, sample_template,
        sample_email_template, mocker):
    yesterday = datetime.utcnow() - timedelta(days=1)

    mocker.patch('app.celery.reporting_tasks.get_rate',
                 side_effect=mocker_get_rate)

    sample_notification(
        notify_db,
        notify_db_session,
        created_at=yesterday,
        service=sample_service,
        template=sample_template,
        status='delivered',
        sent_by='twilio',
        international=False,
        rate_multiplier=1.0,
        billable_units=1,
    )
    sample_notification(
        notify_db,
        notify_db_session,
        created_at=yesterday,
        service=sample_service,
        template=sample_email_template,
        status='delivered',
        sent_by='ses',
        international=False,
        rate_multiplier=0,
        billable_units=0,
    )

    records = FactBilling.query.all()
    assert len(records) == 0

    create_nightly_billing()
    records = FactBilling.query.order_by('rate_multiplier').all()

    assert len(records) == 2
    multiplier = [0, 1]
    billable_units = [0, 1]
    rate = [0, Decimal(1.33)]
    for i, record in enumerate(records):
        assert record.aet_date == datetime.date(convert_utc_to_aet(yesterday))
        assert record.rate == rate[i]
        assert record.billable_units == billable_units[i]
        assert record.rate_multiplier == multiplier[i]
コード例 #16
0
def test_should_send_personalised_template_to_correct_email_provider_and_persist(
    notify_db,
    notify_db_session,
    sample_email_template_with_placeholders,
    mocker
):
    db_notification = sample_notification(
        notify_db=notify_db, notify_db_session=notify_db_session,
        template=sample_email_template_with_placeholders,
        to_field="*****@*****.**",
        personalisation={'name': 'Jo'}
    )

    mocker.patch('app.aws_ses_client.send_email', return_value='reference')
    mocker.patch('app.aws_ses_client.get_name', return_value="ses")

    send_to_providers.send_email_to_provider(
        db_notification
    )

    app.aws_ses_client.send_email.assert_called_once_with(
        '"Sample service" <*****@*****.**>',
        '*****@*****.**',
        'Jo',
        body='Hello Jo\nThis is an email from GOV.\u200bUK',
        html_body=ANY,
        reply_to_address=None
    )
    assert '<!DOCTYPE html' in app.aws_ses_client.send_email.call_args[1]['html_body']

    notification = Notification.query.filter_by(id=db_notification.id).one()
    assert notification.status == 'sending'
    assert notification.sent_at <= datetime.utcnow()
    assert notification.sent_by == 'ses'
    assert notification.personalisation == {"name": "Jo"}
コード例 #17
0
def test_should_not_process_email_job_if_would_exceed_send_limits_inc_today(notify_db, notify_db_session, mocker):
    service = sample_service(notify_db, notify_db_session, limit=1)
    template = sample_email_template(notify_db, notify_db_session, service=service)
    job = sample_job(notify_db, notify_db_session, service=service, template=template)

    sample_notification(notify_db, notify_db_session, service=service, job=job)

    mocker.patch('app.celery.tasks.s3.get_job_from_s3', return_value=load_example_csv('email'))
    mocker.patch('app.celery.tasks.send_email.apply_async')

    process_job(job.id)

    job = jobs_dao.dao_get_job_by_id(job.id)
    assert job.job_status == 'sending limits exceeded'
    assert s3.get_job_from_s3.called is False
    assert tasks.send_email.apply_async.called is False
コード例 #18
0
def test_should_send_sms_sender_from_service_if_present(
        notify_db,
        notify_db_session,
        sample_service,
        sample_template,
        mocker):
    db_notification = sample_notification(notify_db, notify_db_session, template=sample_template,
                                          to_field="+447234123123",
                                          status='created')

    sample_service.sms_sender = 'elevenchars'
    notify_db.session.add(sample_service)
    notify_db.session.commit()

    mocker.patch('app.mmg_client.send_sms')
    mocker.patch('app.mmg_client.get_name', return_value="mmg")

    send_to_providers.send_sms_to_provider(
        db_notification
    )

    mmg_client.send_sms.assert_called_once_with(
        to=format_phone_number(validate_phone_number("+447234123123")),
        content="This is a template:\nwith a newline",
        reference=str(db_notification.id),
        sender=sample_service.sms_sender
    )
コード例 #19
0
def test_should_send_personalised_template_to_correct_sms_provider_and_persist(
    notify_db,
    notify_db_session,
    sample_template_with_placeholders,
    mocker
):
    db_notification = sample_notification(notify_db, notify_db_session, template=sample_template_with_placeholders,
                                          to_field="+447234123123", personalisation={"name": "Jo"},
                                          status='created')

    mocker.patch('app.mmg_client.send_sms')
    mocker.patch('app.mmg_client.get_name', return_value="mmg")

    send_to_providers.send_sms_to_provider(
        db_notification
    )

    mmg_client.send_sms.assert_called_once_with(
        to=format_phone_number(validate_phone_number("+447234123123")),
        content="Sample service: Hello Jo\nYour thing is due soon",
        reference=str(db_notification.id),
        sender=None
    )
    notification = Notification.query.filter_by(id=db_notification.id).one()

    assert notification.status == 'sending'
    assert notification.sent_at <= datetime.utcnow()
    assert notification.sent_by == 'mmg'
    assert notification.billable_units == 1
    assert notification.personalisation == {"name": "Jo"}
コード例 #20
0
def test_should_not_update_status_by_reference_if_not_sending_and_does_not_update_job(notify_db, notify_db_session):
    job = sample_job(notify_db, notify_db_session)
    notification = sample_notification(notify_db, notify_db_session, status='delivered', reference='reference', job=job)
    assert Notification.query.get(notification.id).status == 'delivered'
    assert not update_notification_status_by_reference('reference', 'failed')
    assert Notification.query.get(notification.id).status == 'delivered'
    assert job == Job.query.get(notification.job_id)
コード例 #21
0
def test_dao_timeout_notifications_only_updates_for_older_notifications(notify_db, notify_db_session):
    with freeze_time(datetime.utcnow() + timedelta(minutes=10)):
        created = sample_notification(notify_db, notify_db_session, status='created')
        sending = sample_notification(notify_db, notify_db_session, status='sending')
        pending = sample_notification(notify_db, notify_db_session, status='pending')
        delivered = sample_notification(notify_db, notify_db_session, status='delivered')

    assert Notification.query.get(created.id).status == 'created'
    assert Notification.query.get(sending.id).status == 'sending'
    assert Notification.query.get(pending.id).status == 'pending'
    assert Notification.query.get(delivered.id).status == 'delivered'
    updated = dao_timeout_notifications(1)
    assert NotificationHistory.query.get(created.id).status == 'created'
    assert NotificationHistory.query.get(sending.id).status == 'sending'
    assert NotificationHistory.query.get(pending.id).status == 'pending'
    assert NotificationHistory.query.get(delivered.id).status == 'delivered'
    assert updated == 0
コード例 #22
0
def test_should_return_notifications_excluding_jobs_by_default(notify_db, notify_db_session, sample_service):
    assert len(Notification.query.all()) == 0

    job = sample_job(notify_db, notify_db_session)
    with_job = sample_notification(
        notify_db, notify_db_session, created_at=datetime.utcnow(), status="delivered", job=job
    )
    without_job = sample_notification(
        notify_db, notify_db_session, created_at=datetime.utcnow(), status="delivered"
    )

    all_notifications = Notification.query.all()
    assert len(all_notifications) == 2

    all_notifications = get_notifications_for_service(sample_service.id).items
    assert len(all_notifications) == 1
    assert all_notifications[0].id == without_job.id
コード例 #23
0
ファイル: test_rest.py プロジェクト: trodjr/notify
def test_get_template_statistics_by_id_returns_last_notification(
        notify_db, notify_db_session, client):
    sample_notification(notify_db, notify_db_session)
    sample_notification(notify_db, notify_db_session)
    notification_3 = sample_notification(notify_db, notify_db_session)

    auth_header = create_authorization_header()

    response = client.get(
        '/service/{}/template-statistics/{}'.format(
            notification_3.service_id, notification_3.template_id),
        headers=[('Content-Type', 'application/json'), auth_header],
    )

    assert response.status_code == 200
    json_resp = json.loads(response.get_data(as_text=True))['data']
    assert json_resp['id'] == str(notification_3.id)
コード例 #24
0
def test_should_by_able_to_get_template_count_from_notifications_history(notify_db, notify_db_session, sample_service):
    sms = sample_template(notify_db, notify_db_session)
    email = sample_email_template(notify_db, notify_db_session)
    sample_notification(notify_db, notify_db_session, service=sample_service, template=sms)
    sample_notification(notify_db, notify_db_session, service=sample_service, template=sms)
    sample_notification(notify_db, notify_db_session, service=sample_service, template=sms)
    sample_notification(notify_db, notify_db_session, service=sample_service, template=email)
    sample_notification(notify_db, notify_db_session, service=sample_service, template=email)

    results = dao_get_template_usage(sample_service.id)
    assert results[0].name == 'Email Template Name'
    assert results[0].template_type == 'email'
    assert results[0].count == 2

    assert results[1].name == 'Template Name'
    assert results[1].template_type == 'sms'
    assert results[1].count == 3
コード例 #25
0
def test_should_limit_notifications_return_by_day_limit_plus_one(notify_db, notify_db_session, sample_service):
    assert len(Notification.query.all()) == 0

    # create one notification a day between 1st and 9th
    for i in range(1, 11):
        past_date = '2016-01-{0:02d}'.format(i)
        with freeze_time(past_date):
            sample_notification(notify_db, notify_db_session, created_at=datetime.utcnow(), status="failed")

    all_notifications = Notification.query.all()
    assert len(all_notifications) == 10

    all_notifications = get_notifications_for_service(sample_service.id, limit_days=10).items
    assert len(all_notifications) == 10

    all_notifications = get_notifications_for_service(sample_service.id, limit_days=1).items
    assert len(all_notifications) == 2
コード例 #26
0
def test_should_delete_notifications_after_seven_days(notify_db, notify_db_session):
    assert len(Notification.query.all()) == 0

    # create one notification a day between 1st and 10th from 11:00 to 19:00
    for i in range(1, 11):
        past_date = '2016-01-{0:02d}  {0:02d}:00:00.000000'.format(i)
        with freeze_time(past_date):
            sample_notification(notify_db, notify_db_session, created_at=datetime.utcnow(), status="failed")

    all_notifications = Notification.query.all()
    assert len(all_notifications) == 10

    # Records from before 3rd should be deleted
    delete_notifications_created_more_than_a_week_ago('failed')
    remaining_notifications = Notification.query.all()
    assert len(remaining_notifications) == 8
    for notification in remaining_notifications:
        assert notification.created_at.date() >= date(2016, 1, 3)
コード例 #27
0
def test_create_nightly_billing_use_BST(notify_db, notify_db_session,
                                        sample_service, sample_template,
                                        mocker):

    mocker.patch('app.dao.fact_billing_dao.get_rate',
                 side_effect=mocker_get_rate)

    sample_notification(
        notify_db,
        notify_db_session,
        created_at=datetime(2018, 3, 25, 12, 0),
        service=sample_service,
        template=sample_template,
        status='delivered',
        sent_by=None,
        international=False,
        rate_multiplier=1.0,
        billable_units=1,
    )

    sample_notification(
        notify_db,
        notify_db_session,
        created_at=datetime(2018, 3, 25, 23, 5),
        service=sample_service,
        template=sample_template,
        status='delivered',
        sent_by=None,
        international=False,
        rate_multiplier=1.0,
        billable_units=1,
    )

    notifications = Notification.query.order_by(Notification.created_at).all()
    assert len(notifications) == 2
    records = FactBilling.query.all()
    assert len(records) == 0

    create_nightly_billing()
    records = FactBilling.query.order_by(FactBilling.bst_date).all()

    assert len(records) == 2
    assert records[0].bst_date == date(2018, 3, 25)
    assert records[-1].bst_date == date(2018, 3, 26)
コード例 #28
0
def test_should_not_process_sms_job_if_would_exceed_send_limits_inc_today(notify_db,
                                                                          notify_db_session,
                                                                          mocker):
    service = sample_service(notify_db, notify_db_session, limit=1)
    job = sample_job(notify_db, notify_db_session, service=service)

    sample_notification(notify_db, notify_db_session, service=service, job=job)

    mocker.patch('app.celery.tasks.s3.get_job_from_s3', return_value=load_example_csv('sms'))
    mocker.patch('app.celery.tasks.send_sms.apply_async')
    mocker.patch('app.encryption.encrypt', return_value="something_encrypted")
    mocker.patch('app.celery.tasks.create_uuid', return_value="uuid")

    process_job(job.id)

    job = jobs_dao.dao_get_job_by_id(job.id)
    assert job.job_status == 'sending limits exceeded'
    assert s3.get_job_from_s3.called is False
    assert tasks.send_sms.apply_async.called is False
コード例 #29
0
def test_should_be_able_to_get_template_usage_history(notify_db, notify_db_session, sample_service):
    with freeze_time('2000-01-01 12:00:00'):
        sms = sample_template(notify_db, notify_db_session)
        notification = sample_notification(notify_db, notify_db_session, service=sample_service, template=sms)
        results = dao_get_last_template_usage(sms.id)
        assert results.template.name == 'Template Name'
        assert results.template.template_type == 'sms'
        assert results.created_at == datetime(year=2000, month=1, day=1, hour=12, minute=0, second=0)
        assert results.template_id == sms.id
        assert results.id == notification.id
コード例 #30
0
def test_get_template_statistics_by_id_returns_last_notification(
        notify_db,
        notify_db_session,
        notify_api,
        sample_service):

    template = create_sample_template(
        notify_db,
        notify_db_session,
        template_name='Sample Template 1',
        service=sample_service
    )

    notification_1 = sample_notification(
        notify_db,
        notify_db_session,
        service=sample_service,
        template=template)
    notification_2 = sample_notification(
        notify_db,
        notify_db_session,
        service=sample_service,
        template=template)
    notification_3 = sample_notification(
        notify_db,
        notify_db_session,
        service=sample_service,
        template=template)

    with notify_api.test_request_context():
        with notify_api.test_client() as client:
            auth_header = create_authorization_header()

            response = client.get(
                '/service/{}/template-statistics/{}'.format(sample_service.id, template.id),
                headers=[('Content-Type', 'application/json'), auth_header],
            )

            assert response.status_code == 200
            json_resp = json.loads(response.get_data(as_text=True))['data']
            assert json_resp['id'] == str(notification_3.id)
コード例 #31
0
def test_dao_timeout_notifications(notify_db, notify_db_session, ):
    with freeze_time(datetime.utcnow() - timedelta(minutes=2)):
        created = sample_notification(notify_db, notify_db_session, status='created')
        sending = sample_notification(notify_db, notify_db_session, status='sending')
        pending = sample_notification(notify_db, notify_db_session, status='pending')
        delivered = sample_notification(notify_db, notify_db_session, status='delivered')

    assert Notification.query.get(created.id).status == 'created'
    assert Notification.query.get(sending.id).status == 'sending'
    assert Notification.query.get(pending.id).status == 'pending'
    assert Notification.query.get(delivered.id).status == 'delivered'
    updated = dao_timeout_notifications(1)
    assert Notification.query.get(created.id).status == 'technical-failure'
    assert Notification.query.get(sending.id).status == 'temporary-failure'
    assert Notification.query.get(pending.id).status == 'temporary-failure'
    assert Notification.query.get(delivered.id).status == 'delivered'
    assert NotificationHistory.query.get(created.id).status == 'technical-failure'
    assert NotificationHistory.query.get(sending.id).status == 'temporary-failure'
    assert NotificationHistory.query.get(pending.id).status == 'temporary-failure'
    assert NotificationHistory.query.get(delivered.id).status == 'delivered'
    assert updated == 3
コード例 #32
0
def test_get_notification_billable_unit_count_per_month(notify_db, notify_db_session, sample_service):

    for year, month, day in (
        (2017, 1, 15),  # ↓ 2016 financial year
        (2016, 8, 1),
        (2016, 7, 15),
        (2016, 4, 15),
        (2016, 4, 15),
        (2016, 4, 1),  # ↓ 2015 financial year
        (2016, 3, 31),
        (2016, 1, 15)
    ):
        sample_notification(
            notify_db, notify_db_session, service=sample_service,
            created_at=datetime(
                year, month, day, 0, 0, 0, 0
            ) - timedelta(hours=1, seconds=1)  # one second before midnight
        )

    for financial_year, months in (
        (
            2017,
            []
        ),
        (
            2016,
            [('April', 2), ('July', 2), ('January', 1)]
        ),
        (
            2015,
            [('January', 1), ('March', 2)]
        ),
        (
            2014,
            []
        )
    ):
        assert get_notification_billable_unit_count_per_month(
            sample_service.id, financial_year
        ) == months
コード例 #33
0
def test_get_all_notifications_for_job_by_status(notify_db, notify_db_session, sample_job):
    notifications = partial(get_notifications_for_job, sample_job.service.id, sample_job.id)

    for status in NOTIFICATION_STATUS_TYPES:
        sample_notification(
            notify_db,
            notify_db_session,
            service=sample_job.service,
            template=sample_job.template,
            job=sample_job,
            status=status
        )

    assert len(notifications().items) == len(NOTIFICATION_STATUS_TYPES)

    for status in NOTIFICATION_STATUS_TYPES:
        if status == 'failed':
            assert len(notifications(filter_dict={'status': status}).items) == len(NOTIFICATION_STATUS_TYPES_FAILED)
        else:
            assert len(notifications(filter_dict={'status': status}).items) == 1

    assert len(notifications(filter_dict={'status': NOTIFICATION_STATUS_TYPES[:3]}).items) == 3
コード例 #34
0
def test_should_not_delete_notification_history(notify_db, notify_db_session):
    with freeze_time('2016-01-01 12:00'):
        notification = sample_notification(notify_db, notify_db_session, created_at=datetime.utcnow(), status="failed")
        notification_id = notification.id

    assert Notification.query.count() == 1
    assert NotificationHistory.query.count() == 1

    delete_notifications_created_more_than_a_week_ago('failed')

    assert Notification.query.count() == 0
    assert NotificationHistory.query.count() == 1
    assert NotificationHistory.query.one().id == notification_id
コード例 #35
0
def test_get_notifications_by_reference(notify_db, notify_db_session, sample_service):
    client_reference = 'some-client-ref'
    assert len(Notification.query.all()) == 0
    sample_notification(notify_db, notify_db_session, client_reference=client_reference)
    sample_notification(notify_db, notify_db_session, client_reference=client_reference)
    sample_notification(notify_db, notify_db_session, client_reference='other-ref')
    all_notifications = get_notifications_for_service(sample_service.id, client_reference=client_reference).items
    assert len(all_notifications) == 2
コード例 #36
0
def test_should_be_able_to_get_all_template_usage_history_order_by_notification_created_at(
        notify_db,
        notify_db_session,
        sample_service):
    sms = sample_template(notify_db, notify_db_session)

    sample_notification(notify_db, notify_db_session, service=sample_service, template=sms)
    sample_notification(notify_db, notify_db_session, service=sample_service, template=sms)
    sample_notification(notify_db, notify_db_session, service=sample_service, template=sms)
    most_recent = sample_notification(notify_db, notify_db_session, service=sample_service, template=sms)

    results = dao_get_last_template_usage(sms.id)
    assert results.id == most_recent.id
コード例 #37
0
def test_create_nightly_billing_null_sent_by_sms(notify_db, notify_db_session,
                                                 sample_service,
                                                 sample_template, mocker):
    yesterday = datetime.now() - timedelta(days=1)

    mocker.patch('app.dao.fact_billing_dao.get_rate',
                 side_effect=mocker_get_rate)

    sample_notification(
        notify_db,
        notify_db_session,
        created_at=yesterday,
        service=sample_service,
        template=sample_template,
        status='delivered',
        sent_by=None,
        international=False,
        rate_multiplier=1.0,
        billable_units=1,
    )

    records = FactBilling.query.all()
    assert len(records) == 0

    # Celery expects the arguments to be a string or primitive type.
    yesterday_str = datetime.strftime(yesterday, "%Y-%m-%d")
    create_nightly_billing(yesterday_str)
    records = FactBilling.query.all()

    assert len(records) == 1
    record = records[0]
    assert record.bst_date == datetime.date(yesterday)
    assert record.rate == Decimal(1.33)
    assert record.billable_units == 1
    assert record.rate_multiplier == 1
    assert record.provider == 'unknown'
コード例 #38
0
def test_should_not_update_status_one_notification_status_is_delivered(notify_db, notify_db_session,
                                                                       sample_email_template,
                                                                       ses_provider):
    notification = sample_notification(notify_db=notify_db, notify_db_session=notify_db_session,
                                       template=sample_email_template,
                                       status='sending')
    assert Notification.query.get(notification.id).status == "sending"

    notification.reference = 'reference'
    dao_update_notification(notification)
    update_notification_status_by_reference('reference', 'delivered')
    assert Notification.query.get(notification.id).status == 'delivered'

    update_notification_status_by_reference('reference', 'failed')
    assert Notification.query.get(notification.id).status == 'delivered'
コード例 #39
0
def test_get_delivery_status_with_undelivered_notification(notify_api, notify_db, notify_db_session):

    notification = sample_notification(notify_db=notify_db, notify_db_session=notify_db_session, status='sending')
    more_than_five_mins_ago = datetime.utcnow() - timedelta(minutes=10)
    notification.created_at = more_than_five_mins_ago
    notify_db.session.add(notification)
    notify_db.session.commit()

    with notify_api.test_request_context():
        with notify_api.test_client() as client:
            path = '/_delivery_status'
            response = client.get(path)
            assert response.status_code == 500
            resp_json = json.loads(response.get_data(as_text=True))
            assert resp_json['status'] == 'error'
            assert resp_json['message'] == '1 notifications in sending state over 5 minutes'
コード例 #40
0
def test_should_not_send_to_provider_when_status_is_not_created(notify_db, notify_db_session,
                                                                sample_service,
                                                                mocker):
    notification = sample_notification(notify_db=notify_db, notify_db_session=notify_db_session,
                                       service=sample_service,
                                       status='sending')
    mocker.patch('app.mmg_client.send_sms')
    mocker.patch('app.mmg_client.get_name', return_value="mmg")
    mocker.patch('app.celery.research_mode_tasks.send_sms_response.apply_async')

    send_to_providers.send_sms_to_provider(
        notification
    )

    app.mmg_client.send_sms.assert_not_called()
    app.celery.research_mode_tasks.send_sms_response.apply_async.assert_not_called()
コード例 #41
0
def test_should_return_notifications_including_jobs(notify_db, notify_db_session, sample_service):
    assert len(Notification.query.all()) == 0

    job = sample_job(notify_db, notify_db_session)
    with_job = sample_notification(
        notify_db, notify_db_session, created_at=datetime.utcnow(), status="delivered", job=job
    )

    all_notifications = Notification.query.all()
    assert len(all_notifications) == 1

    all_notifications = get_notifications_for_service(sample_service.id).items
    assert len(all_notifications) == 0

    all_notifications = get_notifications_for_service(sample_service.id, limit_days=1, include_jobs=True).items
    assert len(all_notifications) == 1
    assert all_notifications[0].id == with_job.id
コード例 #42
0
def test_send_email_to_provider_should_call_research_mode_task_response_task_if_research_mode(
        notify_db,
        notify_db_session,
        sample_service,
        sample_email_template,
        ses_provider,
        mocker,
        research_mode,
        key_type):
    notification = sample_notification(notify_db=notify_db, notify_db_session=notify_db_session,
                                       template=sample_email_template,
                                       to_field="*****@*****.**",
                                       key_type=key_type
                                       )

    reference = uuid.uuid4()
    mocker.patch('app.uuid.uuid4', return_value=reference)
    mocker.patch('app.aws_ses_client.send_email')
    mocker.patch('app.aws_ses_client.get_name', return_value="ses")
    mocker.patch('app.celery.research_mode_tasks.send_email_response.apply_async')

    if research_mode:
        sample_service.research_mode = True
        notify_db.session.add(sample_service)
        notify_db.session.commit()

    send_to_providers.send_email_to_provider(
        notification
    )
    assert not app.aws_ses_client.send_email.called
    send_to_providers.send_email_response.apply_async.assert_called_once_with(
        ('ses', str(reference), '*****@*****.**'), queue="research-mode"
    )
    persisted_notification = Notification.query.filter_by(id=notification.id).one()

    assert persisted_notification.to == '*****@*****.**'
    assert persisted_notification.template_id == sample_email_template.id
    assert persisted_notification.status == 'sending'
    assert persisted_notification.sent_at <= datetime.utcnow()
    assert persisted_notification.created_at <= datetime.utcnow()
    assert persisted_notification.sent_by == 'ses'
    assert persisted_notification.reference == str(reference)
    assert persisted_notification.billable_units == 0
コード例 #43
0
ファイル: test_rest.py プロジェクト: trodjr/notify
def set_up_notifications(notify_db, notify_db_session):
    sms = create_sample_template(notify_db, notify_db_session)
    email = sample_email_template(notify_db, notify_db_session)
    today = datetime.now()
    a_week_ago = datetime.now() - timedelta(days=7)
    a_month_ago = datetime.now() - timedelta(days=30)
    sample_notification(notify_db,
                        notify_db_session,
                        created_at=a_month_ago,
                        template=sms)
    sample_notification(notify_db,
                        notify_db_session,
                        created_at=a_month_ago,
                        template=email)
    email.name = 'Updated Email Template Name'
    dao_update_template(email)
    sms.name = 'Updated SMS Template Name'
    dao_update_template(sms)
    sample_notification(notify_db,
                        notify_db_session,
                        created_at=a_week_ago,
                        template=sms)
    sample_notification(notify_db,
                        notify_db_session,
                        created_at=a_week_ago,
                        template=email)
    email.name = 'New Email Template Name'
    dao_update_template(email)
    sms.name = 'New SMS Template Name'
    dao_update_template(sms)
    sample_notification(notify_db,
                        notify_db_session,
                        created_at=today,
                        template=sms)
    sample_notification(notify_db,
                        notify_db_session,
                        created_at=today,
                        template=email)
    return email, sms