Struts2学习笔记7(OGNL--1)

1、值栈(ValueStack)

Struts2 OGNL上下文设置为Struts2中的ActionContext(内部使用的仍然是OgnlContext),并将值栈设为Struts2 OGNL的根对象。

我们知道,Struts2 OGNL上下文中的根对象可以直接访问,不需要使用任何特殊的“标记”,而引用上下文中的其他对象则需要使用“#”来标记。由于值栈是上下文中的根对象,因此可以直接访问。那么对于值栈中的对象该如何访问呢?Struts2提供了一个特殊的OGNLPropertyAccessor,它可以自动查找栈内的所有对象(从栈顶到栈底),直接找到一个具有你所查找的属性的对象。也就是说,对于值栈中的任何对象都可以直接访问,而不需要使用“#”。

假设值栈中有两个对象:student和employee,两个对象都有name属性,student有学号属性number,而employee有薪水属性salary。employee先入栈,student后入栈,位于栈顶,那么对于表达式name,访问的就是student的name属性,因为student对象位于栈顶;表达式salary,访问的就是employee的salary属性。正如你所见,访问值栈中的对象属性或方法,无须指明对象,也不用“#”,就好像值栈中的对象都是OGNL上下文中的根对象一样。这就是Struts2在OGNL基础上做出的改进。

2、[N]语法

如上所述,如果想要访问employee的name属性,应该如何写表达式呢?我们可以使用[N].xxx(N是从0开始的整数)这样的语法来指定从哪一个位置开始向下查找对象的属性,表达式[1].name访问的就是employee对象的name属性。

在使用[N].xxx语法时,要注意位置序号的含义,它并不是表示“获取栈中索引为N的对象”,而是截取从位置N开始的部分栈。

3、top关键字

top用于获取栈顶的对象,结合[N].xxx语法,我们就可以获取栈中任意位置的对象。

如:[0].top,[1].top等

4、访问静态成员

除了使用标准的OGNL表达式访问静态字段和静态方法外,Struts2还允许你不指定完整的类名,而是通过“vs”前缀来调用保存在栈中的静态字段和静态方法。

@vs@FOO_PROPERTY@vs@someMethod()@vs1@someMethod()

vs表示ValueStack,如果只有vs,那么将使用栈顶对象的类;如果在vs后面跟上一个数字,那么将使用栈中指定位置处的对象类。

标准方法:@类全限定名@静态属性或方法名

< ?xml:namespace prefix = s />< s:property value="@action.SystemInfo@WEB_CONTEXT">< /s:property>

5、值栈中的Action实例

Struts2框架总是把Action实例放在栈顶。因为Action在值栈中,而值栈又是OGNL中的根,所以引用Action的属性可以省略“#”标记,这也是为什么我们在结果页面中可以直接访问Action的属性的原因。

6、Struts2中的命名对象

Struts2还提供了一些命名对象,这些对象没有保存在值栈中,而是保存在ActionContext中,因此访问这些对象需要使用“#”标记。这些命名对象都是Map类型。

parameters

用于访问请求参数。如:#parameters['id']或#parameters.id,相当于调用了HttpServletRequest对象的getParameter()方法。

注意,parameters本质上是一个使用HttpServletRequest对象中的请求参数构造的Map对象,一量对象被创建(在调用Action实例之前就已经创建好了),它和HttpServletRequest对象就没有了任何关系。

request

用于访问请求属性。如:#request['user']或#request.user,相当于调用了HttpServletRequest对象的getAttribute()方法。

session

用于访问session属性。如:#session['user']或#session.user,相当于调用了HttpSession对象的getAttribute()方法。

application

用于访问application属性。如:#application['user']或#application.user,相当于调用了ServletContext的getAttribute()方法。

attr

如果PageContext可用,则访问PageContext,否则依次搜索request、session和application对象。

—    ?:获得所有符合逻辑的元素。

—    ^:获得符合逻辑的第一个元素。

—    $:获得符合逻辑的最后一个元素。

为本示例建立一个业务控制器,该控制器用到了代码8.1中定义的Person人员信息类。该业务控制器如代码8.4所示。

代码8.4  Struts 2OGNL示例业务控制器

