
OGNL表达式是一种独立的语言,strut2将介绍它来构造struts2.
OGNL语言比EL表达式更强大. 它可以访问java类中的对象以及对象的静态方法.
public class OgnlDemo1 {
@Test
public void test1() throws OgnlException{
OgnlContext context = new OgnlContext();
Object value = Ognl.getValue("'hello OGNL'.length()", context, context.getRoot());
System.out.println(value);
}
@Test
public void test2() throws OgnlException{
OgnlContext context = new OgnlContext();
Object root = context.getRoot();
Object value = Ognl.getValue("@java.lang.Math@random()", context, root);
System.out.println(value);
}
}
java对象(通常写为实体对象)存储在根目录中. 访问Java类中的属性演示:
@Test
public void test3() throws OgnlException{
OgnlContext context = new OgnlContext();
//通过context对象和User的有参构造给root设置值
context.setRoot(new User("aloha","keep moving!"));
//获取root
Object root = context.getRoot();
Object username = Ognl.getValue("username", context, root);
Object password = Ognl.getValue("password", context, root);
System.out.println(username);
System.out.println(password);
}
要获取上下文中的数据,您需要添加#:
@Test
public void test4() throws OgnlException{
OgnlContext context = new OgnlContext();
//往Map集合context中添加键值对
context.put("name", "aloha");
Object name = Ognl.getValue("#name", context, context.getRoot());
System.out.println(name);
}
主要用于: 在页面上获取数据.
首先配置struts2环境,然后配置核心过滤器:
<filter>
<filter-name>struts2</filter-name>
<filter-class>org.apache.struts2.dispatcher.ng.filter.StrutsPrepareAndExecuteFilter</filter-class>
</filter>
<filter-mapping>
<filter-name>struts2</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
在jsp页面中介绍strut2标记库:
<%@ taglib uri="/struts-tags" prefix="s" %>

如何使用ognl表达式访问?
<!-- property表示ognl表达式,value属性中写表达式 -->
<s:property value="'aloha'.length()"/>
注意: 默认情况下,strut2中对静态成员的访问处于关闭状态. struts2-core-2.3.24.jar / org.apache.struts2 / default.properties的第208行中的协议: struts.ognl.allowStaticMethodAccess = false,因此我们可以在struts.xml常量配置中将其打开:
<constant name="struts.ognl.allowStaticMethodAccess" value="true" />
这样,您可以调用静态方法.
什么是值堆栈(ValueStack): 它实际上是一个容器. 当前页面发送请求时,struts的默认会将数据封装在请求中,然后将其合并到ValueStack堆栈的顶部. 相当多的数据传输站(Struts2框架中的数据实际上已保存到ValueStack.
ValueStack是struts的接口,而OgnlValueStack是ValueStack的实现类. 客户端发起一个请求,在struts2体系结构之后创建一个动作实例,并创建一个OgnlValueStack值堆栈实例. 该实例贯穿于Action的整个生命周期. Struts2使用OGNL将Action请求的参数封装为对象并将它们存储在值堆栈中,OGNL表示要在值堆栈中读取对象属性值.
为什么要使用ValueStack?
存储在ValueStack中的数据,我们可以在任何地方将其取出. (页面,操作,配置文件)因此建议将数据存储在值堆栈中.
structs2引用OGNL时未引入源代码ognl 表达式 使用,因此在导入struts2源代码后我们无法查看OGNL的源代码,我们需要再次导入ognl的源代码.
ValueStack中有两个主要区域:

根区域和上下文区域: 根区域是继承ArrayList集合的CompoundRoot类,该类实际上是ArrayList集合,该类实现了推入和弹出堆栈,存储动作实例和请求参数的功能,其中Object是保存;上下文区域OgnlContext类是实现Map集合的Map集合,其键值是对常用Web开发对象的引用.
与ServletContext相比,ActionContext对象是获取操作上下文的对象. 可以通过以下方法获得
struts2-core-2.3.24.jar / StrutsPrepareAndExecuteFilter.class / doFilter(ServletRequest req,ServletResponse res,FilterChain chain)方法,如果要通过过滤器,请执行以下语句: prepare.createActionContext(request,response );
看一下源代码: 有一个逻辑: 如果旧的ActionContext为空,则ValueStack stack = dispatcher.getContainer(). getInstance(ValueStackFactory.class).createValueStack();
这句话创建了一个ValueStack对象.
分析源代码并得出结论:
请求到达时,将执行过滤器中的doFilter方法. 在此方法中,创建了ActionContext. 在创建ActionContext的过程中,将创建ValueStack对象ognl 表达式 使用,然后将ValueStack对象传递给ActionContext. 这就是为什么您可以通过ActionContext获取值堆栈对象的原因.
ValueStack stack = ActionContext.getContext().getValueStack();
1. 通过ActionContext方法,如上面的代码所示.
2. 传递请求. struts2将值堆栈存储在请求中. 如下
ValueStack stack = (ValueStack) ServletActionContext.getRequest().getAttribute(ServletActionContext.STRUTS_VALUESTACK_KEY);
1. 提供属性get方法的方法: (部分代码)默认情况下,数据不存在于堆栈顶部

public class ValueStackDemo3 extends ActionSupport {
//action会被压入值栈中,所以属性也会被压入值栈中,我们只需要提供get方法即可
User user ;
public User getUser() {
return user;
}
@Override
public String execute() throws Exception {
user = new User("mlgg", "213");
return SUCCESS;
}
}
值:
<s:debug></s:debug>
<s:property value="user.username"/>
<s:property value="user.password"/>
2. 使用ValueStack自己的方法(代码的一部分)以这种方式将数据存储在堆栈顶部
public class ValueStackDemo4 extends ActionSupport {
@Override
public String execute() throws Exception {
ValueStack valueStack = ActionContext.getContext().getValueStack();
User user = new User("aloha","keep moving");
//方式一
valueStack.push(user);//压栈
//方式二:这种方式可以压栈,但是在debug标签中显示为null,我们可以手动获取到jsp页面
valueStack.set("zyf", "upup");
return super.execute();
}
}
debug标记的执行结果(在编写第二种方法之前):
您可以看到当前堆栈顶部是User对象的用户名aloha. 目前,我们无法使用user.username方法获取jsp中的值. 我们只能使用以下方法直接获取它:
<s:property value="username"/>
<s:property value="password"/>
<!-- 方法二 -->
<s:property value="zyf"/>
public class ValueStackDemo5 extends ActionSupport {
@Override
public String execute() throws Exception {
//向堆栈中保存数据
User user = new User("java","no.1");
ValueStack valueStack = ActionContext.getContext().getValueStack();
valueStack.push(user);
//向集合中保存数据
List<User> list = new ArrayList<User>();
list.add(new User("python", "to be no.1"));
list.add(new User("javascript", "you don't know me"));
list.add(new User("go", "small King"));
ActionContext.getContext().getValueStack().set("list", list);
//向context中保存数据,这些数据可以在debug标签中找出
ServletActionContext.getRequest().setAttribute("name", "aloha");
ServletActionContext.getRequest().getSession().setAttribute("name", "mlgg");
ServletActionContext.getServletContext().setAttribute("name", "sugarcane");
return super.execute();
}
}
本文来自电脑杂谈,转载请注明本文网址:
http://www.pc-fly.com/a/jisuanjixue/article-259275-1.html
3000多