zoukankan      html  css  js  c++  java
  • Java实战之01Struts204拦截器、上传下载、OGNL表达式

    十二、Struts2中的拦截器

    1、拦截器的重要性

    Struts2中的很多功能都是由拦截器完成的。比如:servletConfigstaticParamparamsmodelDriven等等。

    AOP编程思想的一种应用形式。

    2、拦截器的执行时机:

    \

    3、自定义拦截器

    3.1、拦截器的类试图(初级版本)

    3.2、编写步骤:

    a、编写一个类,继承AbstractInterceptor类或者实现Interceptor接口。重写intercept方法。

     1 public class MyInterceptorDemo1 extends AbstractInterceptor {
     2 
     3     public String intercept(ActionInvocation invocation) throws Exception {
     4         System.out.println("MyInterceptorDemo1拦截了:访问动作之前");
     5         //放行的含义:如果有下一个拦截器,则执行下一个拦截器。如果该拦截器是最后一个,则执行动作方法。
     6         String rtValue = invocation.invoke();//此行是放行的方法
     7         System.out.println("MyInterceptorDemo1拦截器"+rtValue);
     8         System.out.println("MyInterceptorDemo1拦截了:访问动作之后");
     9         return rtValue;
    10     }
    11 
    12 }

    b、配置拦截器:注意拦截器必须先声明再使用

     1             a、声明拦截器
     2                 <interceptors>
     3                     <interceptor name="myInterceptor1" class="cn.itcast.web.interceptors.MyInterceptorDemo1"></interceptor>
     4                 </interceptors>
     5             b、使用拦截器
     6                 <action name="action1" class="cn.itcast.web.action.Demo1Action" method="demo1">
     7                     <!-- 使用拦截器。当我们配置了一个拦截器之后,默认的拦截器栈就失效了-->
     8                     <interceptor-ref name="myInterceptor1"></interceptor-ref>
     9                     <result name="success">/success.jsp</result>
    10                 </action>

    3.3、执行顺序

    3.4、多个拦截器的执行顺序

    3.5intercept方法的返回值

    4、拦截器的应用:

    4.1、检查登录的拦截器案例

    配置文件:

     1 <package name="myDefault" extends="struts-default" abstract="true">
     2         <interceptors>
     3             <interceptor name="checkLoginInterceptorDemo2" class="cn.itcast.web.interceptors.CheckLoginInterceptorDemo2"></interceptor>
     4             <interceptor-stack name="myDefaultStack">
     5                 <interceptor-ref name="checkLoginInterceptorDemo2"></interceptor-ref>
     6                 <interceptor-ref name="defaultStack"></interceptor-ref>
     7             </interceptor-stack>
     8         </interceptors> 
     9         <default-interceptor-ref name="myDefaultStack"></default-interceptor-ref>
    10         <global-results>
    11             <result name="login">/login.jsp</result>
    12         </global-results>
    13     </package>
    14     <package name="bbs" extends="myDefault">
    15         <action name="showMain" class="cn.itcast.web.action.BBSAction" method="showMain">
    16             <result name="success">/main.jsp</result>
    17         </action>
    18         <action name="showOther" class="cn.itcast.web.action.BBSAction" method="showOther">
    19             <result name="success">/other.jsp</result>
    20         </action>        
    21         <action name="login" class="cn.itcast.web.action.BBSAction" method="login">
    22             <interceptor-ref name="myDefaultStack">
    23                     <!-- 为拦截器注入参数,告知拦截器要排除的方法 -->
    24                     <param name="checkLoginInterceptorDemo2.excludeMethods">login</param>
    25             </interceptor-ref>
    26             <result name="success" type="redirectAction">showMain</result>
    27         </action>
    28     </package>

    动作类:

    1 public class Demo1Action extends ActionSupport {
    2 
    3     public String demo1(){
    4         System.out.println("Demo1Action的demo1方法执行了");
    5         return SUCCESS;
    6     }
    7 }

    拦截器:

     1 public class CheckLoginInterceptorDemo1 extends AbstractInterceptor {
     2 
     3     public String intercept(ActionInvocation invocation) throws Exception {
     4         Object obj = ServletActionContext.getRequest().getSession().getAttribute("userinfo");
     5         if(obj == null){
     6             return "login";
     7         }
     8         return invocation.invoke();//放行
     9     }
    10 
    11 }

    页面:

     1 <html>
     2   <head>
     3     <title>用户登录</title>
     4   </head>
     5   <body>
     6        <form action="${pageContext.request.contextPath}/login.action">
     7            用户名:<input type="text" name="username"/><br/>
     8            <input type="submit" value="登录"/>
     9        </form>
    10   </body>
    11 </html>

    4.2、案例中的问题

    问题:由于我们写了自己的拦截器,默认的拦截器不起作用了。

    解决办法:

    需要通过AbstractInterceptor类的子类入手,通过查看发现,该类还有一个子类是抽象的:

    所以我们在自定义拦截器时,还可以继承MethodFilterInterceptor并且重写doIntercept方法。

     1 public class CheckLoginInterceptorDemo2 extends MethodFilterInterceptor {
     2 
     3     public String doIntercept(ActionInvocation invocation) throws Exception {
     4         Object obj = ServletActionContext.getRequest().getSession().getAttribute("userinfo");
     5         if(obj == null){
     6             return "login";
     7         }
     8         return invocation.invoke();//放行
     9     }
    10 
    11 }

    并且在struts的配置文件中,配置需要拦截哪些方法,和需要放过哪些方法。

    4.3、拦截器类视图(全):

    十三、文件的上传(拦截器)和下载(stream结果类型)

    1、文件上传

    必要前提:

    a.表单method必须是post

    b.enctype取值必须是multipart/form-data

    c.提供文件选择域。

    动作类:

     1 public class UploadAction extends ActionSupport {
     2 
     3     private String username;
     4     private File photo;
     5     //struts2框架会为我们提供一个变量,用于保存文件名。
     6     private String photoFileName;//该变量的命名规则有要求:必须是文件变量的名称+FileName。严格区分大小写。
     7     
     8     
     9     public String upload()throws Exception{
    10         //1.获取文件要写到服务器的位置
    11         String basePath = ServletActionContext.getServletContext().getRealPath("/WEB-INF/uploads");
    12         //2.判断目录是否存在
    13         File file = new File(basePath);
    14         if(!file.exists()){
    15             file.mkdirs();
    16         }
    17         //3.写文件
    18         /*
    19          * 拷贝:是使用临时文件,复制一份到指定目录
    20          * FileUtils
    21          *      它是apache提供commons-io的jar包中一个类。
    22          * copyFile方法:
    23          *       把参数1复制到指定位置,指定位置是由参数2决定的
    24          * 参数:
    25          *      第一个:源文件
    26          *     第二个:目标文件
    27          * 
    28          * 弊端:
    29          *     会保存两份文件,一份是临时文件,一份是实际写的文件
    30          */
    31         //FileUtils.copyFile(photo, new File(file,photoFileName));
    32         /*
    33          * 剪切:是把临时文件重命名后,存到指定目录(一般采用此种方式)
    34          * 比复制的好处就是:只会保留一份文件
    35          */
    36         photo.renameTo(new File(file,photoFileName));
    37         return SUCCESS;
    38     }

    2、文件上传的配置

    2.1、文件上传大小限制(默认是2MB

    如果上传文件超过了默认大小,upload拦截器会转向一个input的逻辑视图。

    改变上传文件大小限制:

    1 <!-- 改变上传文件大小限制的方式:只能用修改常量的方式 -->
    2     <constant name="struts.multipart.maxSize" value="10485760"></constant>

    2.2、限制文件上传的类型

    a、通过限制上传文件的扩展名

       思路:给fileUpload拦截器注入参数

     1 <action name="upload" class="cn.itcast.web.action.UploadAction" method="upload">
     2             <!-- 给上传文件的拦截器注入参数,限制上传文件的大小
     3             此种方式无法限制上传文件的大小
     4             <interceptor-ref name="defaultStack">
     5                 <param name="fileUpload.maximumSize">10485760</param>
     6             </interceptor-ref> -->
     7             <interceptor-ref name="defaultStack">
     8                 <!-- 限制文件的扩展名 -->
     9                 <param name="fileUpload.allowedExtensions">.jpg,.png,.jpeg,.bmp</param>
    10                 <!-- 限制文件的MIME类型 -->
    11                 <param name="fileUpload.allowedTypes">image/jpeg,image/png,image/pjpeg</param>
    12             </interceptor-ref>
    13             <result name="success">/success.jsp</result>
    14             <result name="input">/index.jsp</result>
    15         </action>

    3、文件下载:其实就是一种结果类型(Stream

    动作类:

     1 public String download() throws Exception{
     2         //3.找到要下载文件的路径
     3         String basePath = ServletActionContext.getServletContext().getRealPath("/WEB-INF/uploads");
     4         //4.使用文件路径+文件名称,构建字节输入流
     5         fileName = "4O5A3624.jpg";//实际开发中是从数据库中查出来的
     6         inputStream = new FileInputStream(basePath+File.separator+fileName);
     7         //5、返回一个成功
     8         return SUCCESS;
     9         /*
    10          * 6.剩下的事,都交给struts2框架。是框架的stream的结果类型为我们实现的
    11          * 我们需要给stream结果类型提供参数
    12          *     <result name="success" type="stream">
    13                 <!-- 给结果类型注入参数:两个头 一个流 -->
    14                 <param name="contentType">application/octet-stream</param>
    15                 <param name="contentDisposition">attachment;filename=1.jpg</param>
    16                 <param name="inputStream">inputStream</param>
    17             </result>
    18          */
    19     }

    配置文件:

    1 <action name="download" class="cn.itcast.web.action.DownLoadAction" method="download">
    2             <result name="success" type="stream">
    3                 <!-- 给结果类型注入参数:两个头 一个流 -->
    4                 <param name="contentType">application/octet-stream</param>
    5                 <param name="contentDisposition">attachment;filename=1.jpg</param>
    6                 <param name="inputStream">inputStream</param>
    7             </result>
    8         </action>

    十四、OGNL简介

    1、什么是OGNL

    OGNLObject Graphic Navigation Language(对象图导航语言)的缩写,它是一个单独的开源项目。 Struts2框架使用OGNL作为默认的表达式语言。

    2OGNL的功能

    前提:OGNLstruts2整合的一个开源项目,所以在struts2中,要想使用OGNL表达式,必须使用Struts2标签库

    2.1、支持普通方法的调用

     1   <body>
     2     <%--s:property标签
     3             作用:把该标签中value属性的值所对应的内容输出到浏览器上。
     4             属性:
     5                 value:取值不是一个普通的字符串,而是一个OGNL表达式。
     6                            它是去一个位置查找数据去了,把找到的结果显示出来。
     7     --%>
     8     <s:property value="OGNL-Expression"/><br/>
     9     <%--使用引号,把value的值括起来,取值将变成一个普通的字符串 --%>
    10     <s:property value="'OGNL-Expression'"/><br/>
    11     <%--支持普通方法调用 --%>
    12     <s:property value="'OGNL-Expression'.length()"/><br/>
    13     <s:property value="'OGNL-Expression'.toUpperCase()"/><br/>
    14     <s:property value="'OGNL-Expression'.split('-')[0]"/><hr/>
    15     <%--OGNL还可以访问静态属性 
    16         @包名.包名.类名@属性名称
    17         例如:
    18             @java.lang.Integer@MAX_VALUE
    19     --%>
    20     <s:property value="@java.lang.Integer@MAX_VALUE"/>
    21     <hr/>
    22     <%--OGNL还可以调用静态方法 
    23         @包名.包名.类名@方法名称
    24         例如:
    25             @java.lang.Math@random()
    26     --%>
    27     <s:property value="@java.lang.Math@random()"/>
    28     <hr/>
    29     <%--OGNL操作集合对象
    30         s:radio标签的list属性取值是一个OGNL表达式。
    31         {'男','女'}就相当于创建了一个List集合,里面包含了两个元素
    32      --%>
    33     <s:radio list="{'男','女'}" name="gender" label="性别"></s:radio>
    34     <hr size="50px" color="gray"/>
    35     <%--OGNL操作map对象 
    36         #{'male':'男','female':'女'}就相当于创建了一个map。冒号左侧的作为key,冒号右侧的作为value。
    37         在生成浏览器认识的html标签时:
    38             会把map的key给html标签的value赋值
    39             把map的value作为文本显示在页面上
    40             
    41         例如:
    42         <input type="radio" value="male">43         <input type="radio" value="female">44     --%>
    45     <s:radio list="#{'male':'男','female':'女'}" name="gender" label="性别"></s:radio>
    46   
    47   </body>

    (EL表达式只能调用静态方法)

  • 相关阅读:
    解析大型.NET ERP系统 权限模块设计与实现
    Enterprise Solution 开源项目资源汇总 Visual Studio Online 源代码托管 企业管理软件开发框架
    解析大型.NET ERP系统 单据编码功能实现
    解析大型.NET ERP系统 单据标准(新增,修改,删除,复制,打印)功能程序设计
    Windows 10 部署Enterprise Solution 5.5
    解析大型.NET ERP系统 设计异常处理模块
    解析大型.NET ERP系统 业务逻辑设计与实现
    解析大型.NET ERP系统 多国语言实现
    Enterprise Solution 管理软件开发框架流程实战
    解析大型.NET ERP系统 数据审计功能
  • 原文地址:https://www.cnblogs.com/minihouseCoder/p/5589333.html
Copyright © 2011-2022 走看看