Using PyLaTeX with Streamlit

So I was looking for a way to make the user press on the download button to generate a pdf containing both text and figures(plots, charts, etc.), and download it, I did it using PyLatex:

def gen_pdf():
    # initialize a Document
    doc = Document('tmppdf', geometry_options=geometry_options)

    # this is a sample of a document, you could add more sections
    with doc.create(MiniPage(align='c')):
        doc.append(LargeText(bold("Title")))
    
    # plot saved as png
    image_filename = 'path/to/image.png'
    with doc.create(Section('Section Title')):
        with doc.create(Figure(position='h!')) as fig:
            fig.add_image(image_filename,
                          width='15cm')
            fig.add_caption('Caption for the figure')
    
    # generate the pdf file
    # this file will be generated at the Streamlit server side under the name *tmppdf.pdf*
    doc.generate_pdf("tmppdf", clean_tex=False)
    
    # Open the file and read it as bytes
    with open("tmppdf.pdf", "rb") as pdf_file:
        PDFbyte = pdf_file.read()
  
    #  return the bytes object created *PDFbyte*since the data argument in the download button must be string or bytes or file
    return PDFbyte

# the download button will get the generated file stored in Streamlit server side, and download it at the user's side
st.download_button(label="Download PDF Report",
                   key='download_pdf_btn',
                   data=gen_pdf(),
                   file_name='name_of_your_file.pdf', # this might be changed from browser after pressing on the download button
                   mime='application/octet-stream',)

See see Pylatex to add more sections to your pdf
I know there were other solutions, but they didn’t work for my case, I needed to add text and figures in specific formats and I thought of sharing for future reference.

1 Like

This is a good suggestion, however I can not make this work entirely. Can you edit your answer with some details to make a working example? For example:
Which libraries that need inclusion, I guess pylatex, so
from pylatex import *
since the Document class comes from there.
Even with that import the bold("Title") did not work, and the geometry_options is not defined.

When I removed those details another error I got is that I need to either specify or download a latex-compiler. I tried pip install pdflatex and then added a compiler as argument in doc.generate_pdf("tmppdf", clean_tex=False, compiler='pdflatex'), as suggested by other threads here and here. However - no success, I get the same error that no latex compiler is found.

And, is there a latex compiler installed on your system?
What platform are we talking about?

Well I do not have Miktex installed, I have installed pdflatex via pip, as was suggested by the threads I mentioned. The error message from python said: Either specify a LaTex compiler or make sure you have latexmk or pdfLaTex installed.
I will be running the streamlit application in the cloud (azure) so if I need to install the compiler in another way I’m not sure it will work in the cloud.

No matter on which platform, you need a latex compiler.

This will not install any latex compiler, just another python wrapper that IMHO you don’t need at all.
Don’t believe or copy everything you find on Stackoverflow… :wink:

If you want to deploy on Streamlit Cloud, you probably need at least the following package in your packages.txt file:

texlive

Maybe some more packages…

I don’t know the Azure environment and how deployment works, it should be doable, but a latex compiler is required in any case.

Thank you for your replies. I interpreted the python error message as that a pip installation of pdflatex would be sufficient, but apparently not.
For now I will continue my work using the fpdf-package instead, though not as flexible as latex it gets the job done good enough at this stage. If I ever install a latex compiler on Azure cloud I’ll keep the community posted.

Even with that import the bold("Title") did not work

This one comes from pylatex.utils:

from pylatex.utils import bold

and the geometry_options is not defined.

The geometry_options parameter, you can go without it, it’s not a requirement for this script to work. I should have removed it in my example!
I used it to specify margins in the generated pdf:

geometry_options = {"margin": "0.7in"}

Please see documentation of Pylatex if you want to further analyze and use the parameter

As for the compiler issue:
The error you had should be stating that “Either specify a LaTex compiler or make sure you have latexmk or pdfLaTex installed.”
So (as @Franky1 said as well) you must have it installed in your system, and not as a python wrapper!
In my case, I have installed latexmk in my system using MikTex.
You can follow these steps to do so depending on your OS, then you don’t need to sepcify a compiler in the generate_pdf function.

Good luck!

This topic was automatically closed 365 days after the last reply. New replies are no longer allowed.