Ask Questions and Find Answers
Important:
Ask is now read-only. You can review any existing questions and answers, but not add anything new.
But - don't panic! While ask is no more, we've replaced it with discuss - the new Liferay Discussion Forum! Read more here here or just visit the site here:
discuss.liferay.com
RE: RE: PDF file returned from serveResource does not render
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:
@Override
public boolean serveResource(ResourceRequest resourceRequest, ResourceResponse resourceResponse)
throws PortletException {
String body = "";
// 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 = "/mydata/data/iTextTable.pdf";
File downloadFile = new File(fileRef);
// modifies response
httpresponse.setContentType("application/pdf");
httpresponse.setContentLength((int) downloadFile.length());
String headerValue = String.format("inline; filename=\"%s\"", fileRef);
// set caching to no cache by whatever means you can.
httpresponse.addHeader("Content Disposition", headerValue);
httpresponse.addHeader("Cache-Control", "no-cache, no-store, must-revalidate");
httpresponse.setHeader("Pragma", "no-cache");
String fileRef = BASE_DATA_PATH + "iSortedTextTable.pdf";
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)) > 0) {
outStream.write(buffer, 0, bytesRead);
}
outStream.flush();
inStream.close();
outStream.close();
} catch(Exception e) {
e.printStackTrace();
}
return false;
}
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:
%PDF-1.4
%����
2 0 obj
<</Length 544/Filter/FlateDecode>>stream
....and much much more "junk"
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.
Thanks,
Pete
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.
Thanks,
Krishna
Thanks Krishna,
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:
let blob = new Blob([result], {type: 'application/pdf'});
var filename = "Data-Report.pdf";
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 ;
Not optimal, but it DID work. Still, I'd love to know why the
original approach wasn't working
.
Appreciate the feedback.
Pete
Powered by Liferay™