Liferay diaries: Serving resources from a portlet with Spring

Posted on by George Georgovasilis

So there comes the day when you finally have to serve an image, pdf or excel report generated by a portlet or, more elegantly, by a Spring controller backing a portlet. At a first take this may seem impossible since the markup produced by a portlet is embedded in the markup (i.e. HTML) of all the other portlets running on that page and then decorated by the portal's theme which makes it pretty much impossible to generate a standalone XML or even a binary file like an image from a database or a PDF report.

The elements of the solution is provided in this post [1] which needs to be adapted a little bit for our Spring setup.

1. Requesting the resource

The HTML must request the resource (here: an Excel report over an account balance) by using the portlet:resourceURL tag:

<portlet:resourceURL id="searchBalanceExcel" var="searchBalanceExcelURL"/>
<a href="<%=searchBalanceExcelURL%>">Download Report</a>

2. Serving the resource

Our controller needs to provide a handling method annotated with @ResourceMapping:

@ResourceMapping("searchBalanceExcel")
public ModelAndView findDeliveries(BalanceQuery query,BindingResult result,ResourceRequest request, ResourceResponse response, ModelMap modelMap) throws Exception{
 
ModelAndView mav = new ModelAndView("balanceReportExcel");
 
if (!result.hasErrors()) {
 query.setCredentials(getLoggedInCustomerCredentials());
 List<Balance> rs = customersService.findBalance(query);
 modelMap.put("result", rs);
}
response.setContentType("application/vnd.ms-excel");
response.setCharacterEncoding("UTF-8");
modelMap.put("balanceQuery", query);
return mav;
}

In this case the Excel is rendered by a JSP (trivia: MS Excel actually can parse a specially formatted HTML as an Excel file), but the response object offers an OutputStream which can be written binary data to.

Resources

[1] Portlet 2.0 AJAX serveResource portlet:resourceURL does not work in 5.0.1

http://www.liferay.com/community/forums/-/message_boards/message/937530

This entry was posted in Liferay, portlet, spring and tagged by George Georgovasilis