0

我在 Spring 3 框架 webapp 中实现了一个下载控制器,它应该被调用以在调用时启动一个打开/保存对话框。

它确实启动了打开/保存对话框并且保存工作正常。但是,当我单击“打开”时,它会在我的文件名后附加一个“.htm”并打开它全部错误。为什么?

控制器:

@RequestMapping("download/downloadFile")
    @ResponseBody
    public byte[] downloadFile(@RequestParam String fileID, HttpServletResponse response) {

        response.setContentType("application/octet-stream");
        File file = getFileByID(fileID);                       

        byte[] bytes = FileCopyUtils.copyToByteArray(file);

        response.setHeader("Content-Disposition", "attachment; filename=\"" + file.getName() + "\"");     
        response.setContentLength(bytes.length);

        return bytes;
    }

当我看到响应标头时,我看到内容类型是 text/html,就像它忽略了我将其设置为 application/octet-stream!

Cache-Control   no-cache, no-store
Connection  close
Content-Disposition attachment; filename="test.txt"
Content-Length  22071
Content-Type    text/html
Date    Tue, 05 Feb 2013 21:12:20 GMT
Expires Thu, 01 Jan 1970 00:00:00 GMT
Pragma  no-cache
Server  Apache/2.2.10 (Linux/SUSE)
X-Powered-By    Servlet/2.5 JSP/2.1
X-UA-Compatible IE=8, chrome=1

可能是因为我在 web.xml 中设置 Spring MVC 的方式?

<servlet-mapping>
    <servlet-name>springmvc</servlet-name>
    <url-pattern>*.html</url-pattern>
</servlet-mapping>

一切都映射到以“.html”结尾的 URL 并且浏览器正在查看它?

4

1 回答 1

0

您正在混合两种产生响应的方式。直接写入响应,并要求Spring将方法的返回值写入响应体。您应该坚持一个,因为您目前拥有它,框架正在覆盖响应内容类型。produces通常,您可以将响应的内容类型作为@RequestMapping注释的属性提及。但是,由于在这种情况下您还想编写内容处置标头,因此我建议使用自定义视图,而不是@ResponseBody注释。

在您的自定义视图类中,设置所需的标头,然后自己将字节流式传输到响应输出流。

希望这可以帮助。

于 2013-04-19T12:48:34.760 回答