`

jsp导出excel

    博客分类:
  • jsp
阅读更多

[转]HTTP Response Header 的 Content-Disposition

因为听到有同事讨论JSP输出Excel文件的,就是在页面上有一个【导出】按钮,能够将查询结果导出到Excel文件让用户下载。有人说要用POI在后台生成临时的Excel文件,然后通过读取FileStream写入到OutputStream来解决。其实这个功能不需要这么重型的武器的,虽然很多人讨厌MS,但是不得不承认MS绝对不是乱盖的,IE和Office产品的几近完美的结合就是一个列子。页面里面的Table很容易就可以导出到Excel文件,而且格式都能够完好的保存,所以如果要将查询结果导出到Excel,只需将页面的Context-Type修改一下就可以了:

<%@ page language="java" contentType="application/vnd.ms-excel"%>

然后请求这个页面的时候,就会出现这样的IE窗口:

image

 

看到上面的菜单了么?除了IE的,还有Excel的。而且在点击“文件”->“另存为”的时候,如果选择“Excel工作簿”,那么保存的文件就是真正的转换到Excel文件的存储格式了。

 

不过,有一个问题是,如果我不希望直接在IE里面打开Excel文件,我希望能够提供那个打开/保存的对话框,应该如何做?

模模糊糊记得很久很久以前用过一个参数,于是乎,google一下吧,找到了,就是这个Content-Disposition参数,HTTP Response Header的一个参数。但是这个不是标准参数,查看一下HTTP/1.1的规范文档,对于这个参数的解释大意如下:

Content-Disposition参数本来是为了在客户端另存文件时提供一个建议的文件名,但是考虑到安全的原因,就从规范中去掉了这个参数。但是由于很多浏览器已经能够支持这个参数,所以只是在规范文档中列出,但是要注意这个不是HTTP/1.1的标准参数。

于是,在页面加入一行代码:

<%
response.addHeader("Content-Disposition", "attachment;filename=test.xls");
%>

 

能够看到“文件下载”的对话框了:

image

 

测试了一下,其实IE是根据Content-Disposition中filename这个段中文件名的后缀来识别这个文件类型的,所以,如果有很多种文件类型的时候,可以将Content-Type设置为二进制模式的:

<%@ page language="java" contentType="application/octet-stream"%>

 

附Content-Disposition的解释:

19.5.1 Content-Disposition The Content-Disposition response-header field has been proposed as a means for the origin server to suggest a default filename if the user requests that the content is saved to a file. This usage is derived from the definition of Content-Disposition in RFC 1806 [35].

content-disposition = "Content-Disposition" ":" disposition-type *( ";" disposition-parm ) 
disposition-type = "attachment" | disp-extension-token 
disposition-parm = filename-parm | disp-extension-parm 
filename-parm = "filename" "=" quoted-string 
disp-extension-token = token 
disp-extension-parm = token "=" ( token | quoted-string )

An example is 
    Content-Disposition: attachment; filename="fname.ext"

 

The receiving user agent SHOULD NOT respect any directory path information present in the filename-parm parameter, which is the only parameter believed to apply to HTTP implementations at this time. The filename SHOULD be treated as a terminal component only.

If this header is used in a response with the application/octet- stream content-type, the implied suggestion is that the user agent should not display the response, but directly enter a `save response as...' dialog.

 

Content-Disposition中文乱码

Response.setHeader(”Content-Disposition”, “attachment; filename=” + fileName+”.xls”);
如果file.Name为中文则乱码。解决办法是
方法1:
response.setHeader(”Content-Disposition”, “attachment; filename=” + java.net.URLEncoder.encode(fileName, “UTF-8″));
下载的程序里有了上面一句,一般在IE6的下载提示框上将正确显示文件的名字,无论是简体中文,还是日文。但是文字只要超过17个字,就不能下载了。
一. 通过原来的方式,也就是先用URLEncoder编码,当中文文字超过17个时,IE6 无法下载文件。这是IE的bug,参见微软的知识库文章 KB816868 。原因可能是IE在处理 Response Header 的时候,对header的长度限制在150字节左右。而一个汉字编码成UTF-8是9个字节,那么17个字便是153个字节,所以会报错。而且不跟后缀也不对.

