Ejemplo n.º 1
0
def _check_messages(service_id,
                    template_id,
                    upload_id,
                    preview_row,
                    letters_as_pdf=False):

    try:
        # The happy path is that the job doesn’t already exist, so the
        # API will return a 404 and the client will raise HTTPError.
        job_api_client.get_job(service_id, upload_id)

        # the job exists already - so go back to the templates page
        # If we just return a `redirect` (302) object here, we'll get
        # errors when we try and unpack in the check_messages route.
        # Rasing a werkzeug.routing redirect means that doesn't happen.
        raise PermanentRedirect(
            url_for('.send_messages',
                    service_id=service_id,
                    template_id=template_id))
    except HTTPError as e:
        if e.status_code != 404:
            raise

    statistics = service_api_client.get_service_statistics(service_id,
                                                           today_only=True)
    remaining_messages = (current_service.message_limit -
                          sum(stat['requested']
                              for stat in statistics.values()))

    contents = s3download(service_id, upload_id)

    db_template = current_service.get_template_with_user_permission_or_403(
        template_id, current_user)

    email_reply_to = None
    sms_sender = None
    if db_template['template_type'] == 'email':
        email_reply_to = get_email_reply_to_address_from_session()
    elif db_template['template_type'] == 'sms':
        sms_sender = get_sms_sender_from_session()
    template = get_template(
        db_template,
        current_service,
        show_recipient=True,
        letter_preview_url=url_for(
            '.check_messages_preview',
            service_id=service_id,
            template_id=template_id,
            upload_id=upload_id,
            filetype='png',
            row_index=preview_row,
        ) if not letters_as_pdf else None,
        email_reply_to=email_reply_to,
        sms_sender=sms_sender,
        page_count=get_page_count_for_letter(db_template),
    )
    recipients = RecipientCSV(
        contents,
        template_type=template.template_type,
        placeholders=template.placeholders,
        max_initial_rows_shown=50,
        max_errors_shown=50,
        whitelist=itertools.chain.from_iterable(
            [user.name, user.mobile_number, user.email_address]
            for user in Users(service_id))
        if current_service.trial_mode else None,
        remaining_messages=remaining_messages,
        international_sms=current_service.has_permission('international_sms'),
    )

    if request.args.get('from_test'):
        # only happens if generating a letter preview test
        back_link = url_for('.send_test',
                            service_id=service_id,
                            template_id=template.id)
        choose_time_form = None
    else:
        back_link = url_for('.send_messages',
                            service_id=service_id,
                            template_id=template.id)
        choose_time_form = ChooseTimeForm()

    if preview_row < 2:
        abort(404)

    if preview_row < len(recipients) + 2:
        template.values = recipients[preview_row -
                                     2].recipient_and_personalisation
    elif preview_row > 2:
        abort(404)

    return dict(
        recipients=recipients,
        template=template,
        errors=recipients.has_errors,
        row_errors=get_errors_for_csv(recipients, template.template_type),
        count_of_recipients=len(recipients),
        count_of_displayed_recipients=len(list(recipients.displayed_rows)),
        original_file_name=request.args.get('original_file_name', ''),
        upload_id=upload_id,
        form=CsvUploadForm(),
        remaining_messages=remaining_messages,
        choose_time_form=choose_time_form,
        back_link=back_link,
        help=get_help_argument(),
        trying_to_send_letters_in_trial_mode=all((
            current_service.trial_mode,
            template.template_type == 'letter',
        )),
        required_recipient_columns=OrderedSet(
            recipients.recipient_column_headers) - optional_address_columns,
        preview_row=preview_row,
        sent_previously=job_api_client.has_sent_previously(
            service_id, template.id, db_template['version'],
            request.args.get('original_file_name', '')))
