Files
notifications-admin/app/main/views/conversation.py
Alexey Bezhan 29bed8ba55 Add Service.get_templates method with filters by type and folder
With the addition of template folders we need to filter templates
based on a combination of type and parent folder ID.

This replaces the existing `templates_by_type` method with
`get_templates`, which supports both type and parent folder filters,
avoiding a need to create specific methods for each use case.

We still need the templates property to exist in some way in order
to cache it, but it needs to be clear that it's different from
`.get_templates`. One option was to make it "private" (i.e. `_templates`),
and always use `.get_templates` in the rest of the code, but this requires
adding "include all folders" to `.get_templates`, which doesn't have an
obvious interface since `parent_folder_id=None` already means "top-level
only".

This will probably come up again when we need to look into adding
templates from nested folders into the page for live search, but
for now renaming `Service.templates` to `.all_templates` makes it
clear what the property contains.
2018-11-06 13:13:13 +00:00

130 lines
4.4 KiB
Python

from flask import jsonify, redirect, render_template, session, url_for
from flask_login import login_required
from notifications_python_client.errors import HTTPError
from notifications_utils.recipients import format_phone_number_human_readable
from notifications_utils.template import SMSPreviewTemplate
from app import current_service, notification_api_client, service_api_client
from app.main import main
from app.main.forms import SearchTemplatesForm
from app.utils import user_has_permissions
@main.route("/services/<service_id>/conversation/<notification_id>")
@login_required
@user_has_permissions('view_activity')
def conversation(service_id, notification_id):
user_number = get_user_number(service_id, notification_id)
return render_template(
'views/conversations/conversation.html',
user_number=user_number,
partials=get_conversation_partials(service_id, user_number),
updates_url=url_for('.conversation_updates', service_id=service_id, notification_id=notification_id),
notification_id=notification_id,
)
@main.route("/services/<service_id>/conversation/<notification_id>.json")
@login_required
@user_has_permissions('view_activity')
def conversation_updates(service_id, notification_id):
return jsonify(get_conversation_partials(
service_id,
get_user_number(service_id, notification_id)
))
@main.route("/services/<service_id>/conversation/<notification_id>/reply-with")
@login_required
@user_has_permissions('send_messages')
def conversation_reply(
service_id,
notification_id,
):
templates = current_service.get_templates('sms')
return render_template(
'views/templates/choose-reply.html',
templates=templates,
show_search_box=(len(templates) > 7),
template_type='sms',
search_form=SearchTemplatesForm(),
notification_id=notification_id,
)
@main.route("/services/<service_id>/conversation/<notification_id>/reply-with/<template_id>")
@login_required
@user_has_permissions('send_messages')
def conversation_reply_with_template(
service_id,
notification_id,
template_id,
):
session['recipient'] = get_user_number(service_id, notification_id)
session['placeholders'] = {'phone number': session['recipient']}
return redirect(url_for(
'main.send_one_off_step',
service_id=service_id,
template_id=template_id,
step_index=1,
))
def get_conversation_partials(service_id, user_number):
return {
'messages': render_template(
'views/conversations/messages.html',
conversation=get_sms_thread(service_id, user_number),
)
}
def get_user_number(service_id, notification_id):
try:
user_number = service_api_client.get_inbound_sms_by_id(service_id, notification_id)['user_number']
except HTTPError as e:
if e.status_code != 404:
raise
user_number = notification_api_client.get_notification(service_id, notification_id)['to']
return format_phone_number_human_readable(user_number)
def get_sms_thread(service_id, user_number):
for notification in sorted((
notification_api_client.get_notifications_for_service(service_id,
to=user_number,
template_type='sms')['notifications'] +
service_api_client.get_inbound_sms(service_id, user_number=user_number)['data']
), key=lambda notification: notification['created_at']):
is_inbound = ('notify_number' in notification)
redact_personalisation = not is_inbound and notification['template']['redact_personalisation']
if redact_personalisation:
notification['personalisation'] = {}
yield {
'inbound': is_inbound,
'content': SMSPreviewTemplate(
{
'content': (
notification['content'] if is_inbound else
notification['template']['content']
)
},
notification.get('personalisation'),
downgrade_non_gsm_characters=(not is_inbound),
redact_missing_personalisation=redact_personalisation,
),
'created_at': notification['created_at'],
'status': notification.get('status'),
'id': notification['id'],
}