Create 'v2' get notification route

The new 'v2' API wants to return less data than the previous one,
which was sending back tons of fields the clients never used.

This new route returns only useful information, with the JSON
response dict being built up in the model's `.serialize()` method.

Note that writing the test for this was a bit painful because of
having to treat loads of keys differently. Hopefully we think this
is a good way to write this test, because if we don't, we should
start thinking of a better way to check the values are what we
expect.
This commit is contained in:
Paul Craig
2016-11-18 17:36:11 +00:00
parent fddb1653ac
commit 9758b96a2b
5 changed files with 113 additions and 6 deletions

View File

@@ -96,8 +96,11 @@ def register_blueprint(application):
def register_v2_blueprints(application):
from app.v2.notifications.post_notifications import notification_blueprint
application.register_blueprint(notification_blueprint)
from app.v2.notifications.post_notifications import notification_blueprint as post_notifications
from app.v2.notifications.get_notifications import notification_blueprint as get_notifications
application.register_blueprint(post_notifications)
application.register_blueprint(get_notifications)
def init_app(app):

View File

@@ -1,5 +1,6 @@
import uuid
import datetime
from flask import url_for
from sqlalchemy.dialects.postgresql import (
UUID,
@@ -22,7 +23,8 @@ from app.authentication.utils import get_secret
from app import (
db,
encryption,
DATETIME_FORMAT)
DATETIME_FORMAT
)
from app.history_meta import Versioned
@@ -281,6 +283,10 @@ class Template(db.Model):
created_by = db.relationship('User')
version = db.Column(db.Integer, default=1, nullable=False)
def get_link(self):
# TODO: use "/v2/" route once available
return url_for("template.get_template_by_id_and_service_id", service_id=self.service_id, template_id=self.id)
class TemplateHistory(db.Model):
__tablename__ = 'templates_history'
@@ -553,6 +559,49 @@ class Notification(db.Model):
return provider_rate.rate * self.billable_units
def completed_at(self):
if self.status in [
NOTIFICATION_DELIVERED,
NOTIFICATION_FAILED,
NOTIFICATION_TECHNICAL_FAILURE,
NOTIFICATION_TEMPORARY_FAILURE,
NOTIFICATION_PERMANENT_FAILURE
]:
return self.updated_at.strftime(DATETIME_FORMAT)
return None
def serialize(self):
template_dict = {
'version': self.template.version,
'id': self.template.id,
'uri': self.template.get_link()
}
serialized = {
"id": self.id,
"reference": self.client_reference,
"email_address": self.to if self.notification_type == EMAIL_TYPE else None,
"phone_number": self.to if self.notification_type == SMS_TYPE else None,
"line_1": None,
"line_2": None,
"line_3": None,
"line_4": None,
"line_5": None,
"line_6": None,
"postcode": None,
"cost": self.cost(),
"type": self.notification_type,
"status": self.status,
"template": template_dict,
"created_at": self.created_at.strftime(DATETIME_FORMAT),
"sent_at": self.sent_at.strftime(DATETIME_FORMAT) if self.sent_at else None,
"completed_at": self.completed_at()
}
return serialized
class NotificationHistory(db.Model):
__tablename__ = 'notification_history'

View File

@@ -1,9 +1,17 @@
from flask import jsonify
from app import api_user
from app.dao import notifications_dao
from app.v2.notifications import notification_blueprint
@notification_blueprint.route("/<uuid:id>", methods=['GET'])
def get_notification_by_id(id):
pass
notification = notifications_dao.get_notification_with_personalisation(
str(api_user.service_id), id, key_type=None
)
return jsonify(notification.serialize()), 200
@notification_blueprint.route("/", methods=['GET'])

View File

@@ -0,0 +1,46 @@
import json
from app import DATETIME_FORMAT
from tests import create_authorization_header
def test_get_notification_by_id_returns_200(client, sample_notification):
auth_header = create_authorization_header(service_id=sample_notification.service_id)
response = client.get(
path='/v2/notifications/{}'.format(sample_notification.id),
headers=[('Content-Type', 'application/json'), auth_header])
assert response.status_code == 200
assert response.headers['Content-type'] == 'application/json'
json_response = json.loads(response.get_data(as_text=True))
expected_template_response = {
'id': '{}'.format(sample_notification.serialize()['template']['id']),
'version': sample_notification.serialize()['template']['version'],
'uri': sample_notification.serialize()['template']['uri']
}
expected_response = {
'id': '{}'.format(sample_notification.id),
'reference': None,
'email_address': None,
'phone_number': '{}'.format(sample_notification.to),
'line_1': None,
'line_2': None,
'line_3': None,
'line_4': None,
'line_5': None,
'line_6': None,
'postcode': None,
'cost': sample_notification.cost(),
'type': '{}'.format(sample_notification.notification_type),
'status': '{}'.format(sample_notification.status),
'template': expected_template_response,
'created_at': sample_notification.created_at.strftime(DATETIME_FORMAT),
'sent_at': sample_notification.sent_at,
'completed_at': sample_notification.completed_at()
}
assert json_response == expected_response

View File

@@ -4,8 +4,9 @@ import pytest
from flask import json
from jsonschema import ValidationError
from app.v2.notifications.notification_schemas import post_sms_request, post_sms_response, post_email_request, \
post_email_response
from app.v2.notifications.notification_schemas import (
post_sms_request, post_sms_response, post_email_request, post_email_response
)
from app.schema_validation import validate
valid_json = {"phone_number": "07515111111",