Java webapp:添加内容处置标头以强制浏览器“另存为”行为

时间:2010-03-08 23:23:55

标签: java jsp web-applications content-disposition

即使它不是HTTP 1.1 / RFC2616 webapps的一部分,希望强制资源在浏览器中下载(而不是显示),也可以像这样使用Content-Disposition标题:

Content-Disposition: attachment; filename=FILENAME

即使很难,它只在HTTP2的RFC2183和部分中定义,它可以在大多数Web浏览器中使用。

所以从客户端来看,一切都很好。

然而,在服务器端,在我的情况下,我有一个Java webapp,我不知道我应该如何设置该标头,特别是在以下情况下......

我将在Amazon S3实例上托管一个文件(称为“ bigfile ”)(我的S3存储桶可以使用部分地址访问,例如: files.mycompany.com / )这样用户就可以在 files.mycompany.com/bigfile 访问此文件。

现在有办法制作 servlet (或 .jsp ),以便在用户想要下载时始终添加Content-Disposition标题那个文件?

代码会是什么样的,有什么问题?如果有的话?

4 个答案:

答案 0 :(得分:4)

Pointy指出,我得到了这个工作。现在可以链接到名为download.jsp的JSP,而不是直接链接到资产 - 在我的情况下是pdfs - 它接受并解析GET参数,然后将pdf作为下载提供。

在此下载

这是我使用的jsp代码。它在IE8,Chrome和Firefox中工作:

<%@page session="false"
            contentType="text/html; charset=utf-8"
            import="java.io.IOException,
                    java.io.InputStream,
        java.io.OutputStream,
        javax.servlet.ServletContext,
        javax.servlet.http.HttpServlet,
        javax.servlet.http.HttpServletRequest,
        javax.servlet.http.HttpServletResponse,
        java.io.File,
        java.io.FileInputStream"
 %>
<%  
//Set the headers.
response.setContentType("application/x-download"); 
response.setHeader("Content-Disposition", "attachment; filename=downloaded.pdf");

[pull the file path from the request parameters]   

File file = new File("[pdf path pulled from the requests parameters]");
FileInputStream fileIn = new FileInputStream(file);
ServletOutputStream outstream = response.getOutputStream();

byte[] outputByte = new byte[40096];

while(fileIn.read(outputByte, 0, 40096) != -1)
{
    outstream.write(outputByte, 0, 40096);
}
fileIn.close();
outstream.flush();
outstream.close();

%>

答案 1 :(得分:2)

您不会拥有直接引用该文件的网址。相反,您将拥有一个指向您的servlet代码的URL(或者服务器端框架中的某种操作代码)。反过来,在设置标题后,它必须访问文件内容并将其铲出到客户端。 (您还需要记住在适当时处理缓存控制标头。)

HttpServletResponse类具有API,可让您设置所需的所有标题。您必须确保在开始转储文件内容之前设置标题,因为标题必须首先出现在发送到浏览器的流中。

这与您可能具有生成即时下载的servlet的情况没有太大区别。

编辑为了后人的缘故,我会把这些东西放在这里,但是我会注意到,当你存储一个文件,这样亚马逊会在提供文件时将这些文件吐出来。我不确定你是怎么做到的,我不确定“Content-disposition”是一个你可以这样设置的标题,但我会继续寻找。

答案 2 :(得分:0)

.htaccess文件放在根文件夹中,并带有以下行:

Header set Content-Disposition attachment

答案 3 :(得分:0)

我刚刚通过谷歌找到了这个。

我有一个类似的问题,但我仍然想使用Servlet(因为我生成了内容)。

但是,在Servlet中只需要以下行。

response.setHeader("Content-Disposition", "attachment; filename=downloadedData.json");