package ch8;

import java.util.Date;

import java.util.LinkedList;

import java.util.List;

import javax.servlet.http.HttpServletRequest;

import javax.servlet.http.HttpServletResponse;

import javax.servlet.http.HttpSession;

import org.apache.struts2.ServletActionContext;

import com.opensymphony.xwork2.ActionContext;

import com.opensymphony.xwork2.ActionSupport;

public class OgnlAction extends ActionSupport {

    //List类型属性

    private List<Person> persons;

    //execute方法

    public String execute() throws Exception {

        // 获得ActionContext实例,以便访问Servlet API

        ActionContext ctx = ActionContext.getContext();

        // 存入application

        ctx.getApplication().put("msg", "application信息");

        // 保存session

        ctx.getSession().put("msg", "seesion信息");

        // 保存request信息

        HttpServletRequest request = ServletActionContext.getRequest();

        request.setAttribute("msg", "request信息");

        //为persons赋值

        persons = new LinkedList<Person>();

        Person person1=new Person();

        person1.setName("pla1");

        person1.setAge(26);

        person1.setBirthday(new Date());

          persons.add(person1);

         

          Person person2=new Person();

          person2.setName("pla2");

        person2.setAge(36);

        person2.setBirthday(new Date());

          persons.add(person2);

          Person person3=new Person();

          person3.setName("pla3");

        person3.setAge(16);

        person3.setBirthday(new Date());

          persons.add(person3);

          return SUCCESS;

    }

    public List<Person> getPersons() {

        return persons;

    }

    public void setPersons(List<Person> persons) {

        this.persons = persons;

    }

}

该业务控制器分别在applicationsessionrequest中存入名为“msg”的字符串信息,另外定义了一个List类型属性,同时添加了两个Person类型元素。在配置文件中增加了相应的配置,代码如下:

<action name="OgnlAction" class="ch8.OgnlAction">

        <result name="success">/ch8/showognl.jsp</result>

</action>

8.3.2  JSP视图

showognl.jsp是使用了OGNL表达式的JSP视图,视图用来显示Action中处理的各种信息,读者可以看到,使用OGNL表达式,代码更加简洁和直观,如代码8.5所示。

代码8.5  使用OGNL表达式的JSP视图

<%@ page language="java" contentType="text/html; charset=utf-8" pageEncoding="utf-8" %>

<%@ taglib prefix="s" uri="/struts-tags" %>

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/ xhtml1/DTD/xhtml1-transitional.dtd">

<html xmlns="http://www.w3.org/1999/xhtml">

<head>

    <title>Struts2 OGNL 演示</title>

</head>

<body>   

    <h3>访问OGNL上下文和Action上下文</h3>

    <!-使用OGNL访问属性值-->

    <p>parameters: <s:property value="#parameters.msg" /></p>

    <p>request.msg: <s:property value="#request.msg" /></p>

    <p>session.msg: <s:property value="#session.msg" /></p>

    <p>application.msg: <s:property value="#application.msg" /></p>

    <p>attr.msg: <s:property value="#attr.msg" /></p>

    <hr />

    <h3>用于过滤和投影(projecting)集合</h3>

    <p>年龄大于20</p>

    <ul>

    <!-判断年龄-->

        <s:iterator value="persons.{?#this.age>20}">

            <li><s:property value="name" /> - 年龄:<s:property value="age" /></li>

        </s:iterator>

    </ul>

    <p>姓名为pla1的年龄: <s:property value="persons. {?#this.name=='pla1'} .{age}[0]"/></p>

    <hr />

    <h3>构造Map</h3>

    <s:set name="foobar" value="#{'foo1':'bar1', 'foo2':'bar2'}" />

    <p>The value of key "foo1" is <s:property value="#foobar['foo1']" /></p>

</body>

</html>

8.3.3  运行示例

在浏览器中输入http://localhost:8080/bookcode/ch8/OgnlAction.action?msg=hello,运行结果如图8.3所示。

 

本示例演示了如何使用OGNL表达式来访问OGNL上下文和值栈,同时演示了如何使用OGNL表达式进行集合操作。对读者深入理解Struts 2OGNL表达式的使用有所帮助。

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值