一、文件上传
1、上传文件jsp页面
表单中enctype 必须为 multipart/form-data,提交方式必须为 post。
<%@ page language="java" import="java.util.*" pageEncoding="UTF-8"%> <%@taglib prefix="s" uri="/struts-tags" %> <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"> <html> <head> <title>My JSP 'fileupload.jsp' starting page</title> <meta http-equiv="pragma" content="no-cache"> <meta http-equiv="cache-control" content="no-cache"> <meta http-equiv="expires" content="0"> </head> <body> <form action="fileupload_fileUpload.action" enctype="multipart/form-data" method="post"> <s:if test="fieldErrors['upload'].size()>0"> <s:property value="fieldErrors['upload'][0]"/> </s:if> <!-- 说明上传成功 --> <s:else> <p> <s:property value="message"/> <!-- 显示上传成功的提示信息 --> 文件名:<s:property value="uploadFileName"/> <!-- 显示上传文件名 --> 文件类型:<s:property value="uploadContentType"/> <!-- 显示上传文件类型 --> </p> </s:else> <p> 上传者:<input type="text" name="author" class="ipt"> </p> <p> 选择文件:<input type="file" name="upload" class="ipt"> </p> <p><input type="submit" value="提交"> </p> </form> </body> </html>
2、上传文件Action
对于name属性为xxx的文件,Action中需要用File类型的xxx封装上传的文件实例,用String类型的xxxFileName封装文件的名称,用xxxContent封装文件的文件类型。
package com.action; import java.io.File; import org.apache.commons.io.FileUtils; import org.apache.struts2.ServletActionContext; import com.opensymphony.xwork2.ActionContext; import com.opensymphony.xwork2.ActionSupport; public class FileUploadAction extends ActionSupport { /** * */ private static final long serialVersionUID = 1L; private String message; // 提示信息 private String author; // 上传者 //需要提供get set方法才会封装进值 private File upload; // Struts2会将上传成功的文件对象赋值给该属性 private String uploadFileName; // 封装上传文件的名称,包括后缀 private String uploadContentType; // 封装上传文件的类型 public String fileUpload() throws Exception { // 保存文件的路径 String realpath = ServletActionContext.getServletContext().getRealPath("/upload"); System.out.println("文件路径" + realpath+" "+"文件类型:"+uploadContentType); // 未选择上传文件就提交的处理 if (upload != null) { File savefile = new File(new File(realpath), uploadFileName); // 如果该文件所在目录不存在,则生成一个目录 if (!savefile.getParentFile().exists()) { savefile.getParentFile().mkdirs(); } FileUtils.copyFile(upload, savefile); ActionContext.getContext().put("msg", "上传文件成功"); }else{ ActionContext.getContext().put("msg", "请选择上传文件"); } return "success"; } public String getMessage() { return message; } public void setMessage(String message) { this.message = message; } public String getAuthor() { return author; } public void setAuthor(String author) { this.author = author; } public File getUpload() { return upload; } public void setUpload(File upload) { this.upload = upload; } public String getUploadFileName() { return uploadFileName; } public void setUploadFileName(String uploadFileName) { this.uploadFileName = uploadFileName; } public static long getSerialversionuid() { return serialVersionUID; } public String getUploadContentType() { return uploadContentType; } public void setUploadContentType(String uploadContentType) { this.uploadContentType = uploadContentType; } }
3、struts.xml配置
如果不配置上传的文件大小,当所选文件过大时,会报错。
Struts2提供了一个文件上传的拦截器,配置拦截器时,可以为其指定两个参数:allowedTypes 和 maximumSize。
注意:其中常量里配置的文件上传大小是总的上传文件大小,拦截器中是单个上传文件大小。常量配置的允许大小,可视为总开关,不满足条件的大小将不会触发拦截且会报错。
<?xml version="1.0" encoding="UTF-8"?> <!DOCTYPE struts PUBLIC "-//Apache Software Foundation//DTD Struts Configuration 2.3//EN" "struts-2.3.dtd" > <struts> <!-- 热部署 --> <constant name="struts.configuration.xml.reload" value="true"></constant> <!-- 修改struts2允许上传的最大值 --> <constant name="struts.multipart.maxSize" value="7097152"/> <!-- 动态方法调用 --> <constant name="struts.enable.DynamicMethodInvocation" value="true"></constant> <package name="hello" namespace="/" extends="struts-default"> <action name="fileupload_*" class="com.action.FileUploadAction" method="{1}"> <!-- 引入文件上传过滤器 --> <interceptor-ref name="fileUpload"> <param name="maximumSize">7097152</param> <!-- 允许上传的单个文件大小 --> <param name="allowedTypes">image/bmp</param> <!-- 允许上传的文件类型,多个用,隔开 --> </interceptor-ref> <!-- 配置系统默认拦截器 --> <interceptor-ref name="defaultStack"/> <result name="input">/fileupload.jsp</result> <!-- 文件过滤失败后,转入input视图 --> <result name="success">/fileupload.jsp</result> </action> </package> </struts>
常见问题:
当我们上传文件出错时,会出现Struts2系统默认的提示信息,这些信息,可以根据<s:debug>标签获取,为了获取更国际化的提示信息,例如,将提示信息改为中文。
操作步骤:
1、在struts.xml配置中加载全局国际化资源文件的常量
<constant name="struts.custom.i18n.resources" value="message"/>
2、在src目录下创建message.properties全国国际化文件,文件中添加如下内容
struts.messages.error.file.too.large=u60A8u8981u4E0Au4F20u7684u6587u4EF6u592Au5927uFF0Cu8BF7u91CDu65B0u9009u62E9
Struts2同时上传多个文件
Action类:
public class ManyFileUploadAction extends ActionSupport{ private List<File> upload; //多文件封装为List private List<String> uploadFileName; public String manyFileUpload() throws Exception{ for(int i=0;i<upload.size();i++){ //处理每个文件上传的业务操作 } }
二、文件下载
<a href="downLoad_downLoad.action?fileName=struts2学习笔记.txt">下载</a> <a href="downLoad_downLoad.action?fileName=readme.txt">下载</a> <!-- 下载至本地计算机中 --> <a href="upload/readme.txt">下载</a> <!-- 直接显示在网页中 -->
struts.xml配置:
<action name="downLoad_*" class="com.action.DownloadAction" method="{1}"> <!-- 文件下载时返回类型必须为stream --> <result name="success" type="stream"> <param name="contentDisposition"> <!-- attachment 表示浏览器以附件形式供下载 inline 表示内联方式 ${fileName}表示获取DownLoadAction的fileName值 --> attachment;filename="${fileName}" </param> <!-- <param name="inputName"> InputStream </param> --> </result> </action>
action类:
遗留问题:下载中文名称文件报错无法下载。
package com.action; import java.io.FileInputStream; import java.io.FileNotFoundException; import java.io.InputStream; import java.io.UnsupportedEncodingException; import org.apache.struts2.ServletActionContext; import com.opensymphony.xwork2.ActionSupport; public class DownloadAction extends ActionSupport{ private String fileName; // 要下载的文件名 public String downLoad(){ return "success"; } /** * 返回类型必须为 InputStream * @return * @throws FileNotFoundException * @throws UnsupportedEncodingException */ public InputStream getInputStream() throws FileNotFoundException, UnsupportedEncodingException { System.out.println("文件名:"+getFileName()); String path = ServletActionContext.getServletContext().getRealPath("/upload/"+fileName); System.out.println("下载路径:"+path); FileInputStream fis = new FileInputStream(path); return fis; } /** * 解决乱码问题 * @return * @throws UnsupportedEncodingException */ public String getFileName() throws UnsupportedEncodingException{ return new String(this.fileName.getBytes(),"ISO8859-1"); } public void setFileName(String fileName) { this.fileName = fileName; } }