1. 使用 fileupload 组件完成文件的上传应用

commons-dbutils-1.3.jar
commons-fileupload-1.2.1.jar

1). 需求:

> 在 upload.jsp 页面上使用 jQuery 实现 "新增一个附件", "删除附件". 但至少需要保留一个.

> 对文件的扩展名和文件的大小进行验证. 以下的规则是可配置的. 而不是写死在程序中的.

①文件的扩展名必须为 .pptx, docx, doc
   ② 每个文件的大小不能超过 1 M
   ③ 总的文件大小不能超过 5 M.

upload.properties

exts=pptx,docx,doc
file.max.size=1048576
total.file.max.size=5242880

> 若验证失败, 则在 upload.jsp 页面上显示错误消息:

① 若某一个文件不符合要求: xxx 文件扩展名不合法 或 xxx 文件大小超过 1 M
  ② 总的文件大小不能超过 5 M.

> 若验证通过, 则进行文件的上传操作

① 文件上传, 并给一个不能和其他文件重复的名字, 但扩展名不变
   ② 在对应的数据表中添加一条记录.
        id file_name file_path file_desc

FileUploadServlet.java

package com.aff.fileupload.app.servlet;

import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.io.UnsupportedEncodingException;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Random;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.apache.commons.fileupload.FileItem;
import org.apache.commons.fileupload.disk.DiskFileItemFactory;
import org.apache.commons.fileupload.servlet.ServletFileUpload;mport com.aff.fileupload.app.bean.FileUploadBean;
import com.aff.fileupload.app.db.UploadFileDao;
import com.aff.fileupload.app.exception.InvalidExtNameException;
import com.aff.fileupload.app.utils.FileUploadAppProperties;
import com.aff.fileupload.app.utils.FileUtils; @WebServlet("/app/fileuploadservlet")
public class FileUploadServlet extends HttpServlet { private static final long serialVersionUID = 1L; private static final String FILE_PATH = "/WEB-INF/files/"; private static final String TEMP_DIR = "d:\\tempDirectory"; private UploadFileDao dao = new UploadFileDao(); protected void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException { request.setCharacterEncoding("UTF-8"); String path = null; // 获取 ServletFileUpload 对象.
ServletFileUpload upload = getServletFileUpload(); try { // 把需要上传的 FileItem 都放入到该 Map 中
// 键: 文件的待存放的路径, 值: 对应的 FileItem 对象
Map<String, FileItem> uploadFiles = new HashMap<String, FileItem>(); // 解析请求, 得到 FileItem 的集合.
List<FileItem> items = upload.parseRequest(request); // 1. 构建 FileUploadBean 的集合, 同时填充 uploadFiles
List<FileUploadBean> beans = buildFileUploadBeans(items, uploadFiles); // 2. 校验扩展名:
vaidateExtName(beans); // 3. 校验文件的大小: 在解析时, 已经校验了, 我们只需要通过异常得到结果. // 4. 进行文件的上传操作.
upload(uploadFiles); // 5. 把上传的信息保存到数据库中
saveBeans(beans); // 6. 删除临时文件夹的临时文件
FileUtils.delAllFile(TEMP_DIR); path = "/app/success.jsp"; } catch (Exception e) {
e.printStackTrace();
path = "/app/upload.jsp";
request.setAttribute("message", e.getMessage());
} request.getRequestDispatcher(path).forward(request, response);
} private void saveBeans(List<FileUploadBean> beans) {
dao.save(beans);
} /**
* 文件上传前的准备工作. 得到 filePath 和 InputStream
*
* @param uploadFiles
* @throws IOException
*/
private void upload(Map<String, FileItem> uploadFiles) throws IOException {
for (Map.Entry<String, FileItem> uploadFile : uploadFiles.entrySet()) {
String filePath = uploadFile.getKey();
FileItem item = uploadFile.getValue(); upload(filePath, item.getInputStream());
}
} /**
* 文件上传的 IO 方法.
*
* @param filePath
* @param inputStream
* @throws IOException
*/
private void upload(String filePath, InputStream inputStream) throws IOException {
OutputStream out = new FileOutputStream(filePath); byte[] buffer = new byte[1024];
int len = 0; while ((len = inputStream.read(buffer)) != -1) {
out.write(buffer, 0, len);
} inputStream.close();
out.close(); System.out.println(filePath);
} /**
* 校验扩展名是否合法
*
* @param beans:
*/
private void vaidateExtName(List<FileUploadBean> beans) {
String exts = FileUploadAppProperties.getInstance().getProperty("exts");
List<String> extList = Arrays.asList(exts.split(","));
System.out.println(extList); for (FileUploadBean bean : beans) {
String fileName = bean.getFileName();
System.out.println(fileName.indexOf(".")); String extName = fileName.substring(fileName.lastIndexOf(".") + 1);
System.out.println(extName); if (!extList.contains(extName)) {
throw new InvalidExtNameException(fileName + "文件的扩展名不合法");
}
}
} /**
* 利用传入的 FileItem 的集合, 构建 FileUploadBean 的集合, 同时填充 uploadFiles
*
* FileUploadBean 对象封装了: id, fileName, filePath, fileDesc uploadFiles:
* Map<String, FileItem> 类型, 存放文件域类型的 FileItem. 键: 待保存的文件的名字 ,值: FileItem 对象
*
* 构建过程: 1. 对传入 FileItem 的集合进行遍历. 得到 desc 的那个 Map. 键: desc 的
* fieldName(desc1, desc2 ...). 值: desc 的那个输入的文本值
*
* 2. 对传入 FileItem 的集合进行遍历. 得到文件域的那些 FileItem 对象, 构建对应的 key (desc1 ....)
* 来获取其 desc. 构建的 FileUploadBean 对象, 并填充 beans 和 uploadFiles
*
* @param items
* @param uploadFiles
* @return
* @throws UnsupportedEncodingException
*/
private List<FileUploadBean> buildFileUploadBeans(List<FileItem> items, Map<String, FileItem> uploadFiles)
throws UnsupportedEncodingException {
List<FileUploadBean> beans = new ArrayList<>(); Map<String, String> descs = new HashMap<>(); for (int i = 0; i < items.size(); i++) {
FileItem item = items.get(i); if (item.isFormField()) {
// desc1 或 desc2 ...
String fieldName = item.getFieldName();
String desc = item.getString("UTF-8"); descs.put(fieldName, desc);
}
} for (int i = 0; i < items.size(); i++) {
FileItem item = items.get(i);
FileUploadBean bean = null;
if (!item.isFormField()) {
String fieldName = item.getFieldName();
String descName = "desc" + fieldName.substring(fieldName.length() - 1);
String desc = descs.get(descName); // 对应文件名
String fileName = item.getName();
String filePath = getFilePath(fileName); bean = new FileUploadBean(fileName, filePath, desc);
beans.add(bean); uploadFiles.put(bean.getFilePath(), item);
}
} return beans;
} /**
* 根据跟定的文件名构建一个随机的文件名 1. 构建的文件的文件名的扩展名和给定的文件的扩展名一致 2. 利用 ServletContext 的
* getRealPath 方法获取的绝对路径 3. 利用了 Random 和 当前的系统时间构建随机的文件的名字
*
* @param fileName
* @return
*/
private String getFilePath(String fileName) {
String extName = fileName.substring(fileName.lastIndexOf("."));
Random random = new Random(); String filePath = getServletContext().getRealPath(FILE_PATH) + "\\" + System.currentTimeMillis()
+ random.nextInt(100000) + extName;
return filePath;
} /**
* 构建 ServletFileUpload 对象 从配置文件中读取了部分属性, 用户设置约束. 该方法代码来源于文档.
*
* @return
*/
private ServletFileUpload getServletFileUpload() {
String fileMaxSize = FileUploadAppProperties.getInstance().getProperty("file.max.size");
String totalFileMaxSize = FileUploadAppProperties.getInstance().getProperty("total.file.max.size"); DiskFileItemFactory factory = new DiskFileItemFactory(); factory.setSizeThreshold(1024 * 500);
File tempDirectory = new File(TEMP_DIR);
factory.setRepository(tempDirectory); ServletFileUpload upload = new ServletFileUpload(factory); upload.setSizeMax(Integer.parseInt(totalFileMaxSize));
upload.setFileSizeMax(Integer.parseInt(fileMaxSize)); return upload;
}
}

