Struts 2的OGNL表达式
來(lái)源:http://www.24xuexi.com/w/2011-04-26/88911.html
Struts 2的OGNL表達(dá)式
標(biāo)準(zhǔn)的OGNL會(huì)設(shè)定一個(gè)根對(duì)象(root對(duì)象)。假設(shè)使用標(biāo)準(zhǔn)OGNL表達(dá)式來(lái)求值(不使用Struts 2的OGNL表達(dá)式),如果OGNL上下文(OgnlContext Map類型)有兩個(gè)對(duì)象:foo對(duì)象,在OgnlContext中名稱為foo;bar對(duì)象,在OgnlContext中名稱為bar。同時(shí)foo對(duì)象被設(shè)置為根對(duì)象(root)。則利用下面的OGNL表達(dá)式求值:
// 返回foo.getBlah()
#foo.blah
//返回bar.getBlah()
#bar.blah
//返回foo.getBlah() ,因?yàn)閒oo為根對(duì)象
blah
★ 說(shuō)明 ★
使用OGNL是非常簡(jiǎn)單的,如果要訪問(wèn)的對(duì)象不是根對(duì)象,如示例中的bar對(duì)象,則需要使用命名空間,用“#”來(lái)標(biāo)識(shí),如“#bar”;如果訪問(wèn)一個(gè)根對(duì)象,則不用指定命名空間,可以直接訪問(wèn)根對(duì)象的屬性。
在Struts 2框架中,值棧(Value Stack)就是OGNL的根對(duì)象,假設(shè)值棧中存在兩個(gè)對(duì)對(duì)象實(shí)例:Man和Animal,這兩個(gè)對(duì)象實(shí)例都有一個(gè)name屬性,Animal有一個(gè)species屬性,Man有一個(gè)salary屬性,假設(shè)Animal在值棧的頂部,Man在Animal后面,下面的代碼片斷會(huì)幫助讀者更好地理解OGNL表達(dá)式:
// 調(diào)用animal.getSpecies()
species
// 調(diào)用man.getSalary()
salary
// 調(diào)用animal.getName(),因?yàn)锳nimal位于值棧的頂部
name
最后一行示例代碼,返回的是animal.getName()返回值,即返回了Animal的name屬性,因?yàn)锳nimal是值棧的頂部元素,OGNL將從頂部元素搜索,所以會(huì)返回Animal的name屬性值。如果要獲得Man的name值,則需要如下代碼:
man.name
Struts 2允許在值棧中使用索引,示例代碼如下所示:
[0].name // 調(diào)用animal.getName()
[1].name // 調(diào)用man.getName()
★ 說(shuō)明注意 ★
使用索引,并不是直接獲得指定的元素,而是從指定的索引位置搜索。
Struts 2中的OGNL Context是ActionContext,如圖8.2所示。
圖8.2 Struts 2的OGNL Context結(jié)構(gòu)示意圖
★ 說(shuō)明 ★
圖8.2只是說(shuō)明Struts 2的OGNL Context結(jié)構(gòu),實(shí)際上Context還包含其他對(duì)象。
由于值棧是Struts 2中OGNL的根對(duì)象,如果用戶需要訪問(wèn)值棧中的對(duì)象,則可以直接通過(guò)下面的代碼訪問(wèn)值棧中的屬性:
//獲得值棧中的foo屬性
${foo}
如果訪問(wèn)其他Context中的對(duì)象,由于不是根對(duì)象,在訪問(wèn)時(shí),需要加#前綴。
― application對(duì)象:用于訪問(wèn)ServletContext,例如#application.userName或者#application['userName'],相當(dāng)于調(diào)用Servlet的getAttribute("username")。
― session對(duì)象:用來(lái)訪問(wèn)HttpSession,例如#session.userName或者#session['userName'],相當(dāng)于調(diào)用session.getAttribute("userName")。
― request對(duì)象:用來(lái)訪問(wèn)HttpServletRequest屬性(attribute)的Map,例如#request.userName或者#request['userName'],相當(dāng)于調(diào)用request.get力Attribute ("userName")。
― parameters對(duì)象:用于訪問(wèn)HTTP的請(qǐng)求參數(shù),例如#parameters.userName或者#parameters['userName'],相當(dāng)于調(diào)用request.getParameter("username")。
― attr對(duì)象:用于按page-request-session-application順序訪問(wèn)其屬性。
8.2.2 OGNL的集合操作如果需要一個(gè)集合元素的時(shí)候(例如List對(duì)象或者M(jìn)ap對(duì)象),可以使用OGNL中同集合相關(guān)的表達(dá)式。
可以使用如下代碼直接生成一個(gè)List對(duì)象:
{e1,e2,e3…}
該OGNL表達(dá)式中,直接生成了一個(gè)List對(duì)象,該List對(duì)象中包含3個(gè)元素:e1、e2和e3。如果需要更多的元素,可以按照這樣的格式定義多個(gè)元素,多個(gè)元素之間使用逗號(hào)隔開。
如下代碼可以直接生成一個(gè)Map對(duì)象:
#{key1:value1,key2:value2,…}
Map類型的集合對(duì)象,使用key-value格式定義,每個(gè)key-value元素使用冒號(hào)標(biāo)識(shí),多個(gè)元素之間使用逗號(hào)隔開。
對(duì)于集合類型,OGNL表達(dá)式可以使用in和not in兩個(gè)元素符號(hào)。其中,in表達(dá)式用來(lái)判斷某個(gè)元素是否在指定的集合對(duì)象中;not in判斷某個(gè)元素是否不在指定的集合對(duì)象中,如代碼8.3所示。
代碼8.3 使用OGNL集合操作符
<s:if test="'foo' in {'foo','bar'}">
muhahaha
</s:if>
<s:else>
boo
</s:else>
<s:if test="'foo' not in {'foo','bar'}">
muhahaha
</s:if>
<s:else>
boo
</s:else>
除了in和not in之外,OGNL還允許使用某個(gè)規(guī)則獲得集合對(duì)象的子集,常用的有以下3個(gè)相關(guān)操作符。
― ?:獲得所有符合邏輯的元素。
― ^:獲得符合邏輯的第一個(gè)元素。
― $:獲得符合邏輯的最后一個(gè)元素。
例如代碼:
person.relatives.{? #this.gender == 'male'}
該代碼可以獲得person的所有性別為male的relatievs集合。
8.2.3 Lambda表達(dá)式OGNL支持基本的Lambda表達(dá)式語(yǔ)法,通過(guò)Lambda表達(dá)式語(yǔ)法,可以在OGNL中使用一些簡(jiǎn)單的函數(shù)。例如:
Fibonacci:
if n==0 return 0;
elseif n==1 return 1;
else return fib(n-2)+fib(n-1);
fib(0) = 0
fib(1) = 1
fib(11) = 89
開發(fā)者可以使用Lambda表達(dá)式語(yǔ)法:
<s:property value="#fib =:[#this==0 ? 0 : #this==1 ? 1 : #fib(#this-2)+#fib(#this-1)], #fib(11)" />
JSP視圖
showognl.jsp是使用了OGNL表達(dá)式的JSP視圖,視圖用來(lái)顯示Action中處理的各種信息,讀者可以看到,使用OGNL表達(dá)式,代碼更加簡(jiǎn)潔和直觀,如代碼8.5所示。
代碼8.5 使用OGNL表達(dá)式的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>訪問(wèn)OGNL上下文和Action上下文</h3>
<!-使用OGNL訪問(wèn)屬性值-->
<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>用于過(guò)濾和投影(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>構(gòu)造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>
OGNL中的#、%和$符號(hào)
#、%和$符號(hào)在OGNL表達(dá)式中經(jīng)常出現(xiàn),而這三種符號(hào)也是開發(fā)者不容易掌握和理解的部分。在這里筆者簡(jiǎn)單介紹它們的相應(yīng)用途。
1.#符號(hào)#符號(hào)的用途一般有三種。
― 訪問(wèn)非根對(duì)象屬性,例如示例中的#session.msg表達(dá)式,由于Struts 2中值棧被視為根對(duì)象,所以訪問(wèn)其他非根對(duì)象時(shí),需要加#前綴。實(shí)際上,#相當(dāng)于ActionContext. getContext();#session.msg表達(dá)式相當(dāng)于ActionContext.getContext().getSession(). getAttribute("msg")。
― 用于過(guò)濾和投影(projecting)集合,如示例中的persons.{?#this.age>20}。
― 用來(lái)構(gòu)造Map,例如示例中的#{'foo1':'bar1','foo2':'bar2'}。
2.%符號(hào)%符號(hào)的用途是在標(biāo)志的屬性為字符串類型時(shí),計(jì)算OGNL表達(dá)式的值。如下面的代碼所示:
<h3>構(gòu)造Map</h3>
<s:set name="foobar" value="#{'foo1':'bar1', 'foo2':'bar2'}" />
<p>The value of key "foo1" is <s:property value="#foobar['foo1']" /></p>
<p>不使用%:<s:url value="#foobar['foo1']" /></p>
<p>使用%:<s:url value="%{#foobar['foo1']}" /></p>
運(yùn)行界面如圖8.4所示。
3.$符號(hào)$符號(hào)主要有兩個(gè)方面的用途。
― 在國(guó)際化資源文件中,引用OGNL表達(dá)式,例如國(guó)際化資源文件中的代碼:reg.agerange=國(guó)際化資源信息:年齡必須在${min}同${max}之間。
― 在Struts 2框架的配置文件中引用OGNL表達(dá)式,例如下面的代碼片斷所示:
<validators>
<field name="intb">
<field-validator type="int">
<param name="min">10</param>
<param name="max">100</param>
<message>BAction-test校驗(yàn):數(shù)字必須為${min}為${max}之間!</message>
</field-validator>
</field>
</validators>
總結(jié)
以上是生活随笔為你收集整理的Struts 2的OGNL表达式的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問(wèn)題。
- 上一篇: DotNetty[通俗易懂]
- 下一篇: CICD简介[通俗易懂]