(1)普通的实现方式:
①有ServletFileUpload获得是否是Multipart形式提交,如果是,执行②
②创建一个ServletFileUpload对象upload。
③由上面的upload创建一个FileItemIterator对象
④获取iterator值,获取FileItemStram对象fis,并通过这个对象通过openStream()方法获得InputStrame对象
⑤使用fis判断是否是表单,如果是表单的话就直接获取表单中的参数和值就可以了,这里通过Streams.asString(is)来获得表单的值。如果不是表单说明是文件上传,可以通过FileOutputStream来进行byte写入。
public voiddoPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException,IOException {
file02(request,response);
request.setCharacterEncoding("utf-8");
boolean isMultipart =ServletFileUpload.isMultipartContent(request);
InputStream is = null;
FileOutputStream fos = null;
try {
if (isMultipart) {
ServletFileUpload upload = newServletFileUpload();
FileItemIterator iter =upload.getItemIterator(request);
while (iter.hasNext()) {
FileItemStream fis =iter.next();
//是multipart就表示需要使用字节数据进行传递,需要使用输入流
is = fis.openStream();
if (fis.isFormField()) {
System.out.println(fis.getFieldName());
System.out.println(newString(Streams.asString(is).getBytes("ISO-8859-1"),"gbk"));//通过该方法可以将流中的数据转换为String
} else {
System.out.println(fis.getName());
String path =request.getSession().getServletContext().getRealPath("/upload");
path= path + "/" + fis.getName();
fos = newFileOutputStream(path);
byte[] buf = newbyte[2014];
int len = 0;
while((len=is.read(buf))>0){
fos.write(buf,0,len);
}
}
}
}
} catch (Exception e) {
} finally {
if(is!=null) is.close();
if(fos!=null) fos.close();
}
}
(2)使用自己创建的一个新类来创建一个封装,然后servlet直接简单调用就好了,这个类需要继承HttpServletRequestWrapper。将表单提交上来的数据如果是以Multipart形式提交的,首先创建MultipartRequestWrapper对象,然后将提交上来的数据封装在Map中,servlet直接调用这里面的相应的getParameter方法即可获得,以前通过req.getParameter()方法获得的值,从而达到统一。另外,这里文件上传是通过Streams.copy(is, new FileOutputStream(PATH + "/upload/" + fis.getName()), true);这个方法来获得的,不是上面的byte形式,比较简单。
注意:在IE中,传过来的fis.getName就是c:/……这种全路径,那么可以使用
//对于IE上传的文件会得到完整的绝对路径,需要将绝对路径字符串进行截取文件名
String fname = FilenameUtils.getName(fis.getName());//得到文件名
这个方法可以实现兼容,就可以直接获得文件名,而不用管IE还是火狐
public class MultipartRequestWrapper extends HttpServletRequestWrapper{
private Map
private static final String PATH = "D:\\MyEclipse-8.6\\Workspaces\\MyEclipse8.6\\FileUploadTest01\\WebRoot\\";
public MultipartRequestWrapper(HttpServletRequest request) {
super(request);
setParams(request);
}
private void setParams(HttpServletRequest request) {
try {
request.setCharacterEncoding("UTF-8");
} catch (UnsupportedEncodingException e1) {
// TODO Auto-generatedcatch block
e1.printStackTrace();
}
//判断是否是multipart类型
boolean isMul = ServletFileUpload.isMultipartContent(request);
if(isMul) {
ServletFileUpload upload = new ServletFileUpload();
try {
FileItemIterator iter =upload.getItemIterator(request);
InputStream is = null;
while (iter.hasNext()) {
FileItemStream fis = iter.next();
is = fis.openStream();
if (fis.isFormField()) {
setFormParams(fis.getFieldName(),is);//主要是针对类似于checkbox这种多name的
} else {
//要输入流中有数据(>0)才进上传,否则不进行
if(is.available()>0) {
//对于IE上传的文件会得到完整的绝对路径,需要将绝对路径字符串进行截取文件名
String fname = FilenameUtils.getName(fis.getName());//得到文件名
//完成文件上传
System.out.println(PATH+"upload\\"+ fname);
Streams.copy(is, new FileOutputStream(PATH + "/upload/"
+ fname), true);
params.put(fis.getFieldName(), new String[] { fis
.getName() });
}
}
}
} catch (Exception e) {
// TODO: handleexception
}
} else {
//如果不是Multipart直接通过请求获取值
params = request.getParameterMap();
}
}
private void setFormParams(String paramKey,InputStream is) throws IOException {
if(params.containsKey(paramKey)) {
//说明表单域中已经存在了值,需要向params的String的数组中添加
String[] values = params.get(paramKey);
values = Arrays.copyOf(values, values.length+1);//数组长度加1
values[values.length-1] = Streams.asString(is);
params.put(paramKey, values);
} else {
params.put(paramKey, new String[]{Streams.asString(is)});
}
}
public Map
return params;
}
public String getParameter(String name) {
String[] values = params.get(name);
if(values!=null) {
return values[0];
}
return null;
}
@Override
public String[] getParameterValues(String name) {
String[] values = params.get(name);
if(values!=null) {
return values;
}
return null;
}
}