upload.jsp

<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>Insert title here</title>
<script type="text/javascript"
src="${pageContext.request.contextPath }/scripts/jquery-1.12.3.js"></script>
<script type="text/javascript"> $(function(){
var i = 2;
$("#addFile").click(function(){
$(this).parent().parent().before("<tr class='file'><td>File"
+ i + ":</td><td><input type='file' name='file"
+ i + "'/></td></tr>"
+ "<tr class='desc'><td>Desc"
+ i + ":</td><td><input type='text' name='desc"
+ i + "'/><button id='delete"
+ i + "'>删除</button></td></tr>");
i++; //获取新添加的删除按钮
$("#delete" + (i-1)).click(function(){
var $tr = $(this).parent().parent();
$tr.prev("tr").remove();
$tr.remove(); //对 i 重写排序
$(".file").each(function(index){
var n = index + 1; $(this).find("td:first").text("File" + n);
$(this).find("td:last input").attr("name", "file" + n);
}); $(".desc").each(function(index){
var n = index + 1; $(this).find("td:first").text("Desc" + n);
$(this).find("td:last input").attr("name", "desc" + n);
}); i = i - 1;
}); return false;
}); }); </script> </head>
<body> <font color="red">${message }</font>
<br><br> <form action="fileuploadservlet" method="post" enctype="multipart/form-data"> <table>
<tr class="file">
<td>File1:</td>
<td><input type="file" name="file1"/></td>
</tr>
<tr class="desc">
<td>Desc1:</td>
<td><input type="text" name="desc1"/></td>
</tr> <tr>
<td><input type="submit" id="submit" value="提交"/></td>
<td><button id="addFile">新增一个附件</button></td>
</tr>
</table> </form>
</body>
</html>

