<?xml version="1.0" encoding="UTF-8"?>
<feed xmlns="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <title>PDF file returned from serveResource does not render</title>
  <link rel="self" href="https://liferay.dev/c/message_boards/find_thread?p_l_id=119785294&amp;threadId=121522536" />
  <subtitle>PDF file returned from serveResource does not render</subtitle>
  <id>https://liferay.dev/c/message_boards/find_thread?p_l_id=119785294&amp;threadId=121522536</id>
  <updated>2026-04-05T04:15:20Z</updated>
  <dc:date>2026-04-05T04:15:20Z</dc:date>
  <entry>
    <title>RE: RE: PDF file returned from serveResource does not render</title>
    <link rel="alternate" href="https://liferay.dev/c/message_boards/find_message?p_l_id=119785294&amp;messageId=121526833" />
    <author>
      <name>Pete Helgren</name>
    </author>
    <id>https://liferay.dev/c/message_boards/find_message?p_l_id=119785294&amp;messageId=121526833</id>
    <updated>2022-10-03T14:06:01Z</updated>
    <published>2022-10-02T19:27:25Z</published>
    <summary type="html">&lt;p&gt;Thanks Krishna,&lt;/p&gt;
&lt;p&gt;I had come across the PortletResponseUtil.sendFile solution early on
  in my research but it returned the same Response.  Not sure why this
  particular solution wasn't working.  What I ended up doing was to
  capture the response on the client and then render it like so after a
  successful ajax call:&lt;/p&gt;
&lt;p&gt; &lt;/p&gt;
&lt;pre&gt;
&lt;code class="language-javascript"&gt;        let blob = new Blob([result], {type: 'application/pdf'});
        
        var filename = &amp;quot;Data-Report.pdf&amp;quot;;
        
        var element = document.createElement('a');
        
        let objectURL = window.URL.createObjectURL(blob);
        
        element.href = objectURL;
        
        element.target = '_self';
        
        element.download = filename;

        element.style.display = 'none';
        
        document.body.appendChild(element);

        element.click();

        document.body.removeChild(element);
        
        return ;&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;Not optimal, but it DID work.  Still, I'd love to know why the
  original approach wasn't working&lt;br /&gt; .&lt;br /&gt; Appreciate the feedback.&lt;br /&gt;
  &lt;br /&gt; Pete&lt;/p&gt;</summary>
    <dc:creator>Pete Helgren</dc:creator>
    <dc:date>2022-10-02T19:27:25Z</dc:date>
  </entry>
  <entry>
    <title>RE: PDF file returned from serveResource does not render</title>
    <link rel="alternate" href="https://liferay.dev/c/message_boards/find_message?p_l_id=119785294&amp;messageId=121525553" />
    <author>
      <name>Krishna Rajappa</name>
    </author>
    <id>https://liferay.dev/c/message_boards/find_message?p_l_id=119785294&amp;messageId=121525553</id>
    <updated>2022-09-29T16:54:04Z</updated>
    <published>2022-09-29T01:48:24Z</published>
    <summary type="html">&lt;p&gt;This might work PortletResponseUtil.sendFile but You might need to
  clean up the file is this api would generates and stores the pdf in
  your server.&lt;/p&gt;
&lt;p&gt;Thanks, &lt;/p&gt;
&lt;p&gt;Krishna &lt;/p&gt;</summary>
    <dc:creator>Krishna Rajappa</dc:creator>
    <dc:date>2022-09-29T01:48:24Z</dc:date>
  </entry>
  <entry>
    <title>PDF file returned from serveResource does not render</title>
    <link rel="alternate" href="https://liferay.dev/c/message_boards/find_message?p_l_id=119785294&amp;messageId=121522535" />
    <author>
      <name>Pete Helgren</name>
    </author>
    <id>https://liferay.dev/c/message_boards/find_message?p_l_id=119785294&amp;messageId=121522535</id>
    <updated>2022-09-26T15:48:44Z</updated>
    <published>2022-09-23T19:24:54Z</published>
    <summary type="html">&lt;p&gt;I have a FreeMarker portlet that invokes a method that creates a PDF
  file using iTextPDF.  I know the file is created succesfully because I
  can navigate to the location and doubleclick and open it. So, I
  created some code to return the file to the browser:&lt;/p&gt;
