OGNL和标签库

转载 2018年04月16日 15:35:37

一、前言

OGNL和标签库的作用,粗暴一点说,就是减少在JSP页面中出现java代码,利于维护。

1.1、OGNL

1.1.1、什么是OGNL?

OGNL(Object-Graph Navigation Language):对象图形导航语言,是一种功能强大的表达式语言,通过简单的语法,就能够任意存取对象的属性或者调用对象的方法,能够遍历整个对象的结构图,实现对象属性的类型转换功能。

1.1.2、OGNL的基本知识

1.OGNL表达式的计算是围绕OGNL上下文进行的

OGNL上下文实际上就是一个Map对象,由ognl.OgnlContext类表示。它里面可以存放很多个JavaBean对象。

它有一个上下文根对象。上下文中的根对象可以直接使用名来访问或直接使用它的属性名访问它的属性值。否则要加前缀“#key”。

2.Struts2的标签库都是使用OGNL表达式来访问ActionContext中的对象数据的。如:<s:propertyvalue="xxx"/>。

3.Struts2将ActionContext设置为OGNL上下文,并将值栈作为OGNL的根对象放置到ActionContext中。

4.值栈(ValueStack) :

可以在值栈中放入、删除、查询对象。访问值栈中的对象不用“#”。

Struts2总是把当前Action实例放置在栈顶。所以在OGNL中引用Action中的属性也可以省略“#”。

5.调用ActionContext的put(key,value)放入的数据,需要使用#访问。

OGNL上下文存储图

1.1.3、OGNL中有三个重要的符号:#、%、$

"#"符号的用途:

1、访问非根对象,例如#session.msg表达式,由于Struts 2中值栈被视为根对象,所以访问其他非根对象时,需要加#前缀。实际上,#相当于ActionContext. getContext();#session.msg表达式相当于ActionContext.getContext().getSession(). getAttribute("msg") 。

