封装了 Jakarta 文件上传功能的一个类
后记: 记得改了一个支持 encoding 设置的版本, 竟然找不到了.. 回家再看看, 自己的东西也没做版本管理, 挺混乱.... 回头把此文件加入 BeanSoftLib 中去.
近期项目要用到文件上传功能, 先试了用 Jsp Smart upload, 结果发现一个问题: 如果上传的文件名中有汉字, 则发生无法读取参数和文件数据的错误. 后来想到 Struts 的文件上传功能在 Tomcat 和 Weblogic 下都没有问题, 就想到用它来做上传功能, 于是到 Apache 网站下载了 Commons FileUpload 看了看, 发现虽然功能都用, 但是使用太不方便, 例如获取表单参数竟然要一个一个的遍历, 于是就动手写了一个封装类, 这个类可以方便的读取表单参数和文件项目.
首先说一下参考资料:
FileUpload主站点:
http://jakarta.apache.org/commons/fileupload/index.html
下载FileUpload的源码:
http://archive.apache.org/dist/jakarta/commons/fileupload/source/
点击commons-fileupload-1.0-src.zip下载源码.
下载FileUpload的二进制包(JAR文件):
http://archive.apache.org/dist/jakarta/commons/fileupload/binaries/
在列表中点击commons-fileupload-1.0.zip26-Jun-200308:32128K,
下载后解压缩得到的commons-fileupload-1.0.jar就可以放到类路径中使用了.
Apache自己的使用指导(英文版),强烈建议如果要深入了解如何使用的人看看这个网页:
http://jakarta.apache.org/commons/fileupload/using.html下面就是这个类的源码了(已经在源码注释中包含了使用说明了):
package studio.beansoft.jsp;
import java.util.*;import java.io.*;
import javax.servlet.http.*;
import org.apache.commons.fileupload.*;
/**
*JakartacommonsFileUpload封装类.
*提供:参数读取(在Tomcat4,5下测试过似乎没有中文问题),文件保存功能.
*
*NOTE:所有的表单和页面编码都是按照UTF-8来处理的.
*TODORefactortomakeencodingconfigable.
*
*示例代码(在JSP页面中,忽略了异常处理代码):
*test.htm
<formaction="test.jsp">
Inputname:<inputtype="text"name="username"><br>
Selectafile:<inputtype="file"name="file1"><br>
<inputtype="submit"value="Upload">
</form>test.jsp
<%@pagecontentType="text/html;charset=utf8"%>
<%@pageimport="studio.beansoft.jsp.*,java.io.*"%>
<%
JakartaFileUploadHandleruploadHandler=newJakartaFileUploadHandler(request);
//如果是文件上传表单
if(uploadHandler.isMultipart()){
//读取参数
StringparameterValue=uploadHandler.getParameter("username");
out.println("username="+parameterValue);
//保存文件
JakartaFileUploadHandler.saveFileItem(uploadHandler.getFileItem("file1"),newFile("file1.txt"));
}
%>更多参考资料请看 Apache 的网站上的指导文章:
UsingFileUpload
@linkhttp://jakarta.apache.org/commons/fileupload/using.html
*
*@see#getParameter(String)
*@see#getParameterValues(String)
*@see#saveFileItem(FileItem,File)
*
*这个类依赖于Jakartacommons-fileupload-1.0.zip.
*
*@version1.01
*2005-11-30
*/
publicclassJakartaFileUploadHandler
{
/**文件域列表*/
privateMapfileFields=newTreeMap();
/**表单域列表*/
privateMapformFields=newTreeMap();
/**Checkthatwehaveafileuploadrequest*/
privatebooleanisMultipart=false;
private HttpServletRequest request = null;/**
*空构造器.
*/
public JakartaFileUploadHandler() {}
/**
*根据现有参数构造一个上传处理器.
*/
publicJakartaFileUploadHandler(HttpServletRequestrequest){
setRequest(request);
}/**
*设置HttpServletRequest并分析里面的表单数据.
*@paramrequest-HttpServletRequest
*/
publicvoidsetRequest(HttpServletRequestrequest){
this.request = request;isMultipart = FileUpload.isMultipartContent(request);
// 如果是文件上传请求, 就提取里面的参数
if(isMultipart){
//Createanewfileuploadhandler
DiskFileUpload upload = new DiskFileUpload();/*
*Nov292005,setdefaultuploadencodingtoUTF-8.
*Specifiesthecharacterencodingtobeusedwhenreadingtheheadersof
*individualparts.Whennotspecified,or<code>null</code>,theplatform
*defaultencodingisused.
*/
upload.setHeaderEncoding("UTF-8");try {
//Parsetherequest
List /* FileItem */ items = upload.parseRequest(request);// Process the uploaded items
Iteratoriter=items.iterator();
while(iter.hasNext()){
FileItem item = (FileItem) iter.next();String name = item.getFieldName();String value = item.getString();
if (item.isFormField()) {
processFormField(item);
}else{
processUploadedFile(item);
}
}
}catch(Exceptionex){
System.err.println("无法处理上传数据:"+ex);
}}}
/**
*处理表单项目.
*@paramitem-FileItem对象
*/
privatevoidprocessFormField(FileItemitem){
Stringname=item.getFieldName();
//NOTE文件上传统一使用UTF-8编码2005-10-16
String value = null;try {
value=item.getString("UTF-8");
}catch(UnsupportedEncodingExceptione){
}// 首先尝试获取原来的值Object oldValue = formFields.get(name);
if(oldValue == null) {
formFields.put(name,value);
}else{
// 多个值存储为 List// 原来为单个值则添加现有的值
try{
String oldString = (String)oldValue;List list = new ArrayList();
list.add(oldString);
list.add(value);formFields.put(name, list);
}catch(Exceptionex){
//ex.printStackTrace();
}// 原来为多个值则添加现有的值
try{
Listlist=(List)oldValue;
list.add(value);
formFields.put(name,list);
}catch(Exceptionex){
//ex.printStackTrace();
}
}
}/**
*处理文件项目.
*@paramitem-FileItem对象
*/
privatevoidprocessUploadedFile(FileItemitem){
Stringname=item.getFieldName();
fileFields.put(name,item);
}/**
*获取上传的文件项目.
*@paramname-String,文件域名称
*@returnFileItem-org.apache.commons.fileupload.FileItem对象
*/
publicFileItemgetFileItem(Stringname){
if(!isMultipart) return null;return (FileItem) (fileFields.get(name));}
/**
*获取表单参数.
*@paramname-String,表单域名称
*@returnString-表单域值
*/
publicStringgetParameter(Stringname){
if(!isMultipart){
returnrequest.getParameter(name);
}Object value = formFields.get(name);
if(value!=null){
if(valueinstanceofString){
return(String)value;
}
}
returnnull;
}/**
*获取表单域的多个参数值.
*@paramname-String,表单域名称
*@returnString[]-表单域的多个取值
*/
publicString[]getParameterValues(Stringname){
if(!isMultipart){
returnrequest.getParameterValues(name);
}Object value = formFields.get(name);
if(value!=null){
if(valueinstanceofList){
return(String[])((List)value).toArray(newString[0]);
}
}
returnnull;
}/**
*返回当前请求是否为多部分上传请求.
*/
publicbooleanisMultipart()
{
returnisMultipart;
}/**
*保存FileItem对象到指定的文件.
*@paramitem-FileItem,要保存的上传文件项目
*@paramfile-File,要保存到的文件对象
*@returnboolean-是否保存成功
*/
publicstaticbooleansaveFileItem(FileItemitem,Filefile){
try{
item.write(file);
returntrue;
}catch(Exceptionex){
//ex.printStackTrace();
System.out.println("saveFileItemerror:"+ex);
}
returnfalse;
}/**
*获取FileItem对象的输入流.
*@paramitem-FileItem,要获取输入流的上传文件对象
*@returnInputStream-对象的输入流
*/
publicstaticInputStreamgetInputStreamFromFileItem(FileItemitem){
try{
returnitem.getInputStream();
}catch(Exceptionex){
//ex.printStackTrace();
}
returnnull;
}
}