javaweb-文件的上传下载
本文用到的jar包:
文件上传:commons-fileupload-1.2.1.jar;
commons-io-1.4.jar;
本文需要掌握的知识:html+dom
1 文件的上传概述;
1.1 用户把本地的文件储存到服务器上,就是文件的上传;
1.2 实现文件的上传(目前而言要使用第三方jar包);
1.2.1 jspSmartupload;
适用范围:应用在jsp的模型一里(嵌入执行上传下载操作的JSP文件中) ;
1.2.2 fileUpload;
来源:Apache commons下面的开源,免费项目(谢谢老板);
适用范围:(mvc模式);
1.3 要使用文件的上传,需要满足三个要求:
①表单数据提交,提交方式为post提交;
②在表单里有一个文件的上传想<input type=”file” name=”filename”/>
③在form里面,要设置一个属性值,enctype,设置为multipart/form-data(必须设置,不然只有一个文件名之类的)
2 文件上传的原理分析:
从请求响应信息可知;
Content-Type:multipart/form-data;
通过请求正文可以得到结论:
①找到分割线;
②根据分割线区别不同的项;
③普通输入项得到的是值;
④文件上传项,得到文件的内容,把内容写到服务器里面一个文件中;
⑤使用输入流得到文件上传的内容,使用输出流把文件的内容写到服务器上;
3,文件上传的代码实现的步骤(固定步骤,照着写就可以了);
3.1 :创建磁盘文件工厂;
new DiskFileItemFactory();
3.2:创建核心上传类;
new ServletFileUpload(FileItemFactory fileItemFactory);
3.3:使用核心上传类解析request对象;
parseRequest(-----request(全类名就不写了));
返回的是一个List集合,集合中有多个FileItem,泛型为<FileItem>;
3.4:遍历list集合,得到每个FileItem;
3.5:判断是普通输入项还是文件上传项;
Boolean isFormField();
3.6:如果是普通输入项;如果是文件上传项编写文件上传的代码;
普通输入项:
getField():得到普通输入项name的值;
getString():得到普通输入项里面输入的值;
文件上传项:
得到通过表单提交的文件的输入流,getInputStream;
创建输出流,写出文件到服务器的相应的位置(输出位置要带有盘符,通过
getServletContext().getRealPath(相对路径)可以获取.为什么要这样做,是因为项目在别的服务器上真实路径就不一定一致了,所以要通过相对路径获取到真实路径);
4,核心API的学习(主要是一些重要的方法);
4.1 DiskFileItemFactory(磁盘文件项工厂)(核心上传类,重点在于构造);
构造方法;
DiskFileItemFactory(int sizeThreshold,java.io.File repository);
两个参数:
第一个参数设置上传文件缓冲区的大小;
第二个参数.如果上传文件超出了缓冲区,产生临时文件,设置临时文件路径
(可以看做是先用一个等大小的临时文件做占位,然后数据一步步填充);
DiskFileItemFactory() 无参构造,也可以设置缓冲区;
setSizeThreadshold(int sizeThreadshold):设置上传文件的缓冲区(单位是字节byte);
setRepository(java.io.File repository):设置临时文件路径;
4.2 ServletFileUpload:核心上传类;
构造方法;
ServletFileUpload(FileItemFactory fileItemFactory);
重要方法:;
parseRequest(javax.servlet.HttpServletRequest request):解析request对象;
返回一个list<FileItem>集合,每一个元素都是一个FileItem;
在他的父类中还有一个很重要的方法;
setHeaderEncoding(java.lang.String encoding);设置上传文件名称的编码;
setFileSizeMax(long filesizeMax)”:设置单个文件的大小;
setSIzeMax(long sizeMax): 设置单个文件的总大小;
4.3 FileItem:文件项
Boolea isFormField():判断是否是普通输入项;
getFieldName():得到普通输入项.name的属性值;
getString():得到普通输入项的文本值;
getString(encoding):设置输入项中文本的编码;
getName():得到上传文件的名称(但是有些浏览器得到的带路径的名称,所以要进行截取操作,哭);
getInputStream():得到表单提交的文件输入流;
Delete():删除临时文件(要在关闭流之后删除);
5 JS控制多文件的上传
5.1 需求:在上传的表单里面有两个按钮,一个是上传文件的按钮,一个是增加的按钮,增加上传项.
点击增加按钮之后,增加一行,一个上传输入项和一个删除的按钮
点击删除按钮之后,删除该行
点击上传按钮之后,把当前的文件上传到服务器里面去
5.2 使用js增加一行和删除一行
<script type="text/javascript">
//增加一行
function addFile(){
//在table里面增加一行
var table = document.getElementsByTagName("table")[0];
table.innerHTML+="<tr><td><input type='file' name='filename'/></td><td><input type='button' value='删除' οnclick='dele(this)'/><td/><tr/> ";
}
//删除一行
function dele(who){
//获取当前点击的删除按钮所在的tr
var tr=who.parentNode.parentNode;
//拿到爸爸
var table=tr.parentNode;
//通过爸爸删除儿子
table.removeChild(tr);
}
</script>
5.3 使用button提交表单的方法
//通过按钮提交表单实现上传
function uploadFile(){
var form =document.getElementsByTagName("form")[0];
form.submit();
}
5.4 常见问题的解决:
5.4.1 当已经存在名字重复的文件,再次上传会新文件覆盖原文件
解决方式:在上传的文件名称里添加一个随机的唯一的字符串,保证每个文件都是唯一的值(可以通过uuid生成,也可以使用毫秒数,不过推荐用uuid更加保险
//生成一个随机的唯一的id值
String id = UUID.randomUUID().toString();
JSP页面(为什么我没找到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> </head> <body><form action="${pageContext.request.contextPath }/servlet/Upload2" method="post" enctype="multipart/form-data"><input type="button" value="上传" οnclick="uploadFile()"/><input type="button" value="增加" οnclick="addFile()"/><hr/><table></table><%--<input type="file" name="filename"/><input type="button" value="删除"/> --%></form> </body> <script type="text/javascript">//通过按钮提交表单实现上传 function uploadFile(){var form =document.getElementsByTagName("form")[0];form.submit();}//增加一行 function addFile(){//在table里面增加一行var table = document.getElementsByTagName("table")[0];table.innerHTML+="<tr><td><input type='file' name='filename'/></td><td><input type='button' value='删除' οnclick='dele(this)'/><td/><tr/> ";}//删除一行 function dele(who){//获取当前点击的删除按钮所在的trvar tr=who.parentNode.parentNode;//拿到爸爸var table=tr.parentNode;//通过爸爸删除儿子 table.removeChild(tr);} </script> </html>
servlet处理页面(对应的图片文件就不放上来了)
package com.zzx.upload;import java.io.FileOutputStream; import java.io.IOException; import java.io.InputStream; import java.io.OutputStream; import java.util.List;import javax.servlet.ServletException; 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;public class Upload2 extends HttpServlet {public void doGet(HttpServletRequest request, HttpServletResponse response)throws ServletException, IOException {try {//1,創建磁盤文件工廠DiskFileItemFactory dff = new DiskFileItemFactory();//2,創建核心上傳類ServletFileUpload fileupload = new ServletFileUpload(dff);fileupload.setHeaderEncoding("utf-8");//3,解析对应的请求数据List<FileItem> fl = fileupload.parseRequest(request);for (FileItem fileItem : fl) {//判断是否是普通输入项if(fileItem.isFormField()){//如果是普通输入项,就得到普通输入项name的属性值,和输入的值String name = fileItem.getFieldName();String value = fileItem.getString();System.out.println(name + ":" + value);}else{//如果是文件上传项//获取上传的文件名称,但是有的浏览器里面带的是带路径的名称String filename = fileItem.getName();//优化,判断是否带/,如果带"/"就进行截取,否则就直接用int lens=filename.lastIndexOf("/");if(lens!=-1){filename=filename.substring(lens+1);}//获取文件上传的输入流InputStream is =fileItem.getInputStream();//得到文件夹带盘符的路径String path = getServletContext().getRealPath("/upload");//输出流OutputStream os =new FileOutputStream(path + "/" + filename);//流对接int len=0;byte[]arr =new byte[1024*8];while((len = is.read(arr))!=-1){os.write(arr,0,len);}//关流 is.close();os.close();}}} catch (Exception e) {e.printStackTrace();}}public void doPost(HttpServletRequest request, HttpServletResponse response)throws ServletException, IOException {doGet(request, response);}}
6 文件的下载:
6.1 把服务器上文件保存到本地硬盘,这个过程称为文件的下载
6.2 文件下载的实现方式:
6.2.1: 实现超链接的文件下载
弊端:有的文件无法实现下载,而是显示在页面上(比如图片)
6.2.2: 通过代码实现文件下载
无论什么格式的文件都可以下载
实现步骤:
第0步:设置要下载的文件MIME类型(可选)
第一步:设置头信息,Content-Disposition,无论什么格式,都是以下载的方法打开
第二步:服务器得到文件的输入流
第三步:创建输出流,写出到浏览器
第四步:流对接
具体代码:
6.3 常见问题:
6.3.1 当文件名携带中文的时候(中文名称会乱码,不显示之类的问题)
6.3.2 原因:不同浏览器编码不同
ie浏览器采用的是url编码,
火狐浏览器采用的是base64编码,
6.3. 3 ① 区分不同的浏览器
通过请求头 User-Agent,得到当前浏览器的请求类型
②根据不同的浏览器设置不同的编码(IE,谷歌解决方式一致)
这里是文件下载的页面
package com.zzx.down;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.http.HttpServlet; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse;import sun.misc.BASE64Encoder;import com.sun.xml.internal.messaging.saaj.util.Base64; /** 这个页面是实现文件的下载*/ public class DownServlet extends HttpServlet {public void doGet(HttpServletRequest request, HttpServletResponse response)throws ServletException, IOException {//0,得到文件的路径String path = getServletContext().getRealPath("/down/图片.jpg");//得到文件名//这里寻找"/"要注意使用"\\"才能正确的截取String filename = path.substring(path.lastIndexOf("\\")+1);//得到请求的浏览器类型String agent = request.getHeader("User-Agent");//判断浏览器类型 System.out.println(agent);if(agent.contains("Firefox")){//如果是火狐,进行base64编码filename = "=?UTF-8?B?"+new BASE64Encoder().encode(filename.getBytes("utf-8")) + "?=";}else{//url编码,谷歌,IE都可以通过这样设置filename=URLEncoder.encode(filename, "UTF-8");}//1,设置文件的mime类型//先得到文件的mime类型String type = getServletContext().getMimeType(filename);//设置 response.setContentType(type);response.setHeader("Content-Disposition", "attachment;filename=" + filename);//得到输入流InputStream is = new FileInputStream(path);//得到输出流OutputStream os = response.getOutputStream();//2,流对接int a=0;byte[]arr =new byte[1024*8];while((a = is.read(arr))!=-1){os.write(arr,0,a);}//3,关流os.close(); //会自动关闭,不过要养成关流的习惯 is.close();}public void doPost(HttpServletRequest request, HttpServletResponse response)throws ServletException, IOException {doGet(request, response);}}
转载于:https://www.cnblogs.com/adventurer/p/5496040.html
javaweb-文件的上传下载相关推荐
- javaWeb - 文件的上传下载
文件的上传和下载 <%--文件的上传和下载文件的上传和下载,是非常常见的功能.很多的系统中,或者软件中都经常使用文件的上传和下载.比如:QQ 头像,就使用了上传.邮箱中也有附件的上传和下载功能. ...
- JavaWeb 文件的上传和下载
JavaWeb 文件的上传和下载 这是一个简单的案例,让你快速了解JavaWeb中文件的上传和下载 文件的上传和下载是Web开发中非常常见和重要的功能,很多系统中都会经常使用文件的上传和下载. 如:博 ...
- Java使用SFTP和FTP两种连接服务器的方式实现对文件的上传下载
一.Java实现对SFTP服务器的文件的上传下载: 1.添加maven依赖: <dependency><groupId>com.jcraft</groupId>&l ...
- 文件的上传下载功能的实现(包括进度条)[telerik控件]
文件的上传下载功能的实现(包括进度条) 1.准备工作 首先我们需要Telerik控件,数据库,上传文件文件夹. Telerik控件: RadUpload.RadProgressManager.RadP ...
- ssm框架验证码图片加载不出_基于SSM框架的文件图片上传/下载功能实现
前一段时间很多做毕业设计的同学问:如何写图片和文件的上传下载功能,今天正好有时间,所以就做了一个案例,详细的讲解这个功能. 框架结构: 对于很多做过开发的而言,上传功能肯定都用过,而且用到的场景很多, ...
- ACTIVEX实现大文件FTP上传下载---上
ACTIVEX实现大文件FTP上传 在Windows 操作系统下,有一个重要的机制,就是OLE ,就是可以让某个应用程序(OLE Controller)访问其它应用程序(OLE Server)所提供的 ...
- 基于layui.upload.js 拖拽文件/文件夹上传下载
layui.upload.js 拖拽文件/文件夹上传下载 前言 js代码 页面使用(我这里用的是uploader.jsp) CSS文件 上传效果 总结 前言 项目需求完成文件上传,可以拖拽上传文件/文 ...
- 使用JSP+Servlet实现文件的上传下载上传
<!DOCTYPE html > <html> <head> <meta charset="UTF-8"> <title> ...
- 文件的上传下载(一)
2019独角兽企业重金招聘Python工程师标准>>> 最近公司培训,所以收集整理了一些关于上传下载的资料,进行了整理与大家分享. Struts对文件上传的支持非常好,它是通过jak ...
- 云计算学习笔记004---hadoop的简介,以及安装,用命令实现对hdfs系统进行文件的上传下载
1.Hadoop简介 1.hadoop的诞生 l Nutch和Lucene之父Doug Cutting在2006年完成Hadoop项目. l Hadoop并不是一个单词,它来源于DougCutti ...
最新文章
- java json设置编码_我们如何用Java编码JSON对象?
- 达内出来的混得怎么样了_《士兵突击》主演现状:混得最好的不是王宝强,而是一向低调的他...
- 20172310 2017-2018-2 《程序设计与数据结构》第八周学习总结
- 把有限的精力放在最有意义的事上
- inaflash什么意思中文_英文“flash”翻译成中文是什么意思?
- java模拟登陆_java-模拟登陆练习(示例代码)
- 用c语言程序算自己的年龄,新手编的小程序:计算年龄和出生后经历的天数的小程序...
- python消费kafka逻辑处理导致cpu升高_大数据技术之一次KAFKA消费者异常引起的思考...
- 【JavaScript】Uncaught TypeError: Illegal invocation
- Python面试题之“猴子补丁”(monkey patching)指的是什么?这种做法好吗?
- 关于ArcGIS动态图层空间内栅格数据,JS前端显示颜色不正确的解决方案
- (原創) C++的4個Class Access Label (C/C++)
- 多极神经元切片手绘图,神经组织切片手绘图片
- 堆糖生活家喜欢的图片批量下载
- 舒淇陈坤言承旭周渝民 揭秘与助理的爱恨纠葛
- 【2011集训队出题】跳跳棋
- MICCAI 2022 | mmFormer:Multimodal Medical Transformer for Incomplete Multimodal Learning of BTS
- jQuery贼简单的选项卡切换
- 【HTML | CSS】春节将至,为网页挂上精美的灯笼吧(附源码)程序员的浪漫
- IBM最新洞察:我们所熟知的通信服务时代已经结束
热门文章
- C语言 · 字符删除
- RTMP vs RTMFP
- Linux---Samba文件共享服务
- 490 - Rotating Sentences
- [Android] 开发一款软件我学到了些什么?
- mysql+enable+sql+log_MySQL -- redolog + binlog
- python屏幕找图_Python实现按键精灵(二)-找图找色
- c语言程序设计的例题,C语言程序设计例题与习题--详细介绍
- linux jsp mysql_Linux JSP连接MySQL数据库
- mysql mssql 性能对比_详解mysql分区实验测试--非分区表与分区表的性能对比