Struts2实现文件的上传与下载
2015-08-09 22:11
507 查看
感谢:Struts2多个文件上传的分析及源代码说明
一 介绍
1.新建项目,并导入相应的包
2. Struts2文件上传并未提供自己的请求解析器,也就是说,struts2不会自己去处理multipart/form-data的请求,它需要调用其他的请求解析器,将http请求中的表单域解析出来。但struts2在原有的上传解析器继承上做了进一步封装,更进一步简化了文件上传。
3. Struts2默认使用的是Jakarta和Connon-FileUpload的文件上传框架,因此,如果需要使用struts2的文件上传功能,则需要在Web应用导入上面我所说的几个包
二.实例
1.表单enctype属性
表单的enctype属性指定的是表单数据的编码方式,该属性呢有3个值
(1) application/x-www-form-urlencoded,这是默认的编码方式,它只能处理表单域里的value属性,采用这种编码方式的表单会将表单域的值处理成URL编码方式。
(2)multipart/form-data,采用这种编码方式会以二进制流的方式来处理表单数据 ,这种编码方式会把文件域指定文件的内容也封装到请求参数里。
(3)text/plain,这种编码方式当表单的action属性为mailto:URL的形式是比较方便,这种方式主要适用于直接通过表单发送邮件的方式。
2.html代码:
通过以上的Action我们可以看出Action还包括了两个属性,fileFileName,fileContentType, 这两个属性分别用来封装上传我文件的文件名,上传文件的文件类型,Action类直接通过File类型属性直接封装了上传文件的内容,但这个File属性无法获取上传文件的文件名和文件类型,所以struts2直接将包含的上传文件名和文件类型的信息封装到fileFileName,fileContentType属性中,可以认为:如果表单中包含一个name属性为xxx的文件域,则对应的Action需要使用3个属性来封装该文件域的信息:
(1) 类型为File的xxx属性封装了该文件域对应的文件内容
(2) 类型为String的xxxFileName属性封装了该案文件域对应的文件的文件类型
(3) 类型为String的xxxContentType属性封装了该文件域对应的文件的类型
一 介绍
1.新建项目,并导入相应的包
2. Struts2文件上传并未提供自己的请求解析器,也就是说,struts2不会自己去处理multipart/form-data的请求,它需要调用其他的请求解析器,将http请求中的表单域解析出来。但struts2在原有的上传解析器继承上做了进一步封装,更进一步简化了文件上传。
3. Struts2默认使用的是Jakarta和Connon-FileUpload的文件上传框架,因此,如果需要使用struts2的文件上传功能,则需要在Web应用导入上面我所说的几个包
二.实例
1.表单enctype属性
表单的enctype属性指定的是表单数据的编码方式,该属性呢有3个值
(1) application/x-www-form-urlencoded,这是默认的编码方式,它只能处理表单域里的value属性,采用这种编码方式的表单会将表单域的值处理成URL编码方式。
(2)multipart/form-data,采用这种编码方式会以二进制流的方式来处理表单数据 ,这种编码方式会把文件域指定文件的内容也封装到请求参数里。
(3)text/plain,这种编码方式当表单的action属性为mailto:URL的形式是比较方便,这种方式主要适用于直接通过表单发送邮件的方式。
2.html代码:
<span style="font-size:14px;"><body> <form method="POST" enctype="multipart/form-data" action="upload.html"> File to upload: <input type="file" name="file"><br /> <br /> Notes about the file: <input type="text" name="note"><br /> <br /> <input type="submit" value="Press"> to upload the file! </form><br><br> <form method="POST" enctype="multipart/form-data" action="uploadList.html"> File to upload: <input type="file" name="fileList"><br /> <br /> File to upload: <input type="file" name="fileList"><br /> <br /> File to upload: <input type="file" name="fileList"><br /> <br /> Notes about the file: <input type="text" name="notes"><br /> <br /> <input type="submit" value="Press"> to upload the file! </form><br><br> <a href="listAllFile.html">List all files</a> </body></span>struts.properties配置
<span style="font-size:14px;">#指定Web应用的默认编码集,相当于调用HttpServletRequest的setCharacterEncoding方法 struts.i18n.encoding=UTF-8 #开发者模式,这样可以打印出更详细的错误信息 struts.devMode=true #设置是否每次请求,都重新加载资源文件,默认值为false. struts.i18n.reload=true #当struts的配置文件修改后,系统是否自动重新加载该文件,默认值为false(生产环境下使用),开发阶段最好打开 struts.configuration.xml.reload=true #设置浏览器是否缓存静态内容,默认值为true(生产环境下使用),开发阶段最好关闭 struts.serve.static.browserCache=false #指定Struts 2文件上传中整个请求内容允许的最大字节数,100M struts.multipart.maxSize=104857600 #设置url请求后缀 struts.action.extension=html</span>struts.xml
<span style="font-size:14px;"><?xml version="1.0" encoding="UTF-8" ?> <!DOCTYPE struts PUBLIC "-//Apache Software Foundation//DTD Struts Configuration 2.3//EN" "http://struts.apache.org/dtds/struts-2.3.dtd"> <struts> <package name="default" namespace="/" extends="struts-default"> <action name="upload" class="com.lxz.UploadAndDownloadAction" method="upload"> <result name="success">/WEB-INF/results.jsp</result> <interceptor-ref name="fileUpload"> <!-- 拦截器允许的上传到当前action中的文件最大长度(以byte为单位) --> <!-- properties中的struts.multipart.maxSize和action拦截器的maximumSize属性分工不同 --> <!-- struts.multipart.maxSize掌控整个项目所上传文件的最大的Size,超过了这个size,后台报错,默认2M --> <!-- action拦截器的maximumSize属性必须小于struts.multipart.maxSize的值 --> <!-- <param name="maximumSize">2*1024*1024</param> --> <!-- 拦截器允许的可以传到action中的contentType,如果没有指定就是允许任何上传类型 --> <param name="allowedTypes"> text/plain,application/msword,image/jpeg </param> </interceptor-ref> <!-- 自定义了拦截器后必手动定义默认的拦截器,否则默认的拦截器不会被执行 --> <interceptor-ref name="defaultStack" /> </action> <action name="uploadList" class="com.lxz.UploadAndDownloadAction" method="uploadList"> <result name="success">/WEB-INF/results.jsp</result> <interceptor-ref name="fileUpload"> <!-- <param name="maximumSize">2*1024*1024</param> --> <param name="allowedTypes"> text/plain,application/msword,image/jpeg </param> </interceptor-ref> <interceptor-ref name="defaultStack" /> </action> <action name="download" class="com.lxz.UploadAndDownloadAction" method="download"> <result type="stream" name="success"> <!-- 文件类型 ,application/octet-stream 表示无限制 --> <param name="contentType">application/octet-stream</param> <!-- 数据流对象名,由Action中的getInputStream方法获得 --> <param name="inputName">inputStream</param> <!-- 指定下载的文件名和显示方式 ,但注意中文名的乱码问题,解决办法是:进行编码处理 --> <!-- contentDisposition是文件下载的处理方式,包括内联(inline)和附件(attachment) --> <!-- 默认是inline,使用附件时这样配置:attachment;filename="文件名" --> <param name="contentDisposition">attachment;filename="${fileName}"</param> <!-- 指定下载文件的缓存大小 --> <param name="bufferSize">4096</param> </result> <result type="dispatcher" name="error">/WEB-INF/results.jsp</result> </action> <action name="listAllFile" class="com.lxz.UploadAndDownloadAction" method="listAllFile"> <result>/WEB-INF/results.jsp</result> </action> </package> </struts> </span>action
<span style="font-size:14px;">package com.lxz; import java.io.File; import java.io.FileInputStream; import java.io.FileOutputStream; import java.io.InputStream; import java.io.OutputStream; import java.net.URLDecoder; import java.util.HashMap; import java.util.List; import java.util.Map; import org.apache.struts2.ServletActionContext; import com.opensymphony.xwork2.ActionContext; import com.opensymphony.xwork2.ActionSupport; public class UploadAndDownloadAction extends ActionSupport { private static final long serialVersionUID = 1L; private InputStream inputStream; private String fileName; private File file; // file并不是指前端jsp上传过来的文件本身,而是文件上传过来存放在临时文件夹下面的文件 private String note; private String fileFileName; // 上传文件的名称,file,fileFileName,fileContentType对应 private String fileContentType; // 上传文件的类型(提交过来的file的MIME类型) private List<File> fileList; private String notes; private List<String> fileListFileName; private List<String> fileListContentType; /*private File[] fileList; private String[] fileListFileName; private Str b55c ing[] fileListContentType;*/ /** * 上传单个文件 */ public String upload() throws Exception { // 把上传的文件放到指定的路径下 String path = ServletActionContext.getServletContext().getRealPath( "/WEB-INF/upload"); System.out.println("path = " + path); System.out.println("fileFileName = " + fileFileName); System.out.println("fileContentType = " + fileContentType); System.out.println("note = " + note); File saveFile = new File(path); // 如果指定的路径没有就创建 if (!saveFile.exists() && !saveFile.isDirectory()) { saveFile.mkdir(); } if (file != null) { // 输出流 OutputStream os = new FileOutputStream(new File(path , fileFileName)); // 输入流 InputStream is = new FileInputStream(file); System.out.println("path = " + path); System.out.println("file.getName() = " + file.getName()); System.out.println("file.getPath = " + file.getPath()); byte[] buffer = new byte[1024]; int len = 0; while ((len = is.read(buffer)) > 0) { os.write(buffer, 0, len); } is.close(); os.close(); ActionContext.getContext().put("message", "上传成功"); } return SUCCESS; } /** * 上传多个文件,可采用集合和数组的方法 */ public String uploadList() throws Exception { // 把上传的文件放到指定的路径下 String path = ServletActionContext.getServletContext().getRealPath( "/WEB-INF/uploadList"); File saveFile = new File(path); // 如果指定的路径没有就创建 if (!saveFile.exists() && !saveFile.isDirectory()) { saveFile.mkdir(); } // 把得到的文件的集合通过循环的方式读取并放在指定的路径下 for(int i=0;i<fileList.size();i++){ if(fileList.get(i) != null){ // 输出流 OutputStream os = new FileOutputStream(new File(path , fileListFileName.get(i))); // 输入流 InputStream is = new FileInputStream(fileList.get(i)); System.out.println("path = " + path); System.out.println("fileList.get(i).getName() = " + fileList.get(i).getName()); System.out.println("fileList.get(i).getPath = " + fileList.get(i).getPath()); byte[] buffer = new byte[1024]; int len = 0; while ((len = is.read(buffer)) > 0) { os.write(buffer, 0, len); } is.close(); os.close(); ActionContext.getContext().put("message", "上传成功"); } } return SUCCESS; } /** * 下载文件 */ public String download() throws Exception { // 解码,绝对路径 String realName = URLDecoder.decode(fileName, "UTF-8"); // 获取数据流 inputStream = new FileInputStream(realName); // 获取文件名 fileName = new String( (realName.substring(realName.lastIndexOf("/") + 1)) .getBytes("UTF-8"), "ISO-8859-1"); return SUCCESS; } /** * 列出所有文件 */ public String listAllFile() throws Exception { // 文件目录 String filePath = "d:/temp"; File file = new File(filePath); // 存储要下载的文件 Map<String, String> fileMap = new HashMap<String, String>(); // 如果目录存在,并且目录是一个文件夹 if (file.exists() && file.isDirectory()) { // 获取所有文件 this.getFiles(file, fileMap); ActionContext context = ActionContext.getContext(); // 向request里放attribute context.put("fileMap", fileMap); // 向session里放attribute // context.getSession().put("fileMap", fileMap); } else { file.mkdir(); } return SUCCESS; } public void getFiles(File file, Map<String, String> fileMap) throws Exception { // 目录为文件夹 if (file.isDirectory()) { File[] files = file.listFiles(); // 遍历数组 for (File f : files) { // 递归 getFiles(f, fileMap); } } else {// 文件 // file.getAbsolutePath()获取文件绝对路径,唯一值,如:d:\temp\aaa.txt,需要转为d:/temp/aaa.txt // file.getName()获得文件名,如:aaa.txt fileMap.put(file.getAbsolutePath().replace("\\", "/"), file.getName()); } } <span style="white-space:pre"> </span>//set,get方法省略 } </span>
通过以上的Action我们可以看出Action还包括了两个属性,fileFileName,fileContentType, 这两个属性分别用来封装上传我文件的文件名,上传文件的文件类型,Action类直接通过File类型属性直接封装了上传文件的内容,但这个File属性无法获取上传文件的文件名和文件类型,所以struts2直接将包含的上传文件名和文件类型的信息封装到fileFileName,fileContentType属性中,可以认为:如果表单中包含一个name属性为xxx的文件域,则对应的Action需要使用3个属性来封装该文件域的信息:
(1) 类型为File的xxx属性封装了该文件域对应的文件内容
(2) 类型为String的xxxFileName属性封装了该案文件域对应的文件的文件类型
(3) 类型为String的xxxContentType属性封装了该文件域对应的文件的类型
相关文章推荐
- java对世界各个时区(TimeZone)的通用转换处理方法(转载)
- java-注解annotation
- java-模拟tomcat服务器
- java-用HttpURLConnection发送Http请求.
- java-WEB中的监听器Lisener
- Android IPC进程间通讯机制
- Android Native 绘图方法
- Android java 与 javascript互访(相互调用)的方法例子
- 介绍一款信息管理系统的开源框架---jeecg
- 聚类算法之kmeans算法java版本
- java实现 PageRank算法
- PropertyChangeListener简单理解
- 插入排序
- 冒泡排序
- 堆排序
- 快速排序
- 二叉查找树
- [原创]java局域网聊天系统