FileUploadAppListener.java

package com.aff.fileupload.app.listener;

import java.io.IOException;
import java.io.InputStream;
import java.util.Map;
import java.util.Properties; import javax.servlet.ServletContextEvent;
import javax.servlet.ServletContextListener;
import javax.servlet.annotation.WebListener; import com.aff.fileupload.app.utils.FileUploadAppProperties; @WebListener
public class FileUploadAppListener implements ServletContextListener { public FileUploadAppListener() {
} public void contextInitialized(ServletContextEvent sce) {
InputStream is = getClass().getClassLoader().getResourceAsStream("upload.properties");
Properties properties = new Properties(); try {
properties.load(is); for (Map.Entry<Object, Object> prop : properties.entrySet()) {
String propertyName = (String) prop.getKey();
String propertyValue = (String) prop.getValue(); FileUploadAppProperties.getInstance().addProperty(propertyName, propertyValue); }
} catch (IOException e) {
e.printStackTrace();
}
} public void contextDestroyed(ServletContextEvent sce) {
}
}

UploadFileDao.java

package com.aff.fileupload.app.db;

import java.sql.Connection;
import java.util.List; import com.aff.fileupload.app.bean.FileUploadBean; public class UploadFileDao extends DAO<FileUploadBean> { public List<FileUploadBean> getFiles() { Connection conn = null; try {
conn = JDBCUtils.getConnection();
String sql = "SELECT id, file_name fileName, file_path filePath, " + "file_desc fileDesc FROM upload_files";
return getForList(conn, sql);
} catch (Exception e) {
e.printStackTrace();
} finally {
JDBCUtils.release(conn);
}
return null;
} public void save(List<FileUploadBean> uploadFiles) { Connection conn = null; try {
conn = JDBCUtils.getConnection();
String sql = "INSERT INTO upload_files (file_name, file_path, file_desc) VALUES " + "(?, ?, ?)";
for (FileUploadBean file : uploadFiles) {
update(conn, sql, file.getFileName(), file.getFilePath(), file.getFileDesc());
}
} catch (Exception e) {
e.printStackTrace();
} finally {
JDBCUtils.release(conn);
}
}
}