Ejemplo n.º 2
0
def get_notifications(service_id, message_type, status_override=None):
    # TODO get the api to return count of pages as well.
    page = get_page_from_request()
    if page is None:
        abort(404,
              "Invalid page argument ({}).".format(request.args.get('page')))
    filter_args = parse_filter_args(request.args)
    filter_args['status'] = set_status_filters(filter_args)
    service_data_retention_days = None

    if message_type is not None:
        service_data_retention_days = current_service.get_days_of_retention(
            message_type)

    if request.path.endswith('csv') and current_user.has_permissions(
            'view_activity'):
        return Response(generate_notifications_csv(
            service_id=service_id,
            page=page,
            page_size=5000,
            template_type=[message_type],
            status=filter_args.get('status'),
            limit_days=service_data_retention_days),
                        mimetype='text/csv',
                        headers={
                            'Content-Disposition':
                            'inline; filename="notifications.csv"'
                        })
    notifications = notification_api_client.get_notifications_for_service(
        service_id=service_id,
        page=page,
        template_type=[message_type] if message_type else [],
        status=filter_args.get('status'),
        limit_days=service_data_retention_days,
        to=request.form.get('to', ''),
    )
    url_args = {
        'message_type': message_type,
        'status': request.args.get('status')
    }
    prev_page = None

    if 'links' in notifications and notifications['links'].get('prev', None):
        prev_page = generate_previous_dict('main.view_notifications',
                                           service_id,
                                           page,
                                           url_args=url_args)
    next_page = None

    if 'links' in notifications and notifications['links'].get('next', None):
        next_page = generate_next_dict('main.view_notifications', service_id,
                                       page, url_args)

    if message_type:
        download_link = url_for('.view_notifications_csv',
                                service_id=current_service.id,
                                message_type=message_type,
                                status=request.args.get('status'))
    else:
        download_link = None

    return {
        'service_data_retention_days':
        service_data_retention_days,
        'counts':
        render_template('views/activity/counts.html',
                        status=request.args.get('status'),
                        status_filters=get_status_filters(
                            current_service, message_type,
                            service_api_client.get_service_statistics(
                                service_id,
                                today_only=False,
                                limit_days=service_data_retention_days))),
        'notifications':
        render_template(
            'views/activity/notifications.html',
            notifications=list(
                add_preview_of_content_to_notifications(
                    notifications['notifications'])),
            page=page,
            limit_days=service_data_retention_days,
            prev_page=prev_page,
            next_page=next_page,
            status=request.args.get('status'),
            message_type=message_type,
            download_link=download_link,
        ),
    }
Ejemplo n.º 3
0
def get_dashboard_partials(service_id):
    template_statistics = aggregate_usage(
        template_statistics_client.get_template_statistics_for_service(service_id, limit_days=7)
    )

    scheduled_jobs, immediate_jobs = [], []
    if job_api_client.has_jobs(service_id):
        scheduled_jobs = job_api_client.get_scheduled_jobs(service_id)
        immediate_jobs = [
            add_rate_to_job(job)
            for job in job_api_client.get_immediate_jobs(service_id)
        ]

    stats = service_api_client.get_service_statistics(service_id, today_only=False)
    column_width, max_notifiction_count = get_column_properties(
        number_of_columns=(
            3 if current_service.has_permission('letter') else 2
        )
    )
    dashboard_totals = get_dashboard_totals(stats),
    highest_notification_count = max(
        sum(
            value[key] for key in {'requested', 'failed', 'delivered'}
        )
        for key, value in dashboard_totals[0].items()
    )

    return {
        'upcoming': render_template(
            'views/dashboard/_upcoming.html',
            scheduled_jobs=scheduled_jobs
        ),
        'inbox': render_template(
            'views/dashboard/_inbox.html',
            inbound_sms_summary=(
                service_api_client.get_inbound_sms_summary(service_id)
                if current_service.has_permission('inbound_sms') else None
            ),
        ),
        'totals': render_template(
            'views/dashboard/_totals.html',
            service_id=service_id,
            statistics=dashboard_totals[0],
            column_width=column_width,
            smaller_font_size=(
                highest_notification_count > max_notifiction_count
            ),
        ),
        'template-statistics': render_template(
            'views/dashboard/template-statistics.html',
            template_statistics=template_statistics,
            most_used_template_count=max(
                [row['count'] for row in template_statistics] or [0]
            ),
        ),
        'has_template_statistics': bool(template_statistics),
        'jobs': render_template(
            'views/dashboard/_jobs.html',
            jobs=immediate_jobs
        ),
        'has_jobs': bool(immediate_jobs)
    }
