It is not unfamiliar to see an application using servlet for file downloading these days. However, you still could often see people having problem to do the download using IE.
If you have been searching for a solution on the Internet, probably you got many suggestions of how to set the headers. However, unfortunately, none of them actually work. In this article, I am going to introduce the only way I found that could make the servlet download functional with IE.
Before we get to the details of code, let’s make a note of the advantage of using servlet. The benefit is that you can hide the location of the file to the client, as you would not let user to download the original file directly but the one generated on-fly.
Regardless the browser compatible problem, the work flow should be
Read content of the file into input stream
-> Write the stream out as a MS office file
And this works fine for FireFox and some other browsers. The problem for IE is it requires caching of the file before downloading.
Read content of the file into input stream
-> Write the content into a local file as a cache
-> Read the content of local file into input stream
-> Write the stream out as a MS office file
It sounds very redundant, but that’s the only functional way that I could find.
public void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException, FileNotFoundException {
String filePath = “somewhere\you\hold\your\file”;
File tempFile = new File(filePath);
// Read content of the file into input stream
FileInputStream tempInput = new FileInputStream(tempFile);
//create a local temporary file as a cache
File csvFile = new File("trial.csv");
FileOutputStream csvFileOutputStream = null;
boolean fileExists = false;
try {
// Write the content into a local file as a cache
csvFileOutputStream = new FileOutputStream(csvFile);
BufferedInputStream tempBuf = new BufferedInputStream(tempInput);
int readBytes = 0;
while ((readBytes = tempBuf.read()) != -1) {
csvFileOutputStream.write(readBytes);
}
fileExists = true;
}
catch (Exception ie) {
fileExists = false;
}
finally {
if (csvFileOutputStream != null) {
try {
csvFileOutputStream.close();
} catch (IOException ignore) {
}
}
}
if (fileExists) {
ServletOutputStream outputStream = null;
BufferedInputStream buf = null;
try {
outputStream = response.getOutputStream();
response.setContentType("Application/ms-excel");
response.setHeader("Cache-Control", "private");
response.setHeader("Content-Disposition", "attachment; filename=trial.csv");
response.setDateHeader("Expires", 0);
response.setContentLength((int) csvFile.length());
//Read the content of local file into input stream
FileInputStream input = new FileInputStream(csvFile);
buf = new BufferedInputStream(input);
int readBytes = 0;
while ((readBytes = buf.read()) != -1) {
//Write the stream out as a MS office file
outputStream.write(readBytes);
}
}
catch (Exception ie) {
_LOGGER.error("servletoutputStream problem:" + StringUtils.stackTrace(ie));
//fileExists = false;
}
finally {
if (buf != null) {
try {
buf.close();
} catch (IOException ignore) {
}
}
if (outputStream != null) {
try {
outputStream.flush();
outputStream.close();
} catch (IOException ignore) {
}
}
}
}
}