`
longgangbai
  • 浏览: 7339086 次
  • 性别: Icon_minigender_1
  • 来自: 上海
社区版块
存档分类
最新评论

Struts2和OGNL

 
阅读更多
        OGNL是XWork引入的一个非常有效的数据处理的工具。我们已经了解了OGNL的基本操作和OGNL的内部结构,接下来,我们来看看XWork对OGNL做了什么样的加强,以及OGNL的体系在Struts2中如何运转。

  1. /**  
  2.  * @author Downpour  
  3.  */  
  4. public class User {   
  5.        
  6.     private Integer id;   
  7.        
  8.     private String name;   
  9.        
  10.     private Department department = new Department();   
  11.        
  12.         // setter and getters   
  13. }   
  14.   
  15. //=========================================================================   
  16.   
  17. /**  
  18.  * @author Downpour  
  19.  */  
  20. public class Department {   
  21.        
  22.     private Integer id;   
  23.        
  24.     private String name;   
  25.            
  26.         // setter and getters   
  27. }   
  28.   
  29. //=========================================================================   
  30.   
  31. <form method="post" action="/struts-example/ognl.action">   
  32.     user name: <input type="text" name="user.name" value="downpour" />   
  33.     department name: <input type="text" name="department.name" value="dev" />   
  34.     <input type="submit" value="submit" />   
  35. </form>   
  36.   
  37. //=========================================================================   
  38.   
  39. /**  
  40.  * @author Downpour  
  41.  */  
  42. public class OgnlAction extends ActionSupport {   
  43.   
  44.     private static final Log logger = LogFactory.getLog(OgnlAction.class);   
  45.   
  46.     private User user;   
  47.        
  48.     private Department department;   
  49.        
  50.     /* (non-Javadoc)  
  51.      * @see com.opensymphony.xwork2.ActionSupport#execute()  
  52.      */  
  53.     @Override  
  54.     public String execute() throws Exception {   
  55.         logger.info("user name:" + user.getName());   // -> downpour   
  56.         logger.info("department name:" + department.getName());   // -> dev   
  57.         return super.execute();   
  58.     }   
  59.   
  60.     // setter and getters   
  61. }   
  62.   
  63. //=========================================================================   
  64.   
  65. user name: <s:property value="user.name" />   
  66. department name: <s:property value="department.name" />   
  67.   
  68. //=========================================================================  
我们可以看到在JSP中,form中的元素input等,都使用OGNL的表达式作为name的值。而在form提交时,这些值都会被设置到Action中的Java对象中。而当Action转向到JSP时,Struts2的Tag又可以从Action的Java对象中,通过OGNL进行取值。

在这里,你看不到任何的OGNL的代码级别操作,因为这些都在Struts2内部进行了封装。而这些封装,都是建立在OGNL的基本概念,也就是根对象和上下文环境之上。下面就分别就这两个方面分别进行讲解。

ValueStack —— 对OGNL的加强

细心的读者可能会发现,在上面的例子中,我们使用了不同的表达式,针对Action中的不同的Java对象进行设值。再结合上一讲我们所例举的OGNL的代码操作示例,我们有强烈的理由怀疑,Struts2在内部有可能执行了这样的操作,才使得页面到Action的设值工作顺利完成:
  1. // "user.name" as OGNL expression, action as OGNL Root object   
  2. Ognl.setValue("user.name", action, "downpour");   
  3. Ognl.setValue("department.name", action, "dev");  

如果这个怀疑是正确的,那么我们就能得出这样一个结论:Struts2的Action是OGNL操作的根对象。

这个结论是我们从现象上推出来的,至于它到底正确与否,我们之后可以通过源码分析来进行验证,在这里先卖一个关子,姑且认为它是正确的。不过这个结论对我们来说非常重要,因为这个结论Struts2的Tag,JSTL和Freemarker等表示层元素获取Action中变量的值打下了坚实的基础。

在Struts2(XWork)中,不仅把Action作为OGNL操作的根对象,作为对OGNL的扩展,它还引入了一个ValueStack的概念。这个概念代表了什么呢?还是让我们看看Struts2的Reference怎么说:

Struts2 Reference 写道
The biggest addition that XWork provides on top of OGNL is the support for the ValueStack. While OGNL operates under the assumption there is only one "root", XWork's ValueStack concept requires there be many "roots".


很明显,ValueStack依照它的结构和作用,至少为我们提供两大特性:

1. ValueStack是一个堆栈结构,堆栈中的每个元素对于OGNL操作来说,都被看作是根对象。

2. 由于ValueStack是一个堆栈结构,所以其中的元素都是有序的,对于某个OGNL表达式来说,OGNL将自堆栈顶部开始查找,并返回第一个符合条件的对象元素。


这里我们有必要对第二点啰嗦几句,举个具体的例子来说(这个例子同样摘自Struts2的Reference):如果在ValueStack中有2个对象,分别是“动物”和“人”,这两个对象都具备一个属性,叫做name,而“动物”还有一个属性叫species,“人”还有个属性叫salary。其中,“动物”对象在ValueStack的栈顶,而“人”这个对象在栈底。那么看看下面的OGNL表达式将返回什么?

  1. species    // call to animal.getSpecies()   
  2. salary     // call to person.getSalary()   
  3. name       // call to animal.getName() because animal is on the top  

对于name这个属性,返回的将是“动物”的name,因为“动物”在栈顶,会被先匹配到OGNL的表达式。但是有的时候,你可能需要访问“人”的name属性,怎么办呢?你可以通过下面的方法:

  1. [0].name   // call to animal.getName()   
  2. [1].name   // call to person.getName()  

Struts2中的OGNL上下文环境

有了ValueStack,我们再来仔细研究一下Struts2中OGNL的上下文环境。

Struts2 Reference 写道
The framework sets the OGNL context to be our ActionContext, and the value stack to be the OGNL root object. (The value stack is a set of several objects, but to OGNL it appears to be a single object.) Along with the value stack, the framework places other objects in the ActionContext, including Maps representing the application, session, and request contexts. These objects coexist in the ActionContext, alongside the value stack (our OGNL root)



也就是说,ActionContext是Struts2中OGNL的上下文环境。它维护着一个Map的结构,下面是这个结构的图示:



其中,ValueStack是这个上下文环境中的根对象,而除了这个根对象以外,Struts2还在这个上下文环境中放了许多额外的变量,而这些变量多数都是被XWork封装过的Servlet对象,例如request,session,servletContext(application)等,这些对象都被封装成Map对象,随着ActionContext作用于整个Action执行的生命周期中。

在这里,或许有些读者会提出问题来,为什么好好的Servlet对象要在这里被封装成Map对象呢?我想原因可能有以下两个:

1. 对Struts2的Action彻底屏蔽Servlet容器,从而无需再使用底层Servlet API进行编程。你所面对的,将永远是一个又一个的Java对象。

2. 便于各种View技术,例如JSP,Freemarker,Velocity等对ValueStack中上下文环境,尤其是Servlet对象中的数据进行读取。试想,如果在这里不将HttpServletRequest,HttpSession等Servlet对象转化成Map,那么我们将很难通过OGNL表达式,对这些Servlet对象中的值进行读取。

 

 

分享到:
评论
4 楼 jansel 2010-01-15  
Struts2的性能瓶颈正好恰恰在OGNL上。
3 楼 kjj 2010-01-14  
看看struts2的源码就知道了,抄也抄得坑坑洼洼的!!
抄人文章应该事先说明.........................................
2 楼 longgangbai 2010-01-14  
JArcher 写道
你这文章抄的,@author Downpour  都没删

不好意思,就是Copy,本人仅仅用来分享。
1 楼 JArcher 2010-01-13  
你这文章抄的,@author Downpour  都没删

相关推荐

    Struts2_OGNL

    在掌握Struts2和OGNL的基础上,开发者可以进一步学习Struts2的其他组件和特性,如标签库、异常处理、国际化支持、拦截器机制、输入校验、文件上传和下载等,这些都是构建复杂Web应用不可或缺的组件和功能。

    Struts2 使用OGNL表达式

    Struts2是一个流行的Java web应用程序框架,它极大地简化了MVC(模型-视图-控制器)架构的实现。...如果你想要深入学习Struts2和OGNL,可以参考给出的博客链接,或者查阅官方文档和其他相关的技术资源。

    struts2中的OGNL的源码

    同时,也能让我们理解Struts2框架如何将OGNL与动作类、模型对象和视图组件紧密集成。 通过深入学习OGNL的源码,开发者可以更好地定制和优化Struts2应用,提升性能,增强安全性,并能解决遇到的特定问题。这是一项...

    Struts2 & OGNL

    总结,Struts2和OGNL的结合提供了强大的数据绑定和表达式能力,极大地简化了Java Web开发。然而,理解其内部工作原理,掌握安全最佳实践,是充分利用这个框架并避免潜在问题的关键。通过深入学习和实践,开发者可以...

    struts2_OGNL Demo

    这个项目旨在帮助开发者理解和学习如何在Struts2中使用OGNL来操纵对象和数据。OGNL是Struts2中一个重要的组件,它允许在视图层和控制层之间传递和操作数据。 首先,我们来看`.classpath`、`.mymetadata`、`.project...

    struts2 中 OGNL表达式的使用

    struts2 中 OGNL表达式的使用struts2 中 OGNL表达式的使用

    struts2 ognl用法项目

    在这个“Struts2 OGNL用法项目”中,我们将深入探讨OGNL(Object-Graph Navigation Language),它是Struts2中一个强大的表达式语言,用于在模型对象和视图之间进行数据绑定和表达式计算。 OGNL是Struts2的核心组件...

    很全面的struts2_ognl总结

    OGNL(Object-Graph Navigation Language)是一种基于 Java 的表达式语言,Struts2 框架中使用 OGNL 来访问和操作 ValueStack 中的对象。在 Struts2 中,OGNL 是一个强大的工具,允许开发者访问和操作 ValueStack 中...

    Struts2之Ognl详解案例TextOgnl

    在Struts2中,OGNL(Object-Graph Navigation Language)是一种强大的表达式语言,用于获取和设置对象的属性。这篇博客将深入探讨OGNL在Struts2中的应用,并通过案例"TextOgnl"来展示其工作原理。 一、OGNL的基本...

    struts2 标签 OGNL

    在Struts2中,OGNL被广泛用于访问Action中的属性,以及在视图层(如JSP)中绑定和操作数据。 首先,OGNL使得访问对象属性变得非常直观。它支持点符号(.)和方括号([''])两种方式来访问属性。例如,如果在Action...

    Struts2 ognl中的#、%和$符号用法说明

    总的来说,理解并熟练掌握`#`、`%`和`$`在Struts2和OGNL中的用法,对于有效利用Struts2框架进行开发至关重要。这不仅可以帮助你更好地组织和控制应用程序的行为,还能提高代码的可读性和维护性。在实践中,还需要...

    Struts2核心包ognl-2的源代码

    其中,OGNL(Object-Graph Navigation Language)是Struts2中的一个关键组件,它是一种强大的表达式语言,用于在运行时访问和操作对象的属性。这个压缩包包含的是OGNL的2版本的源代码,这对于理解Struts2框架的工作...

    struts2对Ognl的封装--PropertyAccessor

    "struts2对Ognl的封装--PropertyAccessor"这个主题主要涉及Struts2框架如何处理OGNL表达式,特别是如何通过PropertyAccessor接口来访问和操作对象的属性。 首先,我们来了解什么是OGNL。OGNL是Struts2的核心组件之...

    ognl 源码: struts2 所用的 ognl 包源码

    在 Eclipse 3.4.1 中,你可以使用 OGNL 的源码进行调试和学习,这对于理解 OGNL 的工作原理和优化 Struts2 应用程序非常有帮助。你可以设置源码路径,以便在遇到 OGNL 相关的错误时查看其内部实现。 总的来说,...

    struts2 ognl的用法

    ### Struts2中OGNL的使用详解 #### 一、OGNL简介 OGNL(Object-Graph Navigation Language)是一种强大的表达式...通过本文对OGNL在Struts2中的应用场景和使用技巧的介绍,希望能帮助开发者更好地利用这一强大工具。

    struts2-OGNL表达式测试

    在Struts2中,OGNL(Object-Graph Navigation Language)是一种强大的表达式语言,用于访问和操作对象图。这个“struts2-OGNL表达式测试”可能是一个测试项目或代码示例,旨在演示如何在Struts2应用中使用OGNL表达式...

    STRUTS2+ognl

    Ognl(Object-Graph Navigation Language)是Struts2中的一个重要组件,用于在视图层和模型层之间传递数据。本文将详细介绍Struts2、Webwork以及Ognl的相关知识点,并提供入门指导。 **Struts2框架** Struts2是在...

    Struts 2中的OGNL .rar

    以下是一些关于Struts 2和OGNL的关键知识点: 1. **OGNL表达式**:OGNL表达式可以访问对象的属性,包括方法调用、索引访问、集合和映射操作。例如,`person.name`可以获取`person`对象的`name`属性,而`list[0]`...

Global site tag (gtag.js) - Google Analytics