文件上传该注意的基本问题:
(1)必须使用POST表单;
(2)表单的enctype必须是multipart/form-data;
(3)需要在表单中添加file表单字段,即<input type=”file”…/>;
(4)request.getParameter(String)方法失效,因为request.getParameter(String)方法获取指定的表单字段字符内容,但文件上传表单已经不在是字符内容,而是字节内容;
(5)可以使用request的getInputStream()方法获取ServletInputStream对象,它是InputStream的子类,这个ServletInputStream对象对应整个表单的正文部分(从第一个分隔线开始,到最后),这说明我们需要的解析流中的数据。当然解析它是很麻烦的一件事情。
(6)确定我们需要使用fileupload来对request.getInputStream()的内容进行解析!commons-fileupload是由apache的commons组件提供的上传组件,它最主要的工作就是帮我们解析request.getInputStream()。
fileupload组件需要的JAR包有:
------commons-fileupload.jar,核心包;
------commons-io.jar,依赖包。
fileupload的核心类有:DiskFileItemFactory,ServletFileUpload,FileItem。
————————————————————————————————————————————————
————————————————————————————————————————————————
文件上传该注意的细节问题:
(7)把上传的文件放到WEB-INF目录下;如果没有把用户上传的文件存放到WEB-INF目录下,那么用户就可以通过浏览器直接访问上传的文件,这是非常危险的。
(8)上传文件名称可能是完整路径;使用不同浏览器测试,其中IE6就会返回上传文件的完整路径,就是需要处理这一问题。处理这一问题也很简单,无论是否为完整路径,我们都去截取最后一个“\”后面的内容就可以了。
(9)中文乱码问题;
上传文件名称中包含中文:
当上传的谁的名称中包含中文时,需要设置编码,commons-fileupload组件为我们提供了两种设置编码的方式:
------request.setCharacterEncoding(String):这种方式是我们最为熟悉的方式了;
------fileUpload.setHeaderEncdoing(String):这种方式的优先级高与前一种。
上传文件的文件内容包含中文:
通常我们不需关心上传文件的内容,因为我们会把上传文件保存到硬盘上!也就是说,文件原来是什么样子,到服务器这边还是什么样子!
但是如果你有这样的需求,非要在控制台显示上传的文件内容,那么你可以使用fileItem.getString(“utf-8”)来处理编码。
(10)上传文件同名问题;使用uuid来解决,在每个文件前加uuid;
(11)一个目录不能存放过多的文件;
(12)限制单个上传文件的大小;使用ServletFileUpload类的setFileSizeMax(long)就可以了。参数就是上传文件的上限字节数,例如servletFileUpload.setFileSizeMax(1024*10)表示上限为10KB。
(13)上传文件的总大小限制;使用ServletFileUpload类的setSizeMax(long)方法即可;
(14)设置缓存大小与临时目录;
DiskFileItemFactory dfif = new DiskFileItemFactory(1024*20, new File("F:\temp"));
ServletFileUpload fileUpload = new ServletFileUpload(dfif);
fileupload会判断文件大小是否超出20KB,如果是那么就把文件保存到临时目录temp上,如果没有超出,那么就保存在内存中。
————————————————————————————————————————————————
————————————————————————————————————————————————
文件上传实例:
相关jar包:
jsp页面:
上传代码:
public String add() throws UnsupportedEncodingException { HttpServletRequest request = ServletActionContext.getRequest(); HttpServletResponse response = ServletActionContext.getResponse(); //request.setCharacterEncoding("utf-8"); DiskFileItemFactory factory = new DiskFileItemFactory(); ServletFileUpload sfu = new ServletFileUpload(factory); sfu.setFileSizeMax(2048 * 2048); try { List<FileItem> fileItemList = sfu.parseRequest(request); Map<String, String> map = new HashMap<String, String>(); for (FileItem fileItem : fileItemList) { if (fileItem.isFormField()) { map.put(fileItem.getFieldName(), fileItem.getString("UTF-8")); } } post = CommonUtils.toBean(map, Post.class); post.setPid(CommonUtils.uuid()); User user = (User) request.getSession().getAttribute("sessionUser"); post.setUser(user); post.setPtime(new Date()); // 得到保存的目录 String savepath = ServletActionContext.getServletContext() .getRealPath("/post_img"); // 得到文件名称:给原来文件名称添加uuid前缀!避免文件名冲突 String filename = CommonUtils.uuid() + "_" + fileItemList.get(3).getName(); /* * 校验文件的扩展名 */ if (!filename.toLowerCase().endsWith("jpg")) { request.setAttribute("msg", "您上传的图片不是JPG扩展名!"); return "posting"; } // 使用目录和文件名称创建目标文件 File destFile = new File(savepath, filename); // 保存上传文件到目标文件位置 fileItemList.get(3).write(destFile); post.setPimg("post_img/" + filename); postService.add(post); } catch (Exception e) { if (e instanceof FileUploadBase.FileSizeLimitExceededException) { request.setAttribute("msg", "您上传的文件超出了1024KB"); return "posting"; } } return findByStatus(); }