2、用于过滤和投影(projecting)集合,如persons.{?#this.age>25}.{age},persons.{?#this.name=='pla1'}.{age}[0]。(persons:表示存放在内含对象的值。其中问号?是把所有满足条件的元素都取出来。)

3、构造Map和List

"%"符号的用途:

"%"符号的用途是在标签的属性值被理解为字符串类型时,告诉执行环境%{}里的是OGNL表达式。(等下例子有介绍)

"$"符号的用途:

1、在国际化资源文件中,引用OGNL表达式,例如国际化资源文件中的代码:reg.agerange=国际化资源信息:年龄必须在${min}同${max}之间。

2、在struts.xml中引用OGNL表达式,如:

下面通过例子来进行说明:

新建jsp页面:

复制代码
<%@page import="java.util.LinkedList"%>
<%@page import="java.util.List"%>
<%@page import="com.Ogml.Persons"%>
<%@page import="org.apache.struts2.ServletActionContext"%>
<%@page import="com.opensymphony.xwork2.ActionContext"%>
<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<%@ taglib uri="/struts-tags" prefix="s"%>    
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>学习OGNL</title>
</head>
<body>
    <%
        ActionContext ctx = ActionContext.getContext();
        ctx.getApplication().put("msg", "application消息");
        ctx.getSession().put("msg","session消息");
        ctx.getParameters().put("msg", "parameters消息");
        
        HttpServletRequest re = ServletActionContext.getRequest();
        re.setAttribute("msg", "request消息");
    %>
    
    <!-- 使用OGNL访问属性值 -->
    <!--OGNL中的#号可以取出堆栈上下文中存放的对象  -->
    <p>parameters:<s:property value="#parameters.msg"/></p>
    <p>Application:<s:property value="#application.msg"/></p>
    <p>session:<s:property value="#session.msg"/></p>
    <p>request:<s:property value="#request.msg"/></p>
    <!-- 使用attr:表示它会自动从request-session-applicatioin中寻找,如果找到则返回 -->
    <p>attr:<s:property value="#attr.msg"/></p>
    
    <!--使用OGNL处理集合List,Map-->
    <p>使用List集合:<s:select name="color" list="{'red','yellow','green'}" /></p>
    <p>使用Map集合:
    <s:set var="colors" value="#{'color1':'yellow' }"/>
    <s:property value="#colors['color1']"/></p>
    
    <!-- 不使用%输出结果是:#colors['color1'] -->
    <p>不使用%:<s:url value="#colors['color1']"/></p>
    <!-- “%”符号的用途是在标签的属性值被理解为字符串类型时,告诉执行环境%{}里的是OGNL表达式。  -->
    <p>使用%:<s:url value="%{#colors['color1']}"/></p>
    
    <!-- 过滤和投影(projecting) -->
    <%    
        Persons p1 = new Persons();
        p1.setUname("lisi");
        p1.setAge(36);

     
        application.setAttribute("p", p1);
    %>
    <!-- 问号?是把所有满足条件的元素都取出来。 -->
    <!-- {?#this.age>20}表示的是:获取当前对象的属性,这是一个表达式,如果是true的话,则后面查询的值会输出。false则不会 -->
    <p>使用?#:<s:property value="#application.p.{?#this.age>20}.{uname}"/></p>
    <!-- 输出的是[lisi],有中括号的表示这是一个列表 -->
    
    <!-- 上箭头^是开始的意思,即取符合条件的数据索引中第一条数据 -->
    <p>使用^#:<s:property value="#application.p.{^#this.age>20}.{age}[0]"/></p>
    <!-- 输出的是36,没有中括号,表示这个一个字符串 -->
    
    <!-- 前提必须在strtus.xml中添加
    <constant name="struts.ognl.allowStaticMethodAccess" value="true"></constant> -->
    <!-- 使用@访问静态方法 -->
    <s:property value="@com.Ogml.Persons@sayhello()"/>
    <!-- 使用@访问静态属性 -->
    <s:property value="@com.Ogml.Persons@sex"/><br/>
    
</body>
</html>
复制代码

例子中有使用到^、@符号:

^符号表示的是去符合条件的第一条数据

@符号表示调用类的静态方法或者属性

另外还有美元符号$是结束的意思,即取符合条件的数据索引中最后一条数据,如:

#application.p.{$#this.age>=60}.{uname}输出的是[zhangsan]。

注意:如果使用OGNL要调用静态方法(但是据说Struts2最新版本不允许使用静态方法了,好像说是安全问题。有兴趣可以自己试下)或者静态属性的时候,struts.xml一定要配置:

<constant name="struts.ognl.allowStaticMethodAccess" value="true"></constant>,该语句,不然无法调用。如下:

persons类代码如下:

 Persons

仅作为笔记记录。

1.2、标签库

 笔者对于标签库这些,真的不太感兴趣。但是没办法,还是的学着,发下牢骚。

1.2.1、标签库的好处

在Struts2中,它提供了大量的标签来生成页面效果,简单说来就是使用标签库中为我们提供的标签来达到我们想过的页面效果。而且标签库的使用非常简单,struts2把所有的标签都定义在URI为"/struts-tags"的命名空间下,我们只需要在页面中引入:<%@ taglib uri="/struts-tags" prefix="s"%>,就可以使用该标签库。

1.2.2、标签库的简单分类

UI标签:主要用于生产HTML元素的标签

非UI标签:主要用户数据访问,逻辑控制标签等

Ajax标签:用户Ajax支持的标签

对于UI标签,则可以分为两类:

1、表单标签:主要生成HTML页面的form元素以及普通标签元素

2、非表单标签:主要用于生成页面上的数据,tag页等标签

非UI标签,也可以分为两类:

1、流程控制标签:主要用于实现分支,循环等流程控制的标签

2、数据访问标签:主要包含输出valueStack中的值,完成国际化等功能的标签

这样就清晰多了。

Struts2中的OGNL详解(和标签库一起使用)

首先了解下OGNL的概念: OGNL是Object-Graph Navigation Language的缩写,全称为对象图导航语言,是一种功能强大的表达式语言,它通过简单一致的语法,可以任意存取...
  • u011001084
  • u011001084
  • 2015-12-16 20:01:53
  • 1039

Struts标签库结合OGNL的使用

1.OGNL:object graph navigation language(对象图导航语言),一般是和Struts标签库结合使用。 2.值栈:ValueStack,是对应每一个请求对象的轻量级的内...
  • HLoach
  • HLoach
  • 2017-03-06 17:25:12
  • 612

ognl一些常用标签库

JSTL 里有一组fn(函数)标签 : JSTL 1.1 新增函数(functions)标签库,主要提供一些好用的字符串处理函数,例如:  fn:contains、fn:containsIgn...
  • yeliang0616
  • yeliang0616
  • 2013-12-09 10:48:48
  • 573

OGNL API文档

  • 2017年03月19日 13:42
  • 308KB
  • 下载

struts2中ognl标签详解

if语句 60}"> 老年人 35}"> 中年人 15}"> 青年人 少年 ...
  • u012959829
  • u012959829
  • 2014-07-10 14:45:12
  • 1273

Struts2学习总结(3)--值栈,Ognl表达式,Struts标签库,国际化,数据校验,拦截器

本文包括以下五个部分: 1. 值栈。 2. Ognl表达式。 3. struts2标签库。 4. 国际化。 5. 表单数据校验 6. 拦截器。 ...
  • qq_29829081
  • qq_29829081
  • 2016-03-28 10:56:08
  • 2535

Struts2的标签库及OGNL表达式语言

  • 2007年09月11日 11:33
  • 44KB
  • 下载

人生第一篇博客,求支持。 对EL表达式和JSTL标签库和OGNL表达式的了解

对EL表达式、JSTL标签库、还有OGNL表达式语言进行了描述。
  • sinat_23622505
  • sinat_23622505
  • 2015-12-22 18:40:54
  • 850

struts2框架下-使用OGNL在jsp页面使用<s:set>标签时报错的解决方法

在使用struts2框架的ONGL表达式写前台页面时,需要使用标签在request作用域中定义一个list集合,但当时使用的语法为: 此时页面报错,且启动Tomcat时,报错。报错信息如下: Ac...
  • shen_xy
  • shen_xy
  • 2018-01-31 09:12:47
  • 137

Struts2的标签显示日期、<s:debug>标签、<s:property>使用技巧

原文地址:http://kingxss.iteye.com/blog/1564774 下文会提到ValueStack和Stack Contex,关于这两个值域的具体比较可以参考 蚊香无敌的BLOG:...
  • xing_sky
  • xing_sky
  • 2012-11-30 10:48:55
  • 4723
收藏助手
不良信息举报
您举报文章:OGNL和标签库
举报原因:
原因补充:

(最多只允许输入30个字)