方法2:
response.setHeader( “Content-Disposition”, “attachment;filename=” + new String( fileName.getBytes(”gb2312″), “ISO8859-1″ ) );
在确保附件文件名都是简体中文字的情况下,那么这个办法确实是最有效的,不用让客户逐个的升级IE。如果台湾同胞用,把gb2312改成big5就行。但现在的系统通常都加入了国际化的支持,普遍使用UTF-8。如果文件名中又有简体中文字,又有繁体中文,还有日文。那么乱码便产生了。另外,在上Firefox (v1.0-en)下载也是乱码。

 

本文我们来说一下MIME 协议的一个扩展Content-disposition。

    我们在开发web系统时有时会有以下需求:

  • 希望某类或者某已知MIME 类型的文件(比如:*.gif;*.txt;*.htm)能够在访问时弹出“文件下载”对话框
  • 希望以原始文件名(上传时的文件名,例如:山东省政府1024号文件.doc)提供下载,但服务器上保存的地址却是其他文件名(如:12519810948091234_asdf.doc)
  • 希望某文件直接在浏览器上显示而不是弹出文件下载对话框
  • ……………………

    要解决上述需求就可以使用Content-disposition来解决。第一个需求的解决办法是

Response.AddHeader "content-disposition","attachment; filename=fname.ext" 将上述需求进行归我给出如下例子代码:public static void ToDownload(string serverfilpath,string filename)
{
FileStream fileStream = new FileStream(serverfilpath, FileMode.Open);
long fileSize = fileStream.Length;
HttpContext.Current.Response.ContentType = "application/octet-stream";
HttpContext.Current.Response.AddHeader("Content-Disposition", "attachment; filename=\"" + UTF_FileName(filename) + "\";");
////attachment --- 作为附件下载
////inline --- 在线打开
HttpContext.Current.Response.AddHeader("Content-Length", fileSize.ToString());
byte[] fileBuffer = new byte[fileSize];
fileStream.Read(fileBuffer, 0, (int)fileSize);
HttpContext.Current.Response.BinaryWrite(fileBuffer);
fileStream.Close();
HttpContext.Current.Response.End();
}

public static void ToOpen(string serverfilpath, string filename)
{
FileStream fileStream = new FileStream(serverfilpath, FileMode.Open);
long fileSize = fileStream.Length;
HttpContext.Current.Response.ContentType = "application/octet-stream";
HttpContext.Current.Response.AddHeader("Content-Disposition", "inline; filename=\"" + UTF_FileName(filename) + "\";");
HttpContext.Current.Response.AddHeader("Content-Length", fileSize.ToString());
byte[] fileBuffer = new byte[fileSize];
fileStream.Read(fileBuffer, 0, (int)fileSize);
HttpContext.Current.Response.BinaryWrite(fileBuffer);
fileStream.Close();
HttpContext.Current.Response.End();
}

private static string UTF_FileName(string filename)
{
return HttpUtility.UrlEncode(filename, System.Text.Encoding.UTF8);
}

 

简单的对上述代码做一下解析,ToDownload方法为将一个服务器上的文件(serverfilpath为服务器上的物理地址),以某文件名 (filename)在浏览器上弹出“文件下载”对话框,而ToOpen是将服务器上的某文件以某文件名在浏览器中显示/打开的。注意其中我使用了 UTF_FileName方法,该方法很简单,主要为了解决包含非英文/数字名称的问题,比如说文件名为“衣明志.doc”,使用该方法客户端就不会出现 乱码了。

需要注意以下几个问题:

  1. Content-disposition是MIME协议的扩展,由于多方面的安全性考虑没有被标准化,所以可能某些浏览器不支持,比如说IE4.01
  2. 我们可以使用程序来使用它,也可以在web服务器(比如IIS)上使用它,只需要在http header上做相应的设置即可
分享到:
评论

