Template and personalisation content is now merged and returned with

notifications, when retrieved by notification id, or service id (i.e.
all notifications for service).

There is a new element returned at top level of notification json called
body, which is the template content merged with personalisation. This
is consistent with api to endpoint to create notification which returns
what was sent as 'body' in json response.

Merging of template with personalisation is done in the
NotificationStatusSchema.

Personalisation data in encrypted before storing in db.
This commit is contained in:
Adam Shimali
2016-06-20 16:23:56 +01:00
parent 561b02208d
commit 731bb19a9c
8 changed files with 210 additions and 24 deletions

View File

@@ -18,7 +18,6 @@ from notifications_utils.template import Template
from notifications_utils.recipients import (
RecipientCSV,
validate_and_format_phone_number,
allowed_to_send_to
)
@@ -233,7 +232,8 @@ def send_sms(self, service_id, notification_id, encrypted_notification, created_
job_id=notification.get('job', None),
job_row_number=notification.get('row_number', None),
status='sending',
created_at=datetime.strptime(created_at, DATETIME_FORMAT)
created_at=datetime.strptime(created_at, DATETIME_FORMAT),
personalisation=notification.get('personalisation')
)
dao_create_notification(notification_db_object, TEMPLATE_TYPE_SMS)
@@ -277,7 +277,8 @@ def send_email(service_id, notification_id, encrypted_notification, created_at,
status='sending',
created_at=datetime.strptime(created_at, DATETIME_FORMAT),
sent_at=sent_at,
sent_by=provider.get_name()
sent_by=provider.get_name(),
personalisation=notification.get('personalisation')
)
dao_create_notification(notification_db_object, TEMPLATE_TYPE_EMAIL)

View File

@@ -13,7 +13,10 @@ from app.encryption import (
check_hash
)
from app import db
from app import (
db,
encryption
)
from app.history_meta import Versioned
@@ -347,6 +350,18 @@ class Notification(db.Model):
status = db.Column(
db.Enum(*NOTIFICATION_STATUS_TYPES, name='notify_status_types'), nullable=False, default='sending')
reference = db.Column(db.String, nullable=True, index=True)
_personalisation = db.Column(db.String, nullable=True)
@property
def personalisation(self):
if self._personalisation:
return encryption.decrypt(self._personalisation)
return None
@personalisation.setter
def personalisation(self, personalisation):
if personalisation:
self._personalisation = encryption.encrypt(personalisation)
INVITED_USER_STATUS_TYPES = ['pending', 'accepted', 'cancelled']

View File

@@ -277,7 +277,7 @@ def send_notification(notification_type):
service_stats = notifications_dao.dao_get_notification_statistics_for_service_and_day(
service_id,
datetime.utcnow().strftime(DATE_FORMAT)
datetime.today().strftime(DATE_FORMAT)
)
if service_stats:

View File

@@ -10,7 +10,8 @@ from marshmallow import (
validates,
validates_schema,
pre_load,
pre_dump
pre_dump,
post_dump
)
from marshmallow_sqlalchemy import field_for
@@ -110,6 +111,7 @@ class NotificationModelSchema(BaseSchema):
class Meta:
model = models.Notification
strict = True
exclude = ("_personalisation",)
class BaseTemplateSchema(BaseSchema):
@@ -246,12 +248,30 @@ class SmsAdminNotificationSchema(SmsNotificationSchema):
class NotificationStatusSchema(BaseSchema):
template = fields.Nested(TemplateSchema, only=["id", "name", "template_type"], dump_only=True)
template = fields.Nested(TemplateSchema, only=["id", "name", "template_type", "content"], dump_only=True)
job = fields.Nested(JobSchema, only=["id", "original_file_name"], dump_only=True)
personalisation = fields.Dict(required=False)
class Meta:
model = models.Notification
strict = True
exclude = ('_personalisation',)
@pre_dump
def handle_personalisation_property(self, in_data):
if in_data.personalisation:
self.personalisation = in_data.personalisation
return in_data
@post_dump
def handle_template_merge(self, in_data):
if in_data.get('personalisation'):
from notifications_utils.template import Template
merged = Template(in_data['template'], in_data['personalisation']).replaced
in_data['body'] = merged
in_data.pop('personalisation', None)
in_data['template'].pop('content', None)
return in_data
class InvitedUserSchema(BaseSchema):