Download dynamic file with GWT

Maksim picture Maksim · May 12, 2010 · Viewed 22.8k times · Source

I have a GWT page where user enter data (start date, end date, etc.), then this data goes to the server via RPC call. On the server I want to generate Excel report with POI and let user save that file on their local machine.

This is my test code to stream file back to the client but for some reason I think it does not know how to stream file to the client when I'm using RPC:

public class ReportsServiceImpl extends RemoteServiceServlet implements ReportsService {
    public String myMethod(String s) {

        File f = new File("/excelTestFile.xls");

        String filename = f.getName();

        int length = 0;

        try {
            HttpServletResponse resp = getThreadLocalResponse();
            ServletOutputStream op = resp.getOutputStream();
            ServletContext context = getServletConfig().getServletContext();
            resp.setContentType("application/octet-stream");
            resp.setContentLength((int) f.length());
            resp.setHeader("Content-Disposition", "attachment; filename*=\"utf-8''" + filename + "");

            byte[] bbuf = new byte[1024];
            DataInputStream in = new DataInputStream(new FileInputStream(f));

            while ((in != null) && ((length = in.read(bbuf)) != -1)) {
                op.write(bbuf, 0, length);
            }

            in.close();
            op.flush();
            op.close();

        }
        catch (Exception ex) {
            ex.printStackTrace();
        }

        return "Server says: " + filename;
    }
}

I've read somewhere on internet that you can't do file stream with RPC and I have to use Servlet for that. Is there any example of how to use Servlet and how to call that servlet from ReportsServiceImpl. Do I really need to make a servlet or it is possible to stream it back with my RPC?

Answer

Sripathi Krishnan picture Sripathi Krishnan · May 13, 2010

You have to make a regular Servlet, you cannot stream binary data from ReportsServiceImpl. Also, there is no way to call the servlet from ReportsServiceImpl - your client code has to directly invoke the servlet.

On the client side, you'd have to create a normal anchor link with the parameters passed via the query string. Something like <a href="http://myserver.com/myservlet?parm1=value1&.."</a>.

On the server side, move your code to a standard Servlet, one that does NOT inherit from RemoteServiceServlet. Read the parameters from the request object, create the excel and send it back to the client. The browser will automatically popup the file download dialog box.