FileUploadBean.java

package com.aff.fileupload.app.bean;

public class FileUploadBean {

    private Integer id;
private String fileName;
private String filePath;
private String fileDesc;
public FileUploadBean() {
super();
}
public FileUploadBean(String fileName, String filePath, String fileDesc) {
super();
this.fileName = fileName;
this.filePath = filePath;
this.fileDesc = fileDesc;
}
public Integer getId() {
return id;
}
public void setId(Integer id) {
this.id = id;
}
public String getFileName() {
return fileName;
}
public void setFileName(String fileName) {
this.fileName = fileName;
}
public String getFilePath() {
return filePath;
}
public void setFilePath(String filePath) {
this.filePath = filePath;
}
public String getFileDesc() {
return fileDesc;
}
public void setFileDesc(String fileDesc) {
this.fileDesc = fileDesc;
}
}

目录

2. 如何修改小工具或框架的源代码 ?

1). 原则: 能不修改就不修改.

2). 修改的方法:

> 修改源代码, 替换 jar 包中对应的 class 文件. 
> 在本地新建相同的包, 和类, 在这个类中修改即可.

3. 文件的下载:

DownloadServlet.java

package com.aff.download.servlet;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.net.URLEncoder;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse; @WebServlet("/downloadServlet")
public class DownloadServlet extends HttpServlet {
private static final long serialVersionUID = 1L; protected void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
//I. 设置 contentType 响应头: 设置响应的类型是什么 ? 通知浏览器是个下载的文件
response.setContentType("application/x-msdownload"); String fileName = "文件下载.pptx";
//II. 设置 Content-Disposition 响应头: 通知浏览器不再有浏览器来自行处理(或打开)要下载的文件,
// 而由用户手工完成
response.setHeader("Content-Disposition", "attachment;filename=" + URLEncoder.encode(fileName, "UTF-8"));

//III. 具体的文件: 可以调用 response.getOutputStream 的方式, 以 IO 流的方式发送给客户端.
OutputStream out = response.getOutputStream();
String pptFileName = "C:\\Users\\lz\\Desktop\\NEW\\PPT\\MAPP.pptx"; InputStream in = new FileInputStream(pptFileName); byte[] buffer = new byte[1024];
int len = 0; while ((len = in.read(buffer)) != -1) {
out.write(buffer, 0, len);
}
in.close();
}
}

download.jsp

<body>
<!-- 静态下载 -->
<a href="xyz.txt">download xyz.txt</a>
<br>
<br>
<a href="test.jsp">download test.jsp</a>
<br>
<br>
<a href="downloadServlet">DownLoad abcd.pptx</a>
</body>