Ejemplo n.º 4
0
def get_notifications(service_id, message_type, status_override=None):
    # TODO get the api to return count of pages as well.
    page = get_page_from_request()
    if page is None:
        abort(404,
              "Invalid page argument ({}).".format(request.args.get("page")))
    if message_type not in ["email", "sms", "letter", None]:
        abort(404)
    filter_args = parse_filter_args(request.args)
    filter_args["status"] = set_status_filters(filter_args)
    service_data_retention_days = current_app.config.get(
        "ACTIVITY_STATS_LIMIT_DAYS", None)

    if message_type is not None:
        service_data_retention_days = current_service.get_days_of_retention(
            message_type)

    if request.path.endswith("csv") and current_user.has_permissions(
            "view_activity"):
        return Response(
            generate_notifications_csv(
                service_id=service_id,
                page=page,
                page_size=5000,
                template_type=[message_type],
                status=filter_args.get("status"),
                limit_days=service_data_retention_days,
            ),
            mimetype="text/csv",
            headers={
                "Content-Disposition": 'inline; filename="notifications.csv"'
            },
        )
    notifications = notification_api_client.get_notifications_for_service(
        service_id=service_id,
        page=page,
        template_type=[message_type] if message_type else [],
        status=filter_args.get("status"),
        limit_days=service_data_retention_days,
        to=request.form.get("to", ""),
    )
    url_args = {
        "message_type": message_type,
        "status": request.args.get("status")
    }
    prev_page = None

    if "links" in notifications and notifications["links"].get("prev", None):
        prev_page = generate_previous_dict("main.view_notifications",
                                           service_id,
                                           page,
                                           url_args=url_args)
    next_page = None

    if "links" in notifications and notifications["links"].get("next", None):
        next_page = generate_next_dict("main.view_notifications", service_id,
                                       page, url_args)

    if message_type:
        download_link = url_for(
            ".view_notifications_csv",
            service_id=current_service.id,
            message_type=message_type,
            status=request.args.get("status"),
        )
    else:
        download_link = None

    return {
        "service_data_retention_days":
        service_data_retention_days,
        "counts":
        render_template(
            "views/activity/counts.html",
            status=request.args.get("status"),
            status_filters=get_status_filters(
                current_service,
                message_type,
                service_api_client.get_service_statistics(
                    service_id,
                    today_only=False,
                    limit_days=service_data_retention_days),
            ),
        ),
        "notifications":
        render_template(
            "views/activity/notifications.html",
            notifications=list(
                add_preview_of_content_to_notifications(
                    notifications["notifications"])),
            page=page,
            limit_days=service_data_retention_days,
            prev_page=prev_page,
            next_page=next_page,
            status=request.args.get("status"),
            message_type=message_type,
            download_link=download_link,
        ),
    }
Ejemplo n.º 5
0
def get_dashboard_partials(service_id):
    # all but scheduled and cancelled
    statuses_to_display = job_api_client.JOB_STATUSES - {'scheduled', 'cancelled'}

    template_statistics = aggregate_usage(
        template_statistics_client.get_template_statistics_for_service(service_id, limit_days=7)
    )

    scheduled_jobs = sorted(
        job_api_client.get_jobs(service_id, statuses=['scheduled'])['data'],
        key=lambda job: job['scheduled_for']
    )
    immediate_jobs = [
        add_rate_to_job(job)
        for job in job_api_client.get_jobs(service_id, limit_days=7, statuses=statuses_to_display)['data']
    ]
    stats = service_api_client.get_service_statistics(service_id, today_only=False)
    column_width, max_notifiction_count = get_column_properties(
        number_of_columns=(
            3 if 'letter' in current_service['permissions'] else 2
        )
    )
    dashboard_totals = get_dashboard_totals(stats),
    highest_notification_count = max(
        sum(
            value[key] for key in {'requested', 'failed', 'delivered'}
        )
        for key, value in dashboard_totals[0].items()
    )

    return {
        'upcoming': render_template(
            'views/dashboard/_upcoming.html',
            scheduled_jobs=scheduled_jobs
        ),
        'inbox': render_template(
            'views/dashboard/_inbox.html',
            inbound_sms_summary=(
                service_api_client.get_inbound_sms_summary(service_id)
                if 'inbound_sms' in current_service['permissions'] else None
            ),
        ),
        'totals': render_template(
            'views/dashboard/_totals.html',
            service_id=service_id,
            statistics=dashboard_totals[0],
            column_width=column_width,
            smaller_font_size=(
                highest_notification_count > max_notifiction_count
            ),
        ),
        'template-statistics': render_template(
            'views/dashboard/template-statistics.html',
            template_statistics=template_statistics,
            most_used_template_count=max(
                [row['count'] for row in template_statistics] or [0]
            ),
        ),
        'has_template_statistics': bool(template_statistics),
        'jobs': render_template(
            'views/dashboard/_jobs.html',
            jobs=immediate_jobs
        ),
        'has_jobs': bool(immediate_jobs)
    }