edc-pdf-reports


Nameedc-pdf-reports JSON
Version 0.3.25 PyPI version JSON
download
home_pagehttps://github.com/clinicedc/edc-pdf-reports
SummaryReport classes using reportlab/pdf for clinicedc/edc projects
upload_time2024-11-28 17:07:18
maintainerNone
docs_urlNone
authorErik van Widenfelt
requires_python>=3.12
licenseGPL license, see LICENSE
keywords django edc pdf reportlab clinicedc clinical trials
VCS
bugtrack_url
requirements No requirements were recorded.
Travis-CI No Travis.
coveralls test coverage
            |pypi| |actions| |codecov| |downloads|


edc-pdf-reports
---------------

Reportlab/PDF classes for clinicedc/edc projects

Overview
========

This module offers functionality to link a PDF report to a model registered with ModelAdmin.

The ``CrfPdfReport`` class links a PDF report to a model registered with ModelAdmin. A link as is added
to the changelist that opens an intermediate page to ask for a password. From the intermediate page
a secure file is downloaded into the browser. See also ``PdfIntermediateView`` and ``PrintPdfReportView``.

For this to work, you need to:

* create a pdf report class;
* declare the model with the ``PdfReportModelMixin`` and set the ``pdf_report_cls`` attr on the model;
* declare the model's ModelAdmin class with ``PdfButtonModelAdminMixin``;
* add ``print_to_pdf_action`` to Modeladmin.actions (required to print one or more pdfs using actions);
* add "pdf_button" to the list_display (required for pdf button to appear on each row);
* update your app's urls;
* add edc_pdf_reports to INSTALLED_APPS.

Your changelist will include options for printing one or many PDF reports into a
password protected and secure PDF file.

If you are using this module outside of a clinicedc/edc project, you need to update two
``settings`` attributes:

.. code-block:: python

    # settings.py
    # tells edc_pdf_reports to not import two clinicedc modules
    EDC_PDF_REPORTS_INTEGRATE_EDC = False
    # points
    EDC_PDF_REPORTS_TEMPLATES = {"pdf_intermediate": "edc_pdf_reports/generic_pdf_intermediate.html"}




DeathReport as an example
+++++++++++++++++++++++++

``edc_adverse_event`` has this configured for its ``DeathReport`` model. Let's use this as an example.

Create the ``DeathReport`` model:

.. code-block:: python

    # models.py

    class DeathReport(PdfReportModelMixin, BaseUuidModel):

        pdf_report_cls = DeathPdfReport