使用 fileupload 组件完成文件的上传应用的更多相关文章

  1. 模拟文件上传(三):使用apache fileupload组件进行文件批量上传

    其中涉及到的jar包 jsp显示层: <%@ page language="java" import="java.util.*" pageEncoding ...

  2. javaweb05 文件的上传一

    2.使用fileupload组件完成文件的上传应用 1).需求: I. 上传 >在upload.jsp页面上使用jQuery实现"新增一个附件","删除附件&quo ...

  3. JavaWeb 之文件的上传下载

    又到了每周更新博客的时候了,每看到自己发布的随笔阅读量上涨的时候就特别开心,我也会尽自己的努力提高自己的水平,总结出通俗易读的学习笔记,还望大家能多多支持!!! ------------------- ...

  4. 初学Java Web(7)——文件的上传和下载

    文件上传 文件上传前的准备 在表单中必须有一个上传的控件 <input type="file" name="testImg"/> 因为 GET 方式 ...

  5. MVC文件上传04-使用客户端jQuery-File-Upload插件和服务端Backload组件实现多文件异步上传

    本篇使用客户端jQuery-File-Upload插件和服务端Badkload组件实现多文件异步上传.MVC文件上传相关兄弟篇: MVC文件上传01-使用jquery异步上传并客户端验证类型和大小  ...

  6. 文件的上传Commons FileUpload(web基础学习笔记十六)

    一.表单设置 <form action="<%=request.getContextPath()%>/jsp/admin/doAdd.jsp" enctype=& ...

  7. vue文件夹上传组件选哪个好?

    一. 功能性需求与非功能性需求 要求操作便利,一次选择多个文件和文件夹进行上传:支持PC端全平台操作系统,Windows,Linux,Mac 支持文件和文件夹的批量下载,断点续传.刷新页面后继续传输. ...

  8. B/S文件夹上传下载组件

    在Web应用系统开发中,文件上传和下载功能是非常常用的功能,今天来讲一下JavaWeb中的文件上传和下载功能的实现. 先说下要求: PC端全平台支持,要求支持Windows,Mac,Linux 支持所 ...

  9. html5文件夹上传下载组件

    我们平时经常做的是上传文件,上传文件夹与上传文件类似,但也有一些不同之处,这次做了上传文件夹就记录下以备后用. 这次项目的需求: 支持大文件的上传和续传,要求续传支持所有浏览器,包括ie6,ie7,i ...

随机推荐

  1. Fiddler 弱网测试

    1.设置上传下载速率 在Fiddler Script选项中查找uploaded,找到设置网络上传和下载设置值 分析一下这几行代码: 首先来判断 m_SimulateModem 是否为 true,也就是 ...

  2. 《Docker从入门到跑路》之基本用法介绍

    Docker是一种轻量级的虚拟化技术,它具备传统虚拟机无法比拟的优势,它更简易的安装和使用方式.更快的速度.服务集成和开源流程自动化. Docker的安装 安装Docker的基本要素:1.Docker ...

  3. 编译原理-第四章 语法分析-4.7 规范的LR分析

    规范的LR分析 一.规范LR(l)项 二.规范LR(l)项集族 1.构建项目集 2.例 三.规范LR(1)语法分析表 1.构造 2.例1 3.例2 四.LALR语法分析表 1.重要性 2.特点 3.构 ...

  4. SpringBoot上传文件大小限制

    SpringBoot默认上传文件大小不能超过1MB,超过之后会报以下异常: org.apache.tomcat.util.http.fileupload.FileUploadBase$FileSize ...

  5. 2020牛客寒假算法基础集训营2 J题可以回顾回顾

    2020牛客寒假算法基础集训营2 A.做游戏 这是个签到题. #include <cstdio> #include <cstdlib> #include <cstring ...

  6. LeetCode--LinkedList--83.Remove Duplicates from Sorted List(Easy)

    题目地址https://leetcode.com/problems/remove-duplicates-from-sorted-list/ 83. Remove Duplicates from Sor ...

  7. 存储过程——公用表表达式(CTE)

    目录 0. 背景说明 1. 定义及语法细节 1.1 基本定义 1.2 基本语法 1.3 多个CTE同时声明 1.4 CTE嵌套使用 2. CTE递归查询 2.1 简介 2.2 准备工作 2.3 计算每 ...

  8. java ->Iterator (迭代)

    Iterator迭代器概述 java中提供了很多个集合,它们在存储元素时,采用的存储方式不同.我们要取出这些集合中的元素,可通过一种通用的获取方式来完成. Collection集合元素的通用获取方式: ...

  9. 学习Echarts:(二)异步加载更新

    这部分比较简单,对图表的异步加载和更新,其实只是异步获取数据然后通过setOption传入数据和配置而已. $.get('data.json').done(function (data) { myCh ...

  10. java触发器的学习

         public class OpenVirtualService {             public void open(){ //虚机开通                //业务逻辑 ...