处理下载文件名乱码问题,包括某些情况下chrome出现的乱码。
一、引入jar包
1. commons-fileupload-1.2.1.jar
2. commons-io-1.4.jar
二、文件上传
- html代码 - 1 
 2
 3
 4
 5- <form name="upload_test" action="${pageContext.request.contextPath}/FileServlet?method=upload" method="post" enctype="multipart/form-data"> 
 用户名: <input type="text" name="userName" > <br>
 文件: <input type="file" name="fileName" > <br>
 <input type="submit" value="上传" >
 </form>
- java代码 - 1 
 2
 3
 4
 5
 6
 7
 8
 9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31
 32
 33
 34
 35
 36
 37
 38
 39
 40
 41
 42
 43
 44
 45
 46
 47
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64- private void upload(HttpServletRequest request, HttpServletResponse response) 
 throws ServletException, IOException {
 String uri = null;
 try {
 //文件上传工厂
 FileItemFactory factory = new DiskFileItemFactory();
 //文件上传核心工具类
 ServletFileUpload upload = new ServletFileUpload(factory);
 /******设置大小限制参数******/
 // 单个文件大小限制
 upload.setFileSizeMax(10*1024*1024);
 // 总文件大小限制
 upload.setSizeMax(50*1024*1024);
 // 对中文文件编码处理
 upload.setHeaderEncoding("UTF-8");
 //判断: 当前表单是否为文件上传表单
 if(upload.isMultipartContent(request)){
 //把请求数据转换为一个FileItem对象,再用集合封装
 List<FileItem> list = upload.parseRequest(request);
 // 遍历: 得到每一个上传的数据
 for (FileItem item : list) {
 // 判断类型(true:普通表单 || false:上传表单)
 if(item.isFormField()){
 //获取名称
 String name = item.getFieldName();
 //获取值
 String value = item.getString();
 //打印内容
 System.out.println("name: " + name + "\tvalue: " + value);
 } else {
 /*****上传表单*****/
 //获取文件名称
 String name = item.getName();
 // ----处理上传文件名重名问题----
 //获取一个36位的uuid字符串
 String id = UUID.randomUUID().toString();
 //拼接文件名
 name = id + "#" + name;
 //得到上传目录
 String basePath = getServletContext().getRealPath("upload");
 System.out.println("basePath: " + basePath);
 //创建要上传的文件对象
 File file = new File(basePath, name);
 //上传
 item.write(file);
 // 删除组件运行时产生的临时文件
 item.delete();
 }
 }
 } else {
 System.out.println("不是上传表单");
 }
 
 uri = "/success.jsp";
 } catch (FileUploadException e) {
 e.printStackTrace();
 uri = "/error/error.jsp";
 } catch (Exception e) {
 e.printStackTrace();
 uri = "/error/error.jsp";
 } finally {
 request.getRequestDispatcher(uri).forward(request, response);
 }
 }
三、文件列表
- html代码 - 1 
 2
 3
 4
 5
 6
 7
 8
 9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31- <table border="1" width="80%" align="center" cellpadding="5" cellspacing="0"> 
 <tr>
 <th>序号</th>
 <th>文件名</th>
 <th>操作</th>
 </tr>
 <c:choose>
 <c:when test="${not empty requestScope.fileMap}">
 <c:forEach items="${requestScope.fileMap }" var="en" varStatus="vs">
 <tr>
 <td>${vs.count }</td>
 <td>${en.value }</td>
 <td>
 <!-- 构建一个地址 -->
 <c:url var="url" value="FileServlet">
 <c:param name="method" value="down"></c:param>
 <c:param name="fileName" value="${en.key }"></c:param>
 </c:url>
 <!-- 使用上面地址 -->
 <a href="${url }">下载</a>
 </td>
 </tr>
 </c:forEach>
 </c:when>
 <c:otherwise>
 <tr>
 <td align="center" colspan="3">对不起,没有你要找的数据</td>
 </tr>
 </c:otherwise>
 </c:choose>
 </table>
- java代码 - 1 
 2
 3
 4
 5
 6
 7
 8
 9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29- private void downList(HttpServletRequest request, HttpServletResponse response) 
 throws ServletException, IOException {
 // 实现思路:先获取upload目录下所有文件的文件名,再保存;跳转到down.jsp列表展示
 
 //初始化map集合Map<包含唯一标记的文件名, 简短文件名>
 Map<String, String> fileMap = new HashMap<String, String>();
 //获取上传目录
 String basePath = getServletContext().getRealPath("/upload");
 System.out.println(basePath);
 //目录
 File file = new File(basePath);
 //遍历目录获取文件名
 String[] list = file.list();
 //遍历,封装
 if (list != null && list.length > 0) {
 for (String name : list) {
 System.out.println(name);
 String shortName = name.substring(name.lastIndexOf("#")+1);
 System.out.println("shortName: " + shortName);
 fileMap.put(name, shortName);
 }
 }
 
 //保存到request域
 request.setAttribute("fileMap", fileMap);
 //转发
 request.getRequestDispatcher("/downlist.jsp").forward(request, response);
 }
三、文件下载
- java代码 - 1 
 2
 3
 4
 5
 6
 7
 8
 9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31
 32
 33
 34- private void down(HttpServletRequest request, HttpServletResponse response) 
 throws ServletException, IOException {
 // 获取用户下载的文件名称(url地址后追加数据,get)
 String fileName = request.getParameter("fileName");
 System.out.println("未编码:" + fileName);
 
 //获取文件目录路径
 String basePath = getServletContext().getRealPath("/upload");
 //获取文件流
 InputStream is = new FileInputStream(new File(basePath, fileName));
 
 //截取字符串
 String shortName = fileName.substring(fileName.lastIndexOf("#")+1);
 System.out.println("截取后未编码:" + shortName);
 shortName = new String(shortName.getBytes(),"ISO8859-1");
 System.out.println("截取后编码:" + shortName);
 
 //设置浏览器编码
 response.setCharacterEncoding("UTF-8");
 // 设置下载的响应头
 response.addHeader("content-disposition", "attachment;fileName="+shortName);
 // 获取response字节流
 OutputStream os = response.getOutputStream();
 byte[] by = new byte[1024];
 int len = -1;
 while ((len = is.read(by)) != -1) {
 os.write(by, 0, len);
 }
 
 //关闭
 os.close();
 is.close();
 
 }