From a6318f26749150f4102e82455ba74384b308498e Mon Sep 17 00:00:00 2001 From: Leo Hemsted Date: Mon, 10 Apr 2017 17:25:08 +0100 Subject: [PATCH] remove pdf/png code from admin app entirely while PDFs work on paas, they only do that because it turns out the python buildpack happens to have imagemagick preinstalled - if that ever changes then it'd break. so move those to the template preview service. This also means we can get rid of weazyprint and wand dependencies --- app/main/views/send.py | 21 +++-------- app/main/views/templates.py | 74 ++++++------------------------------- app/template_previews.py | 40 +++++++++++++------- app/utils.py | 17 --------- requirements.txt | 3 -- 5 files changed, 42 insertions(+), 113 deletions(-) diff --git a/app/main/views/send.py b/app/main/views/send.py index 9feee1257..0dbfab8c2 100644 --- a/app/main/views/send.py +++ b/app/main/views/send.py @@ -19,7 +19,6 @@ from flask import ( ) from flask_login import login_required, current_user -from flask_weasyprint import HTML, render_pdf from notifications_utils.columns import Columns from notifications_utils.recipients import RecipientCSV, first_column_headings, validate_and_format_phone_number @@ -36,9 +35,9 @@ from app.utils import ( get_errors_for_csv, Spreadsheet, get_help_argument, - get_template, - png_from_pdf, + get_template ) +from app.template_previews import TemplatePreview def get_page_headings(template_type): @@ -291,24 +290,14 @@ def check_messages(service_id, template_type, upload_id): ) -@main.route("/services///check/.pdf", methods=['GET']) +@main.route("/services///check/.", methods=['GET']) @login_required @user_has_permissions('send_texts', 'send_emails', 'send_letters') -def check_messages_as_pdf(service_id, template_type, upload_id): +def check_messages_preview(service_id, template_type, upload_id, filetype): template = _check_messages( service_id, template_type, upload_id, letters_as_pdf=True )['template'] - return render_pdf(HTML(string=str(template))) - - -@main.route("/services///check/.png", methods=['GET']) -@login_required -@user_has_permissions('send_texts', 'send_emails', 'send_letters') -def check_messages_as_png(service_id, template_type, upload_id): - return send_file(**png_from_pdf( - check_messages_as_pdf(service_id, template_type, upload_id) - )) - + return TemplatePreview.from_utils_template(template, filetype) @main.route("/services///check/", methods=['POST']) @login_required diff --git a/app/main/views/templates.py b/app/main/views/templates.py index a5ca308f4..e78371c2e 100644 --- a/app/main/views/templates.py +++ b/app/main/views/templates.py @@ -1,6 +1,5 @@ from datetime import datetime, timedelta from string import ascii_uppercase -from io import StringIO from flask import ( request, @@ -9,21 +8,17 @@ from flask import ( url_for, flash, abort, - send_file, - current_app ) from flask_login import login_required, current_user -from flask_weasyprint import HTML, render_pdf from dateutil.parser import parse -import requests from notifications_utils.formatters import escape_html -from notifications_utils.template import LetterPreviewTemplate from notifications_utils.recipients import first_column_headings from notifications_python_client.errors import HTTPError from app.main import main -from app.utils import user_has_permissions, get_template, png_from_pdf +from app.utils import user_has_permissions, get_template +from app.template_previews import TemplatePreview from app.main.forms import ( ChooseTemplateType, SMSTemplateForm, @@ -89,37 +84,12 @@ def view_template(service_id, template_id): ) -def get_template_preview(service_id, template_id, filetype): +@main.route("/services//templates/.") +@login_required +@user_has_permissions('view_activity', admin_override=True) +def view_letter_template_as_filetype(service_id, template_id, filetype): db_template = service_api_client.get_service_template(service_id, template_id)['data'] - data = { - "letter_contact_block": current_service['letter_contact_block'], - "admin_base_url": current_app.config['ADMIN_BASE_URL'], - "template": db_template, - "values": None - } - resp = requests.post( - '{}/preview.{}'.format(current_app.config['TEMPLATE_PREVIEW_SERVICE_URL'], filetype), - json=data, - headers={'Authorization': 'Token my-secret-key'} - ) - return resp - - -@main.route("/services//templates/.pdf") -@login_required -@user_has_permissions('view_activity', admin_override=True) -def view_letter_template_as_pdf(service_id, template_id): - resp = get_template_preview(service_id, template_id, 'pdf') - return (resp.content, resp.status_code, resp.headers.items()) - - -@main.route("/services//templates/.png") -@login_required -@user_has_permissions('view_activity', admin_override=True) -def view_letter_template_as_png(service_id, template_id): - resp = get_template_preview(service_id, template_id, 'png') - return (resp.content, resp.status_code, resp.headers.items()) - + return TemplatePreview.from_database_object(db_template, filetype) def _view_template_version(service_id, template_id, version, letters_as_pdf=False): return dict(template=get_template( @@ -153,7 +123,7 @@ def view_template_version(service_id, template_id, version): ) -@main.route("/services//templates//version/.pdf") +@main.route("/services//templates//version/.") @login_required @user_has_permissions( 'view_activity', @@ -164,31 +134,9 @@ def view_template_version(service_id, template_id, version): admin_override=True, any_=True ) -def view_template_version_as_pdf(service_id, template_id, version): - return render_pdf(HTML(string=str( - LetterPreviewTemplate( - service_api_client.get_service_template(service_id, template_id, version=version)['data'], - contact_block=current_service['letter_contact_block'], - admin_base_url=current_app.config['ADMIN_BASE_URL'] - ) - ))) - - -@main.route("/services//templates//version/.png") -@login_required -@user_has_permissions( - 'view_activity', - 'send_texts', - 'send_emails', - 'manage_templates', - 'manage_api_keys', - admin_override=True, - any_=True -) -def view_template_version_as_png(service_id, template_id, version): - return send_file(**png_from_pdf( - view_template_version_as_pdf(service_id, template_id, version) - )) +def view_template_version_preview(service_id, template_id, version, filetype): + db_template = service_api_client.get_service_template(service_id, template_id, version=version)['data'] + return TemplatePreview.from_database_object(db_template, filetype) @main.route("/services//templates/add", methods=['GET', 'POST']) diff --git a/app/template_previews.py b/app/template_previews.py index 5fb6a280f..8b4ef6542 100644 --- a/app/template_previews.py +++ b/app/template_previews.py @@ -1,17 +1,29 @@ -from flask import current_app, current_service +from flask import current_app import requests +from app import current_service -def get_template_preview(template, filetype): - data = { - "letter_contact_block": current_service['letter_contact_block'], - "admin_base_url": current_app.config['ADMIN_BASE_URL'], - "template": template, - "values": None - } - resp = requests.post( - '{}/preview.{}'.format(current_app.config['TEMPLATE_PREVIEW_SERVICE_URL'], filetype), - json=data, - headers={'Authorization': 'Token my-secret-key'} - ) - return (resp.content, resp.status_code, resp.headers.items()) + +class TemplatePreview: + @classmethod + def from_database_object(cls, template, filetype, values=None): + data = { + "letter_contact_block": current_service['letter_contact_block'], + "admin_base_url": current_app.config['ADMIN_BASE_URL'], + "template": template, + "values": values + } + resp = requests.post( + '{}/preview.{}'.format(current_app.config['TEMPLATE_PREVIEW_SERVICE_URL'], filetype), + json=data, + headers={'Authorization': 'Token my-secret-key'} + ) + return (resp.content, resp.status_code, resp.headers.items()) + + @classmethod + def from_utils_template(cls, template, filetype): + return cls.from_database_object( + template._template, + filetype, + template.values + ) diff --git a/app/utils.py b/app/utils.py index ff4f7912b..d6e8703f3 100644 --- a/app/utils.py +++ b/app/utils.py @@ -16,8 +16,6 @@ from flask import ( ) from flask_login import current_user -from wand.image import Image - from notifications_utils.template import ( SMSPreviewTemplate, EmailPreviewTemplate, @@ -327,21 +325,6 @@ def get_template( ) -def png_from_pdf(pdf_endpoint): - output = BytesIO() - with Image( - blob=pdf_endpoint.get_data(), - resolution=150, - ) as image: - with image.convert('png') as converted: - converted.save(file=output) - output.seek(0) - return dict( - filename_or_fp=output, - mimetype='image/png', - ) - - def get_current_financial_year(): now = datetime.utcnow() current_month = int(now.strftime('%-m')) diff --git a/requirements.txt b/requirements.txt index 4a714fedd..c3847de74 100644 --- a/requirements.txt +++ b/requirements.txt @@ -4,9 +4,7 @@ Flask==0.10.1 Flask-Script==2.0.5 Flask-WTF==0.11 Flask-Login==0.3.2 -Flask-WeasyPrint==0.5 -html5lib==1.0b10 credstash==1.8.0 boto3==1.4.4 Pygments==2.0.2 @@ -20,7 +18,6 @@ pyexcel-xlsx==0.1.0 pyexcel-ods3==0.1.1 pytz==2016.4 six==1.10.0 -wand==0.4.4 gunicorn==19.6.0 whitenoise==1.0.6 #manages static assets