&lt;pre&gt;
&lt;code class="language-java"&gt;	@Override
	public boolean serveResource(ResourceRequest resourceRequest, ResourceResponse resourceResponse)
			throws PortletException {
		
		String body = &amp;quot;&amp;quot;;
		
		// Just to get a request object we can work with
		HttpServletRequest httprequest = PortalUtil.getHttpServletRequest(resourceRequest);
		HttpServletRequest osr = PortalUtil.getOriginalServletRequest(httprequest);
		HttpServletResponse httpresponse = PortalUtil.getHttpServletResponse(resourceResponse);

		String fileRef = &amp;quot;/mydata/data/iTextTable.pdf&amp;quot;;
		
        File downloadFile = new File(fileRef);

        // modifies response
        httpresponse.setContentType(&amp;quot;application/pdf&amp;quot;);
        httpresponse.setContentLength((int) downloadFile.length());
        
        String headerValue = String.format(&amp;quot;inline; filename=\&amp;quot;%s\&amp;quot;&amp;quot;, fileRef);
        
        // set caching to no cache by whatever means you can.
        httpresponse.addHeader(&amp;quot;Content Disposition&amp;quot;, headerValue);
        httpresponse.addHeader(&amp;quot;Cache-Control&amp;quot;, &amp;quot;no-cache, no-store, must-revalidate&amp;quot;);
        httpresponse.setHeader(&amp;quot;Pragma&amp;quot;, &amp;quot;no-cache&amp;quot;);
		String fileRef = BASE_DATA_PATH + &amp;quot;iSortedTextTable.pdf&amp;quot;;
		
        File downloadFile = new File(fileRef);

        try {
            FileInputStream inStream = new FileInputStream(downloadFile);
          
	        OutputStream outStream =  httpresponse.getOutputStream();
	         
	        byte[] buffer = new byte[4096];
	        int bytesRead = -1;
	         
	        while ((bytesRead = inStream.read(buffer)) &amp;gt; 0) {
	            outStream.write(buffer, 0, bytesRead);
	        }
	         
	        outStream.flush();
	        inStream.close();
            outStream.close();
        
        } catch(Exception e) {
        	e.printStackTrace();
        }

		return false;
	}&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;That is a snippet that I hope contains the relevant code.  The code
  runs without error.   In debug I can see that bytes are being written
  to the output stream but in the browser, nothing renders.  If I use
  the console to view the contant of the http response, I see stuff like this:&lt;br /&gt;
  &lt;br /&gt;  %PDF-1.4&lt;br /&gt; %����&lt;br /&gt; 2 0 obj&lt;br /&gt; &amp;lt;&amp;lt;/Length 544/Filter/FlateDecode&amp;gt;&amp;gt;stream&lt;/p&gt;
&lt;p&gt;
  &lt;br /&gt; ....and much much more &amp;quot;junk&amp;quot;&lt;/p&gt;
&lt;p&gt;So I am not sure what is going on.  It *seems* like the pdf is being
  sent as a response but there is something wrong the data somehow.  I
  have searched for possible causes for a few days but I haven't come
  across a solution.  Is there a setting or config option I need to
  change?  Seems like I am just missing something simple.&lt;br /&gt;
  &lt;br /&gt; Thanks,&lt;br /&gt;
  &lt;br /&gt; Pete&lt;/p&gt;</summary>
    <dc:creator>Pete Helgren</dc:creator>
    <dc:date>2022-09-23T19:24:54Z</dc:date>
  </entry>
</feed>