Create the ``DeathPdfReport`` class. ``DeathPdfReport`` inherits from  ``CrfPdfReport``. Link the ``model`` and
`changelist_url`` to this PDF report class.

.. code-block:: python

    # death_pdf_report.py

    class DeathPdfReport(CrfPdfReport):
        model = f"{get_adverse_event_app_label()}.deathreport"
        changelist_url = (
            f"{get_adverse_event_app_label()}_admin:{get_adverse_event_app_label()}_"
            "deathreport_changelist"
        )

        def get_report_story(self, **kwargs):
            ...

Declare the ModelAdmin class with ``PdfButtonModelAdminMixin``:

.. code-block:: python

    # admin.py

    @admin.action(permissions=["view"], description="Print Death Reports as PDF")
    def print_to_pdf_action(modeladmin, request, queryset):
        return print_selected_to_pdf_action(modeladmin, request, queryset)


    class DeathReportModelAdmin(PdfButtonModelAdminMixin, DeathReportModelAdminMixin):
        actions = [print_to_pdf_action]
        list_display = ["subject_identifier", "pdf_button", ...]


Update your url patterns:

.. code-block:: python

    # urls.py
    url_patterns = [
        ...,
        *paths_for_urlpatterns("edc_pdf_reports"),
        ...]


Add to ``settings``:

.. code-block:: python

    # settings.py
    INSTALLED_APPS = [
        ...,
        "edc_pdf_reports.apps.AppConfig"
        ...]


Your changelist will have the new column "PDF" and the print as pdf action will be available.

|changelist|

The intermediate page, linked from the changelist, will look like this:

|intermediate_page|

Note the passphrase and click "Create File". The file will be created in the view and downloaded by the browser.

Creating a PDF file outside of the view
=======================================

The view ``PrintPdfReportView`` uses function ``write_queryset_to_secure_pdf`` to create a PDF.
You can access this function directly.

For example:

.. code-block:: python


    import mempass
    import tempfile
    from pathlib import Path
    from django.contrib.auth.models import User
    from edc_pdf_reports.utils import write_queryset_to_secure_pdf, write_model_to_insecure_pdf
    from effect_ae.models import DeathReport

    dir = tempfile.mkdtemp()
    p = Path(dir)
    qs = DeathReport.objects.all()
    user = User.objects.get(username="erikvw")

    # create a secure PDF file for the queryset
    q = p / "death_reports_secure.pdf"
    password = mempass.mkpassword(2)
    buffer = write_queryset_to_secure_pdf(queryset=qs, password=password, user=user)
    q.write_bytes(buffer.getbuffer())
    print(q)

    # create an insecure PDF file for one model instance
    q = p / "death_reports_insecure.pdf"
    model_obj = qs[0]
    buffer = write_model_to_insecure_pdf(model_obj, user=user)
    q.write_bytes(buffer.getbuffer())
    print(q)

Add watermark to report
=======================

When testing, you can add a watermark to the report. In your test settings set the following:

.. code-block:: python

    EDC_PDF_REPORTS_WATERMARK_WORD = "SAMPLE"
    EDC_PDF_REPORTS_WATERMARK_FONT = ("Helvetica", 100)

The watermark prints at a 45 degree rotation across the center of each page.




.. |intermediate_page| image:: /docs/images/intermediate_page.png
   :alt: Intermediate page

.. |changelist| image:: /docs/images/changelist.png
   :alt: ChangeList

.. |pypi| image:: https://img.shields.io/pypi/v/edc-pdf-reports.svg
    :target: https://pypi.python.org/pypi/edc-pdf-reports

.. |actions| image:: https://github.com/clinicedc/edc-pdf-reports/actions/workflows/build.yml/badge.svg
  :target: https://github.com/clinicedc/edc-pdf-reports/actions/workflows/build.yml

.. |codecov| image:: https://codecov.io/gh/clinicedc/edc-pdf-reports/branch/develop/graph/badge.svg
  :target: https://codecov.io/gh/clinicedc/edc-pdf-reports

.. |downloads| image:: https://pepy.tech/badge/edc-pdf-reports
   :target: https://pepy.tech/project/edc-pdf-reports

            

Raw data

            {
    "_id": null,
    "home_page": "https://github.com/clinicedc/edc-pdf-reports",
    "name": "edc-pdf-reports",
    "maintainer": null,
    "docs_url": null,
    "requires_python": ">=3.12",
    "maintainer_email": null,
    "keywords": "django edc pdf reportlab, clinicedc, clinical trials",
    "author": "Erik van Widenfelt",
    "author_email": "ew2789@gmail.com",
    "download_url": "https://files.pythonhosted.org/packages/bb/3c/a6f938f5f2400cd96c83b59a794efe1507ebd31bbab29046cba18af30c0a/edc_pdf_reports-0.3.25.tar.gz",
    "platform": null,
    "description": "|pypi| |actions| |codecov| |downloads|\n\n\nedc-pdf-reports\n---------------\n\nReportlab/PDF classes for clinicedc/edc projects\n\nOverview\n========\n\nThis module offers functionality to link a PDF report to a model registered with ModelAdmin.\n\nThe ``CrfPdfReport`` class links a PDF report to a model registered with ModelAdmin. A link as is added\nto the changelist that opens an intermediate page to ask for a password. From the intermediate page\na secure file is downloaded into the browser. See also ``PdfIntermediateView`` and ``PrintPdfReportView``.\n\nFor this to work, you need to:\n\n* create a pdf report class;\n* declare the model with the ``PdfReportModelMixin`` and set the ``pdf_report_cls`` attr on the model;\n* declare the model's ModelAdmin class with ``PdfButtonModelAdminMixin``;\n* add ``print_to_pdf_action`` to Modeladmin.actions (required to print one or more pdfs using actions);\n* add \"pdf_button\" to the list_display (required for pdf button to appear on each row);\n* update your app's urls;\n* add edc_pdf_reports to INSTALLED_APPS.\n\nYour changelist will include options for printing one or many PDF reports into a\npassword protected and secure PDF file.\n\nIf you are using this module outside of a clinicedc/edc project, you need to update two\n``settings`` attributes:\n\n.. code-block:: python\n\n    # settings.py\n    # tells edc_pdf_reports to not import two clinicedc modules\n    EDC_PDF_REPORTS_INTEGRATE_EDC = False\n    # points\n    EDC_PDF_REPORTS_TEMPLATES = {\"pdf_intermediate\": \"edc_pdf_reports/generic_pdf_intermediate.html\"}\n\n\n\n\nDeathReport as an example\n+++++++++++++++++++++++++\n\n``edc_adverse_event`` has this configured for its ``DeathReport`` model. Let's use this as an example.\n\nCreate the ``DeathReport`` model:\n\n.. code-block:: python\n\n    # models.py\n\n    class DeathReport(PdfReportModelMixin, BaseUuidModel):\n\n        pdf_report_cls = DeathPdfReport\n\n\nCreate the ``DeathPdfReport`` class. ``DeathPdfReport`` inherits from  ``CrfPdfReport``. Link the ``model`` and\n`changelist_url`` to this PDF report class.\n\n.. code-block:: python\n\n    # death_pdf_report.py\n\n    class DeathPdfReport(CrfPdfReport):\n        model = f\"{get_adverse_event_app_label()}.deathreport\"\n        changelist_url = (\n            f\"{get_adverse_event_app_label()}_admin:{get_adverse_event_app_label()}_\"\n            \"deathreport_changelist\"\n        )\n\n        def get_report_story(self, **kwargs):\n            ...\n\nDeclare the ModelAdmin class with ``PdfButtonModelAdminMixin``:\n\n.. code-block:: python\n\n    # admin.py\n\n    @admin.action(permissions=[\"view\"], description=\"Print Death Reports as PDF\")\n    def print_to_pdf_action(modeladmin, request, queryset):\n        return print_selected_to_pdf_action(modeladmin, request, queryset)\n\n\n    class DeathReportModelAdmin(PdfButtonModelAdminMixin, DeathReportModelAdminMixin):\n        actions = [print_to_pdf_action]\n        list_display = [\"subject_identifier\", \"pdf_button\", ...]\n\n\nUpdate your url patterns:\n\n.. code-block:: python\n\n    # urls.py\n    url_patterns = [\n        ...,\n        *paths_for_urlpatterns(\"edc_pdf_reports\"),\n        ...]\n\n\nAdd to ``settings``:\n\n.. code-block:: python\n\n    # settings.py\n    INSTALLED_APPS = [\n        ...,\n        \"edc_pdf_reports.apps.AppConfig\"\n        ...]\n\n\nYour changelist will have the new column \"PDF\" and the print as pdf action will be available.\n\n|changelist|\n\nThe intermediate page, linked from the changelist, will look like this:\n\n|intermediate_page|\n\nNote the passphrase and click \"Create File\". The file will be created in the view and downloaded by the browser.\n\nCreating a PDF file outside of the view\n=======================================\n\nThe view ``PrintPdfReportView`` uses function ``write_queryset_to_secure_pdf`` to create a PDF.\nYou can access this function directly.\n\nFor example:\n\n.. code-block:: python\n\n\n    import mempass\n    import tempfile\n    from pathlib import Path\n    from django.contrib.auth.models import User\n    from edc_pdf_reports.utils import write_queryset_to_secure_pdf, write_model_to_insecure_pdf\n    from effect_ae.models import DeathReport\n\n    dir = tempfile.mkdtemp()\n    p = Path(dir)\n    qs = DeathReport.objects.all()\n    user = User.objects.get(username=\"erikvw\")\n\n    # create a secure PDF file for the queryset\n    q = p / \"death_reports_secure.pdf\"\n    password = mempass.mkpassword(2)\n    buffer = write_queryset_to_secure_pdf(queryset=qs, password=password, user=user)\n    q.write_bytes(buffer.getbuffer())\n    print(q)\n\n    # create an insecure PDF file for one model instance\n    q = p / \"death_reports_insecure.pdf\"\n    model_obj = qs[0]\n    buffer = write_model_to_insecure_pdf(model_obj, user=user)\n    q.write_bytes(buffer.getbuffer())\n    print(q)\n\nAdd watermark to report\n=======================\n\nWhen testing, you can add a watermark to the report. In your test settings set the following:\n\n.. code-block:: python\n\n    EDC_PDF_REPORTS_WATERMARK_WORD = \"SAMPLE\"\n    EDC_PDF_REPORTS_WATERMARK_FONT = (\"Helvetica\", 100)\n\nThe watermark prints at a 45 degree rotation across the center of each page.\n\n\n\n\n.. |intermediate_page| image:: /docs/images/intermediate_page.png\n   :alt: Intermediate page\n\n.. |changelist| image:: /docs/images/changelist.png\n   :alt: ChangeList\n\n.. |pypi| image:: https://img.shields.io/pypi/v/edc-pdf-reports.svg\n    :target: https://pypi.python.org/pypi/edc-pdf-reports\n\n.. |actions| image:: https://github.com/clinicedc/edc-pdf-reports/actions/workflows/build.yml/badge.svg\n  :target: https://github.com/clinicedc/edc-pdf-reports/actions/workflows/build.yml\n\n.. |codecov| image:: https://codecov.io/gh/clinicedc/edc-pdf-reports/branch/develop/graph/badge.svg\n  :target: https://codecov.io/gh/clinicedc/edc-pdf-reports\n\n.. |downloads| image:: https://pepy.tech/badge/edc-pdf-reports\n   :target: https://pepy.tech/project/edc-pdf-reports\n",
    "bugtrack_url": null,
    "license": "GPL license, see LICENSE",
    "summary": "Report classes using reportlab/pdf for clinicedc/edc projects",
    "version": "0.3.25",
    "project_urls": {
        "Homepage": "https://github.com/clinicedc/edc-pdf-reports"
    },
    "split_keywords": [
        "django edc pdf reportlab",
        " clinicedc",
        " clinical trials"
    ],
    "urls": [
        {
            "comment_text": "",
            "digests": {
                "blake2b_256": "9f4007315208ee246465a9d7566cbe4314bcc67deb25b39bb7673d85f8651510",
                "md5": "ca6eab7fbc25ad199e60181620f9fdd3",
                "sha256": "a46c2282191feadf17a92d529955dab9c649515aad1109e492d8ed7f84114593"
            },
            "downloads": -1,
            "filename": "edc_pdf_reports-0.3.25-py3-none-any.whl",
            "has_sig": false,
            "md5_digest": "ca6eab7fbc25ad199e60181620f9fdd3",
            "packagetype": "bdist_wheel",
            "python_version": "py3",
            "requires_python": ">=3.12",
            "size": 47362,
            "upload_time": "2024-11-28T17:07:17",
            "upload_time_iso_8601": "2024-11-28T17:07:17.676255Z",
            "url": "https://files.pythonhosted.org/packages/9f/40/07315208ee246465a9d7566cbe4314bcc67deb25b39bb7673d85f8651510/edc_pdf_reports-0.3.25-py3-none-any.whl",
            "yanked": false,
            "yanked_reason": null
        },
        {
            "comment_text": "",
            "digests": {
                "blake2b_256": "bb3ca6f938f5f2400cd96c83b59a794efe1507ebd31bbab29046cba18af30c0a",
                "md5": "4e98d71394a7aee18d2c6bca481c5609",
                "sha256": "c86362add85bc827368fc6a5553c6e56e9dcc4a55bd0631ec32c4396b3e905f2"
            },
            "downloads": -1,
            "filename": "edc_pdf_reports-0.3.25.tar.gz",
            "has_sig": false,
            "md5_digest": "4e98d71394a7aee18d2c6bca481c5609",
            "packagetype": "sdist",
            "python_version": "source",
            "requires_python": ">=3.12",
            "size": 123974,
            "upload_time": "2024-11-28T17:07:18",
            "upload_time_iso_8601": "2024-11-28T17:07:18.884295Z",
            "url": "https://files.pythonhosted.org/packages/bb/3c/a6f938f5f2400cd96c83b59a794efe1507ebd31bbab29046cba18af30c0a/edc_pdf_reports-0.3.25.tar.gz",
            "yanked": false,
            "yanked_reason": null
        }
    ],
    "upload_time": "2024-11-28 17:07:18",
    "github": true,
    "gitlab": false,
    "bitbucket": false,
    "codeberg": false,
    "github_user": "clinicedc",
    "github_project": "edc-pdf-reports",
    "travis_ci": false,
    "coveralls": true,
    "github_actions": true,
    "lcname": "edc-pdf-reports"
}
        
Elapsed time: 0.51421s