Search code examples
node.jsstreamnestjsblob

black pdf is being downloaded from nodejs nestjs


I have third party api that serves the pdf, when I hit that url directly from postman or thunder client, it serves the pdf file, that works perfectly.

while hitting this url i am setting these headers

Accept: */*
User-Agent: Thunder Client (https://www.thunderclient.com)
x-api-key: my_key
Content-Type: application/pdf
Accept: application/pdf

Now i have wrapped this api in my nodejs API so i have used

controller

@Get("generate")
  async generate(@Res() res: any): Promise<any> {
    try {
      const pdfData = await this.myService.generate();

      res.setHeader('Content-Type', 'application/pdf');
      res.setHeader('Accept', 'application/pdf');

      // Convert the Axios response data to a readable stream
      const readableStream = new Readable();
      readableStream.push(pdfData.data);
      readableStream.push(null); // Signals the end of the stream

      // Stream the PDF data as the response
      readableStream.pipe(res);

and here is the service

async getLabelPdf(refId: string): Promise<any> {
    const url = `url`;
    const headers = {
      "x-api-key": "my_key",
      "Content-Type": "application/pdf",
      "Accept": "application/pdf"
    }
    return axios.get(url, { headers, responseType: "blob" });
  }

but this downloads the black pdf.

any solution for this?


Solution

  • This worked for me

    const pdfStream = await this.getLabelPdf();
    
    res.setHeader('Content-Disposition', 'inline; filename="thunder-file.pdf"');
    res.setHeader('Content-Type', 'application/pdf');
    res.setHeader('Accept', 'application/pdf');
    
    // Pipe the PDF stream directly to the Express response
    pdfStream.pipe(res);
    

    and

    async getLabelPdf(): Promise<any> {
        const url = `url`;
        const headers = {
          "x-api-key": "my_key",
          "Content-Type": "application/pdf",
          "Accept": "application/pdf"
        }
        return axios.get(url, { headers, responseType: "stream" }).then((res) => res.data);
      }