Struts2实现文件上传

一、文件上传原理

表单元素的enctype属性执行的是表单元素的编码方式,该属性有三个值;

1)、application/x-www-form-urlencoded:这是默认的编码方式,它只处理表单中的value,采用这种方式的表单会将表单域里的值处理成url编码方式。

2)、multipart/form-data:这种编码方式的表单会以二进制流的方式来处理表单数据,这种编码方式会把文件域指定文件的内容也封装到请求参数里。

3)、text/plain:这种方式主要适用于直接通过表单发送邮件的方式。

文件上传是通过为表单元素设置enctype=”multipart/form-data”属性,让表单提交的数据以二进制编码的方式提交,在接收此请求的Servlet中用二进制流来获取内容,就可以取得上传文件的内容,从而实现文件的上传。

在Java领域中,有两个常用的文件上传项目:一个是Apache组织Jakarta的Common-FileUpload组件:
([url]http://commons.apache.org/fileupload/)
另一个是Oreilly组织的COS框架:
([url]http://www.servlets.com/cos/)。
利用这两个框架都能很方便的实现文件的上传。

二、Struts2下的文件上传

Struts2并没有提供自己的请求解析器,也就是说Struts2不会自己去处理multipart/form-data的请求,它需要调用其 他请求解析器,将HTTP请求中的表单域解析出来。但Struts2在原有的上传解析器基础上做了进一步封装,更进一步简化了文件上传。

Struts2默认使用的是Jakarta的Common-FileUpload框架来上传文件(可以从defaults.properties文件中看到)

这里写图片描述

因此、我们需要导入两个jar包commons-fileupload.jar和commons-io.jar。它在原上传框架上做了进一步封装,简化了文件上传的代码实现,取消了不同上传框架上的编程差异。

范例:

jsp

<body>
    <fieldset>
        <legend>文件上传</legend>
    <form action="FileUpload_fileUpload.action" method="post" enctype="multipart/form-data">
        文件:<input type="file" name="file" />
        <input type="submit" value="提交" />
    </form>
    </fieldset>
  </body>

Action

    private File file;              //上传文件对象
    private String fileFileName;    //上传文件名
    private String fileContentType; //上传文件类型

    /**
     * 文件上传
     * @return
     */
    public String upload(){
        InputStream is = null;
        OutputStream os = null;
        //获取要上传到的目录
        String path = ServletActionContext.getRequest()
                .getServletContext().getRealPath("/files");
        try {
            is = new FileInputStream(file);
            os = new FileOutputStream(new File(path,fileFileName));

            byte[] bys = new byte[1024];
            int len = 0;
            while((len=is.read(bys))!=-1){
                os.write(bys, 0, len);
            }
        } catch (Exception e) {
            e.printStackTrace();
        }finally{
            if(is != null){
                try {
                    is.close();
                } catch (IOException e) {
                    e.printStackTrace();
                }
            }
            if(os != null){
                try {
                    os.close();
                } catch (IOException e) {
                    e.printStackTrace();
                }
            }
        }
        return "fileUpload";
    }
    //....省略geter/seter

配置

这里写图片描述

其他的一些配置

struts.multipart.saveDir=
struts.multipart.maxSize=2097152

这些是default.properties中的,我们也可以修改这些配置。

<constant name="struts.multipart.saveDir" value="E:\" />
<constant name="struts.multipart.maxSize" value="20971520" />

通过拦截器的配置限制文件上传的扩展名和文件上传的大小。

这里写图片描述

上传文件超过大小范围:
这里写图片描述

这是需要进行国际化错误信息:在核心包中的struts-messsages.properties文件中有这些信息。

这里写图片描述

新建一个i18n.properties文件进行配置

这里写图片描述

一些问题总结:

描述:在使用Struts2的文件上传时,文件大小和类型过滤后,页面无法跳转至input页面

原因:文件上传类未继承ActionSupport,导致拦截器的跳转到input页面的功能不能真正使用

描述:文件上传的过滤先后问题

1.先判断表单提交的数据大小,是否超过配置文件“struts.multipart.maxSize”的值(默认大小:2097152 B);

2.再判断上传的文件数据是否超过拦截器里配置的“maximumSize”的大小;

3.最后检查是否文件类型是否满足拦截器的条件;

另外还有一点需要说明的是,有些配置上传过滤器是这样配置的

<interceptor-ref name="fileUpload">  
    <param name="allowedTypes">  
        image/bmp,image/png,image/gif,image/jpeg  
    </param>  
    <param name="maximumSize">1024000</param>  
</interceptor-ref>  
<interceptor-ref name="defaultStack"></interceptor-ref> 

因为默认拦截器栈“defaultStack”是包含文件上传拦截器的,所以依拦截的先后顺序,此处文件上传拦截器会执行2次,所以不建议如此配置,合理的做法应该是配置默认拦截器栈,在里面覆盖掉“fileUpload”的属性即可。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值