1 、什么是上传和下载?
–  资料上传是指客户端向站群服务器上传资料,客户端向站群服务器传送的所有请求都属于资料上传。档案上传是资料上传的一种特例,指的是客户端向站群服务器上传档案。即将储存在客户端的档案上传至站群服务器中的一个副本,储存到站群服务器中。
–   资料下载是指客户端从站群服务器上获取资料的过程。档案下载是资料下载的一种特例,指的是客户端从站群服务器下载档案,即将原来储存在站群服务器中的档案下载到客户端中一个副本储存。通常我们对站群服务器所发出的请求,大多数是档案下载请求,从站群服务器中下载文字、图片、声音、视讯等档案,然后由客户端浏览器对这些档案进行解析后,才可能看到这些多媒体资讯。
–  但是我们这里所说的档案下载,指的是档案从站群服务器下载到浏览器后,浏览器并不直接解析,而是以附件的形式储存到客户端中。
–  上传与下载的档案可以是文字档案、图片、声音、视讯等各种型别。

2 、档案上传的实现:
a 、上传时对表单的要求:
–  档案上传要求客户端表单提交特殊的请求–multipart 请求,即包含多部分资料的请求。所以档案上传表单对于表单资料的编码型别要求,必须为 multipart/form-data 。即要为

标签指定 enctype 属性值为 “multipart/form-data” 。(enctype,即 encodingtype,编码型别。)
–  由于客户端上传档案的大小是不确定的,所以 HTTP 协议规定,档案上传的资料要存放于请求正文中,而不能够出现在 url 的位址列中,因为位址列中可以存放的资料量太小。也就是说,档案上传的表单,必须提交 POST 请求,而不能够提交 GET 请求。

b 、使用第三方工具实现档案上传:
–  需要使用到两个 jar 包:commons-fileupload-1.3.3.jar 和 commons-io-2.6.jar,jar 包可以在 apache 官网中下载(commons-fileupload-1.3.3.jar 依赖于 commons-io-2.6.jar,如果只使用 fileupload jar 包,会执行程式时会丢掷异常)
–  示例程式码如下:
–  在 index.jsp 档案中填写的程式码如下所示:

– 为 web 应用新增一个 Servlet,在 web.xml 档案中新增配置资讯:

–  自定义 serlvet 类,在 doPost 方法中编写简单实现档案上传的程式码:

–  启动 web 应用,访问 index.jsp,新增图片后,点选 “上传”,可以发现控制台列印结果,在工作空间 web 专案的指定目录可以看到图片已经上传:(在 Eclipse 中,预设会把 Web 专案放到 Eclipse 的工作空间下的.metadata.pluginsorg.eclipse.wst.server.coretmp0(或者是 tmp1)wtpwebapps 下)

–  FileUploadServlet 类中的程式码相关解释:(也包含使用 fileupload jar 包档案上传时的常用方法)
–  org.apache.commons.fileupload.disk.DiskFileItemFactory 类:预设的 FileItemFactory 实现类。这个实现建立 FileItem 例项(档案条目)。如果是小条目,会将其存入内存中,如果是大条目,会将其存入硬碟中的临时档案。大小条目资料的临界值,是可配置的。

–  setRepository(File repository) 方法:设定临时储存档案(这个档案大小大于指定配置临界值)存放的目录位置。
–  setSizeThreshold(int sizeThreshold) 方法:设定临界值(单位为位元组),当超过这个值时档案将会直接写入硬碟中。(如 sizeThreshold 为 1024 * 1024,则为 1 兆)

–  org.apache.commons.fileupload.servlet.ServletFileUpload 类:处理档案上传的高阶 API 。(如何储存各个部分的资料是由建立它们的工厂决定;给定的部分可能在内存中、磁碟上或者其他地方)

–  parseRequest 方法:解析请求,获取 FileItem 型别元素的 List 物件:

–  ServletFileUpload 类的父类 org.apache.commons.fileupload.FileUploadBase 的方法:
–  设定每个 item 的头部字元编码,其可以解决档名的中文乱码问题:(若 tomcat 版本较低时,可能会出现档名中文乱码)

–  setFileSizeMax(long fileSizeMax) 方法设定单个上传档案允许上传的最大边界值。
–  setSizeMax(long sizeMax) 方法设定一次上传所有档案的总和最大边界值。(单位都为位元组)

–  isMultipartContent(HttpServletRequest request) 方法:判断该请求是否包含 multipart 内容

–  org.apache.commons.fileupload.FileItem 介面:表示在 multipart/form-data 的 POST 请求中内的一个档案或者表单条目。

–  isFormField 方法:判断 FileItem 例项是否为一个普通 form 项:

–  getFieldName 方法:获取对应档案条目(即单个表单项)的 name 属性值:

–  getName 方法:获取客户端档案系统中的原上传档名:(包含字尾名)

–  getInputStream 方法:获取输入流,用于取出上传档案中的内容:

–  delete 方法:删除任何相关联的临时磁碟档案:

3 、档案下载的实现:
a 、超连结下载:将下载资源作为超连结的连结目标档案出现。若浏览器可以解析该资原始档,则将在浏览器上直接显示档案内容;若浏览器不支援该档案的解析,则会弹出另存为对话方块,要求使用者储存。
–  该下载方式的缺点很明显,不同的浏览器,以及相同的浏览器所安装的插件外挂不同,那么其对于资源的解析能力也就不同,其是否弹出另存为对话方块的情况也就不一样。决定权由浏览器掌握。
–  如在 jsp 档案中新增如下程式码,在 ff 浏览器中点选,直接在浏览器中开启该图片:

b 、 Servlet 方式的档案下载:
–  示例程式码:
–  jsp 档案中的内容和 web.xml 档案中新增的配置:

–  自定义 Servlet 类中新增如下程式码:

–  如果想要浏览器下载的方式是以附件的形式下载,需要修改响应的头部属性 content-disposition 值为 attachment;filename=档名 + 字尾名。(filename 表示以附件形式下载显示的档名)

javax.servlet.ServletContext 介面的 getResourceAsStream 方法:获取 web 应用中的指定路径下的资源,以位元组输入流 InputStream 的形式返回。

–  启动 web 应用,点选超连结后,可以看到档案以附件的形式下载:

4 、附加说明:
–  上传档案目录的管理:当使用者上传的档案过多,而单个目录能够存放的档案个数有限,(windows 系统下单资料夹中最大可有 65,534 个档案)所以需要上传的档案有时需要分目录进行管理。
–   可以使用 java.io.File 类的 mkdir() 方法来在当前目录中建立直接子目录,或者使用 mkdirs() 方法建立当前目录的多层子目录: