struts2学习三 拦截器和ognl表达式

一,拦截器的生命周期

项目启动:创建拦截器对象->调用init方法
访问:创建action对象->执行拦截器intercept方法(放行之前)->放行(actionInvocation.invoke();)->执行antion业务方法
1)先构造拦截器对象还是Action对象:拦截器
2)先走拦截器的intercept业务方法,再走Action的业务方法

二,拦截器范围

1)局部使用
<package name="intercepter" extends="struts-default">
        <!--定义拦截器-->
        <interceptors>
            <interceptor name="inter1" class="study.intercepter.MyIntercepter"></interceptor>
        </interceptors>
        <action name="user" class="study.intercepter.UserAction" method="login">
            <!--使用自定义局部拦截器-->
            <!--<interceptor-ref name="inter1"></interceptor-ref>-->
            <result name="success" type="dispatcher">/index.jsp</result>
        </action>
    </package>
2)全局使用
1>不使用拦截器栈(会覆盖父包(struts-default)的全部拦截器使其失效)
<package name="intercepter" extends="struts-default">
        <!--定义拦截器-->
        <interceptors>
            <interceptor name="inter1" class="study.intercepter.MyIntercepter"></interceptor>
        </interceptors>
        <!--定义全局拦截器-->
        <default-interceptor-ref name="inter1"></default-interceptor-ref>
        <action name="user" class="study.intercepter.UserAction" method="login">
            <result name="success" type="dispatcher">/index.jsp</result>
        </action>
    </package>
2>使用拦截器栈(把父包的18个拦截器加进去就解决了覆盖问题)
<!--定义拦截器-->
        <interceptors>
            <interceptor name="inter1" class="study.intercepter.MyIntercepter"></interceptor>
            <interceptor name="inter2" class="study.intercepter.MyIntercepter2"></interceptor>
            <!--定义拦截器栈-->
            <interceptor-stack name="mystack">
                <interceptor-ref name="inter1"></interceptor-ref>
                <interceptor-ref name="inter2"></interceptor-ref>
                <!--这里把父包默认的18个拦截器加进去-->
                <interceptor-ref name="defaultStack"></interceptor-ref>
            </interceptor-stack>
        </interceptors>

拦截器栈中拦截器执行顺序
启动时:按照栈中声明顺序执行
调用antion 时:放行前按启动循序执行拦截器->放行后先执行Action中业务方法->然后反过来执行拦截器中放行后的代码

三,值栈

1)ognl表达式

ognl表达式是struts默认使用的表达式语言

2)ognl和el的区别

ognl表达式:获取域对象数据,可以存放数据,可以调用方法
el表达式:获取域对象数据,不能存放数据,不能调用方法

3)ognl表达式核心(OgnlContext对象)

ognlContext存取数据

public class OgnlDemo1 {
    //往根对象存数据
    @Test
    public void test2(){
        User user=new User();
        user.setUsername("tom");
        user.setPassword("123");
        try {
            //创建ognlcontext对象
            OgnlContext ognlContext=new OgnlContext();
            ognlContext.setRoot(user);
            //使用ognl表达式从OgnlContext中取数据,如果是根对象,不用带上#和对象名
            Object object=Ognl.parseExpression("username");
            String name=(String )Ognl.getValue(object,ognlContext,ognlContext.getRoot());
            System.out.println(name);
        } catch (OgnlException e) {
            e.printStackTrace();
        }

    }
    //往非根对象存数据
    @Test
    public void test1(){
        User user=new User();
        user.setUsername("tom");
        user.setPassword("123");
        try {
            //创建ognlcontext对象
            OgnlContext ognlContext=new OgnlContext();
            ognlContext.put("user",user);
            //使用ognl表达式从OgnlContext中取数据,如果是非根对象,必须带上#
            Object object=Ognl.parseExpression("#user.username");
            String name=(String )Ognl.getValue(object,ognlContext,ognlContext.getRoot());
            System.out.println(name);
        } catch (OgnlException e) {
            e.printStackTrace();
        }
    }
4)struts2的值栈(ValueStack)对象(利用OgnlContext对象)

ValueStack是接口,真正的实现对象是OgnlValueStack

1>valueStack的数据存储结构:分为List(根)栈 和 map(非根)栈

list栈:主要存放action对象和provider代理对象
map栈:存放各个域存放的数据和用户的参数信息

public class OgnlDemo2 {
    @Test
    public void test(){
        //获取ActionContext对象
        ActionContext actionContext=ActionContext.getContext();
        //往域对象存放数据
        actionContext.getContextMap().put("hello","hello");
        actionContext.getSession().put("hi","hi");
        actionContext.getApplication().put("sawadika","sawadika");
        //从antionContext中获取OgnlValueStack对象
        ValueStack valueStack=actionContext.getValueStack();
        //往valueStack的根对象(list栈)中存放数据
        valueStack.push("heiheihei");
    }
}
5)页面获取值栈valueStack数据

List栈的数据(不需要#号,不需要key)
输入Ognl: user
作用: 直接到List栈的每个对象去搜索对应的属性。
搜索规则:
从List栈的栈顶开始搜素 -> user -> 返回,找不到继续向下找
栈的第二个元素 -> user -> 返回,找不到继续向下找
… -> user - > 空
注意:在List栈中尽量不要在两个栈对象中出现相应的属性名,如果出现相应的属性名,只获取第一个对象的属性。
jsp页面取数据时需要<%@ taglib prefix="s" uri="/struts-tags" %>标签

<body>
<%--查看值栈所有数据--%>
<s:debug></s:debug>
<%--取出list栈中的数据s:property可以支持ognl表达式--%>
<s:property value="user.name"/>
<%--user对象嵌套book对象--%>
<s:property value="user.book.id"/>
<%--去除map栈中的数据--%>
<%--对于request域可以忽略#request直接去对象,因为值栈对象是通过request域传递到页面的--%>
<s:property value="#request.user.name"/>
<s:property value="user.name"/>
<s:property value="#session.user.name"/>
<s:property value="#application.user.name"/>
<%--#attr类似于findAttribute依次从小到大三个域中取对象--%>
<s:property value="#attr.user"/>
<%--#parameters是获取的参数(url中携带的才叫参数,user是属性不是参数)--%>
<s:property value="#parameters.name"/>
</body>
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值