相关推荐

    jsp导出excel一般问题及汇总

    本篇文章主要探讨了在使用JSP导出Excel时可能会遇到的一般性问题及其解决方案。 一、导出Excel的基本流程 1. 数据准备:首先,你需要从数据库或其他数据源获取要导出的数据,将其组织成二维数组或集合。 2. 创建...

    jsp导出Excel;简单实用!导出Excel;导出Word

    总之,JSP导出Excel和Word是常见的功能需求,通过Apache POI库可以轻松实现。正确设置响应头和使用流处理可以确保文件能被正确下载,同时根据实际需求调整数据处理和样式设置,能够创建符合业务需求的导出文件。

    JSP导出excel和pdf格式

    一、JSP导出Excel 1. **准备库**:在JSP中导出Excel,通常会用到Apache POI库。这是一个用于读写Microsoft Office格式文件的Java库,包括Excel。首先,需要将POI库添加到项目依赖中。 2. **创建Excel工作簿**:...

    java及jsp下导出excel表格

    #### 结合JSP导出Excel 在Web应用中,通常会结合JSP页面来动态生成Excel文件并提供下载。这涉及到设置正确的HTTP响应头,以便浏览器识别文件类型和进行下载。例如,在JSP中可以这样设置: ```jsp *,javax.servlet....

    jsp导出excel并支持分sheet导出的方法.docx

    ### JSP导出Excel并支持分Sheet导出的方法详解 #### 概述 在Web开发领域,特别是使用Java Server Pages (JSP)进行后端处理的应用程序中,经常需要将数据库中的数据导出到Excel文件中供用户下载或进一步处理。这种...

    JSP导出Excel.docx

    标题中的“JSP导出Excel.docx”表明我们要讨论的主题是使用Java服务器页面(JSP)来生成Excel文件。描述部分未提供具体内容,但我们可以基于标题和标签来深入讲解。 在Java开发中,导出Excel文件是常见的需求,通常...

    关于jsp导出excel用javascript实现

    关于jsp导出excel用javascript实现

    jsp页面导出excel

    在JSP页面导出Excel时,我们会用到POI库来创建和操作Excel工作簿、工作表和单元格。首先,确保项目中已经引入了Apache POI的相关依赖。 2. **服务器端代码** 在后端Java代码中,你需要创建一个Servlet或者...

    JSP导出Excel,数字格式化成字符串

    在IT行业中,尤其是在...总结来说,JSP导出Excel并保持数字格式的关键在于创建和应用自定义的单元格样式,避免Excel自动转换为科学计数法。通过Apache POI库,我们可以灵活地控制Excel文件的生成,满足各种格式需求。

    jsp 导出excel

    在IT行业中,JSP(JavaServer Pages)是一种用于创建动态网页的技术,而“jsp 导出excel”这个主题则是关于如何使用JSP来生成并导出数据到Excel文件中的过程。这种功能通常在企业级应用中非常常见,比如报表生成、...

    JSP导出Excel文件的方法

    在JSP中导出Excel文件是一项常见的...总之,JSP导出Excel文件涉及的主要技术点有:JExcelAPI的使用、HTTP响应头的设置、以及样式和数据的组织。通过这些技术,你可以方便地在Web应用中为用户提供Excel文件的下载服务。

    ireport利用jsp导出excel&pdf;报表源代码

    【标题】:“ireport利用jsp导出excel&pdf;报表源代码” 【描述】:“本人验证过的jsp代码,ireport导出pdf excel报表” 在Java Web开发中,生成各种类型的报表是常见的需求,例如用于数据分析、业务统计或者数据...

    JSP 导出Excel表格的实例

    JSP导出Excel表格实例知识分享: JSP(Java Server Pages)是一种基于Java技术用于开发动态网页的服务器端技术,它的主要作用是在HTML网页中嵌入Java代码。使用JSP导出Excel表格,可以让用户将网页中的表格数据转换...

    jsp导入导出excel文件

    **二、导出Excel到JSP** 1. **创建Excel文件**:在服务器端,使用Apache POI创建一个新的工作簿对象,然后添加工作表。根据需要设置标题行和其他格式。 2. **填充数据**:从数据库或其他数据源获取数据,使用POI ...

    jsp程序excel导出功能

    本人试过了可以用,做jsp程序导出excel功能的可以参考下,下载后按照模版进行修改

Global site tag (gtag.js) - Google Analytics