monty_lennie
monty_lennie

Reputation: 3341

axios post request and node pdfkit shows blank pdf

I am using react axios to send a post request to the express server to create a pdf using pdfkit. When it is sent back, the file is downloaded automatically. It seems to send back pdf info but when opening the file the pdf is blank.

import axios from 'axios';
import download from 'downloadjs';

const url = baseUrl + /invoice-generator/create-pdf;

export const downloadInvoiceApi = async (values) => {
  await axios.post(`${baseUrl}/invoice-generator/create-pdf`, {
    responseType: "arraybuffer",
    headers: {
      "Content-Type": "application/pdf"
    }
  })
  .then((response) => {
    download(response.data, "file.pdf", response.headers['content-type']);
  });

};


Here is the express code

import { Request, Response } from "express"
import PDFDocument from 'pdfkit';

export const createPDF = async (
    req: invoiceGeneratorRequest,
    res: Response
) => {

    try {
      res.writeHead( 200, {
        'Content-Type': 'application/pdf',
        'Content-Disposition': 'attachment; filename=test.pdf'
      } );

      let doc = new PDFDocument( {
          size: 'A4',
          margin: 50
      } );


      doc.fontSize( 12 );

      doc.text( 'PDFKit is simple', 10, 30, {
          align: 'center',
          width: 200
      } );

      doc.end();
      doc.pipe( res );

    } catch (error) {
        console.error("Error creating PDF", error)
        res.status(500).send("Error creating PDF")
    }
}

The pdf data that's returned

%PDF-1.3
%����
7 0 obj
<<
/Type /Page
/Parent 1 0 R
/MediaBox [0 0 595.28 841.89]
/Contents 5 0 R
/Resources 6 0 R
>>
endobj
6 0 obj
<<
/ProcSet [/PDF /Text /ImageB /ImageC /ImageI]
/Font <<
/F1 8 0 R
>>
>>
endobj
5 0 obj
<<
/Length 108
/Filter /FlateDecode
>>
stream
x�m�1
�0F�]��/PG�eقҡ��
�B��d���/���<��'��E]%u�vЗ�߾��V���sI�)�iHF�^+���ۼi�a�܊�}�f�~!4=��Kq
endstream
endobj
10 0 obj
(PDFKit)
endobj
11 0 obj
(PDFKit)
endobj
12 0 obj
(D:20240307162326Z)
endobj
9 0 obj
<<
/Producer 10 0 R
/Creator 11 0 R
/CreationDate 12 0 R
>>
endobj
8 0 obj
<<
/Type /Font
/BaseFont /Helvetica
/Subtype /Type1
/Encoding /WinAnsiEncoding
>>
endobj
4 0 obj
<<
>>
endobj
3 0 obj
<<
/Type /Catalog
/Pages 1 0 R
/Names 2 0 R
>>
endobj
1 0 obj
<<
/Type /Pages
/Count 1
/Kids [7 0 R]
>>
endobj
2 0 obj
<<
/Dests <<
  /Names [
]
>>
>>
endobj
xref
0 13
0000000000 65535 f 
0000000735 00000 n 
0000000792 00000 n 
0000000673 00000 n 
0000000652 00000 n 
0000000214 00000 n 
0000000125 00000 n 
0000000015 00000 n 
0000000555 00000 n 
0000000480 00000 n 
0000000394 00000 n 
0000000419 00000 n 
0000000444 00000 n 
trailer
<<
/Size 13
/Root 3 0 R
/Info 9 0 R
/ID [<c38b249f82e129b82db4804f21d40825> <c38b249f82e129b82db4804f21d40825>]
>>
startxref
839
%%EOF

And the pdf downloads correctly but when I open the PDF it's blank

Upvotes: 0

Views: 116

Answers (1)

traynor
traynor

Reputation: 8682

Change responseType value to blob:

  await axios.post(`${baseUrl}/invoice-generator/create-pdf`, {
    responseType: "blob",
    headers: {
      "Content-Type": "application/pdf"
    }
  })
  .then((response) => {
    download(response.data, "file.pdf", response.headers['content-type']);
  });

and then downloading should go something like this:

const url = window.URL.createObjectURL(response.data);
const link = document.createElement('a');
link.href = url;
link.setAttribute('download', 'test.pdf');
document.body.appendChild(link);
link.click();

document.body.removeChild(link);
URL.revokeObjectURL(url);

Upvotes: 0

Related Questions