Example #1
0
def overlay_template_pdf():
    """
    The api app calls this with a PDF as the POST body, expecting to receive a PDF back with the red overlay applied.

    This endpoint will raise an error if you try and include a page number because it assumes you meant to ask for a png
    in that case.
    """
    encoded_string = request.get_data()

    if not encoded_string:
        raise InvalidRequest('no data received in POST')

    if request.args:
        raise InvalidRequest(
            f'Did not expect any args but received {request.args}. Did you mean to call overlay.png?'
        )

    pdf = PdfFileReader(BytesIO(encoded_string))

    for i in range(pdf.numPages):
        _colour_no_print_areas_of_page_in_red(pdf.getPage(i),
                                              is_first_page=(i == 0))

    return send_file(filename_or_fp=bytesio_from_pdf(pdf),
                     mimetype='application/pdf')
Example #2
0
def overlay_template_png_for_page():
    """
    The admin app calls this multiple times to get pngs of each separate page to show on the front end.

    This endpoint expects a "page_number" param that _must_ be included. It also includes as the HTTP POST body the
    binary data of that individual page of the PDF.
    """
    encoded_string = request.get_data()

    if not encoded_string:
        raise InvalidRequest('no data received in POST')

    file_data = BytesIO(encoded_string)

    if 'is_first_page' in request.args:
        is_first_page = request.args.get('is_first_page', '').lower() == 'true'
    elif 'page_number' in request.args:
        page = int(request.args.get('page_number'))
        is_first_page = page == 1  # page_number arg is one-indexed
    else:
        raise InvalidRequest(
            f'page_number or is_first_page must be specified in request params {request.args}'
        )

    return send_file(
        filename_or_fp=png_from_pdf(
            _colour_no_print_areas_of_single_page_pdf_in_red(
                file_data, is_first_page=is_first_page),
            # the pdf is only one page, so this is always 1.
            page_number=1),
        mimetype='image/png',
    )
Example #3
0
def _colour_no_print_areas_of_single_page_pdf_in_red(src_pdf, is_first_page):
    """
    Overlays the non-printable areas onto the src PDF, this is so users know which parts of they letter fail validation.
    This function expects that src_pdf only represents a single page. It adds red areas (if `is_first_page` is set, then
    it'll add red areas around the address window too) and returns a single page pdf.

    :param BytesIO src_pdf: A file-like representing a single page pdf
    :param bool is_first_page: true if we should overlay the address block red area too.
    """
    pdf = PdfFileReader(src_pdf)

    if pdf.numPages != 1:
        # this function is used to render images, which call template-preview separately for each page. This function
        # should be colouring a single page pdf (which might be any individual page of an original precompiled letter)
        raise InvalidRequest(
            '_colour_no_print_areas_of_page_in_red should only be called for a one-page-pdf'
        )

    page = pdf.getPage(0)
    _colour_no_print_areas_of_page_in_red(page, is_first_page)

    out = bytesio_from_pdf(pdf)
    # it's a good habit to put things back exactly the way we found them
    src_pdf.seek(0)
    return out
Example #4
0
def sanitise_precompiled_letter():
    encoded_string = request.get_data()
    allow_international_letters = (
        request.args.get('allow_international_letters') == 'true')

    if not encoded_string:
        raise InvalidRequest('no-encoded-string')

    sanitise_json = sanitise_file_contents(
        encoded_string,
        allow_international_letters=allow_international_letters,
    )
    status_code = 400 if sanitise_json.get('message') else 200

    return jsonify(sanitise_json), status_code
def _does_pdf_contain_colorspace(colourspace, data):
    doc = fitz.open(stream=data, filetype="pdf")
    for i in range(len(doc)):
        try:
            page = doc.getPageImageList(i)
        except RuntimeError:
            current_app.logger.warning("Fitz couldn't read page info for page {}".format(i + 1))
            raise InvalidRequest("Invalid PDF on page {}".format(i + 1))
        for img in page:
            xref = img[0]
            pix = fitz.Pixmap(doc, xref)
            if colourspace in pix.colorspace.__str__():
                data.seek(0)
                return True
    data.seek(0)
    return False