• Struts2学习第七课 OGNL


    request变成了struts重写的StrutsRequestWrapper

    关于值栈:

    helloWorld时,${productName}读取productName值,实际上该属性并不在request等域中,而是从值栈中获取的。

    ValueStack:

    可以从ActionContext中获取值栈对象

    值栈分为两个逻辑部分:

    1.Map栈:实际上是OgnlContext类型,是个Map,也是对ApplicationContext的一个引用,里边保存着各种Map,requestMap,sessionMap,applicationMap,parametersMap,attr

    2.对象栈:实际上是CompoundRoot类型,是一个使用ArrayList定义的栈。里面保存各种和当前Action实例相关的对象。是一个数据结构意义的栈。

    OGNL(Object-Graph Navigation Language,对象-图导航语言)访问到值栈(ValueStack)里的对象属性。

    如果希望访问值栈中ContextMap中的数据,需要给OGNL表达式加上一个前缀字符#。如果没有前缀字符#,搜索将在ObjectStack里进行。

    struts2利用s:property标签和OGNL表达式来读取值栈中的属性值

    值栈中的属性值:

    对于对象栈:对象栈中某一个对象的属性值

    Map栈:request,session,application的一个属性值或者一个请求参数的值。

    读取ObjectStack里的对象的属性

    弱项访问ObjectStack里的某个对象的属性,可以使用一下几种方式之一:

    object.propertyName

    object['propertyName']

    object["propertyName"]

    ObjectStack里的对象可以通过一个从0开始的下标来引用

    ObjectStack里的暂定对象可以用[0]来引用,它下面的那个对象可以用[1]引用,若希望返回栈顶对象的message属性值:[0].message或者[0]["message"]或者[0]['message']

    若在指定的对象里没有找到指定的属性,则到指定的最想的下一个对象里继续找,即[n]的含义是从n个开始搜索,而不是执手锁第n个对象。

    若从栈顶对象开始搜索,则可以省略下标部分。

    默认情况下,Action对象会被struts2自动的放到值栈的栈顶。

    看代码:

    package logan.struts.study;
    
    import com.opensymphony.xwork2.ActionContext;
    import com.opensymphony.xwork2.util.ValueStack;
    
    public class Product {
        
        private Integer productId;
        private String productName;
        private String productDesc;
        
        private double productPrice;
    
        public Integer getProductId() {
            return productId;
        }
    
        public void setProductId(Integer productId) {
            this.productId = productId;
        }
    
        public String getProductName() {
            return productName;
        }
    
        public void setProductName(String productName) {
            this.productName = productName;
        }
    
        public String getProductDesc() {
            return productDesc;
        }
    
        public void setProductDesc(String productDesc) {
            this.productDesc = productDesc;
        }
    
        public double getProductPrice() {
            return productPrice;
        }
    
        public void setProductPrice(double productPrice) {
            this.productPrice = productPrice;
        }
    
        @Override
        public String toString() {
            return "Product [productId=" + productId + ", productName=" + productName + ", productDesc=" + productDesc
                    + ", productPrice=" + productPrice + "]";
        }
        
        public String save(){
            System.out.println("save: " + this);
            
            ValueStack valueStack = ActionContext.getContext().getValueStack();
            Test test = new Test();
            
            test.setProductDesc("AABBCCDD");
            test.setProductName("ABCD");
            valueStack.push(test);
            
            
            return "success";
        }
    }
    package logan.struts.study;
    
    public class Test {
        
        private String productName;
        private String productDesc;
        public String getProductName() {
            return productName;
        }
        public void setProductName(String productName) {
            this.productName = productName;
        }
        public String getProductDesc() {
            return productDesc;
        }
        public void setProductDesc(String productDesc) {
            this.productDesc = productDesc;
        }
        
    
    }

    struts.xml

    <?xml version="1.0" encoding="UTF-8" ?>
    <!DOCTYPE struts PUBLIC
        "-//Apache Software Foundation//DTD Struts Configuration 2.3//EN"
        "http://struts.apache.org/dtds/struts-2.3.dtd">
    
    <struts>
        
        <package name="default" namespace="/" extends="struts-default">
            <action name="product-save" class="logan.struts.study.Product" method="save">
                <result>/details.jsp</result>
            </action>
            
            
        
        </package>
        
        
    </struts>

    web.xml

    <?xml version="1.0" encoding="UTF-8"?>
    <web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://xmlns.jcp.org/xml/ns/javaee" xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_3_1.xsd" id="WebApp_ID" version="3.1">
      <display-name>struts2-5</display-name>
      <filter>
          <filter-name>struts2</filter-name>
          <filter-class>org.apache.struts2.dispatcher.filter.StrutsPrepareAndExecuteFilter</filter-class>
      </filter>
      
      <filter-mapping>
          <filter-name>struts2</filter-name>
          <url-pattern>/*</url-pattern>
      </filter-mapping>
      
      <welcome-file-list>
          <welcome-file>index.html</welcome-file>
      </welcome-file-list>
    </web-app>

    details.jsp

    <%@ page language="java" contentType="text/html; charset=ISO-8859-1"
        pageEncoding="ISO-8859-1"%>
    <%@taglib prefix="s" uri="/struts-tags"%>
    <!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=ISO-8859-1">
    <title>Insert title here</title>
    </head>
    <body>
            <s:debug></s:debug>
            productId:${productId }
            <br><br>
            productName:${productName }
            <br><br>
            productDesc:${productDesc }
            <br><br>
            productPrice:${productPrice }
            <br><br>
            productPrice:<s:property value="productPrice"/>
            <br><br>
            <%=request %>
    </body>
    </html>

    input.jsp

    <%@ page language="java" contentType="text/html; charset=ISO-8859-1"
        pageEncoding="ISO-8859-1"%>
    <!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=ISO-8859-1">
    <title>Insert title here</title>
    </head>
    <body>
        <form action="product-save.action" method="post">
        ProductName:<input type="text" name="productName">
        <br><br>
        ProductDesc:<input type="text" name="productDesc">
        <br><br>
        ProductPrice:<input type="text" name="productPrice">
        <br><br>
        <input type="submit" value="Submit">
        <br><br>
        </form>
    
    </body>
    </html>

     读取Context Map里的对象属性

    如果想访问ContextMap里的某个对象的属性,可以用一下几种形式之一:

    #object.propertyName

    #object['propertyName']

    #object["propertyName"]

    示例:

    --返回session中的code属性:#session.code

    --返回request中的customer属性的name属性值:#request.cuntomer.name

    --返回域对象(按request,session,application的顺序)的lastAccessDate属性:#attr.lastAccessDate

    看代码:

    package logan.struts.study;
    
    import java.util.Map;
    
    import org.apache.struts2.interceptor.RequestAware;
    import org.apache.struts2.interceptor.SessionAware;
    
    import com.opensymphony.xwork2.ActionContext;
    import com.opensymphony.xwork2.util.ValueStack;
    
    public class Product implements RequestAware,SessionAware{
        
        private Integer productId;
        private String productName;
        private String productDesc;
        
        private double productPrice;
    
        public Integer getProductId() {
            return productId;
        }
    
        public void setProductId(Integer productId) {
            this.productId = productId;
        }
    
        public String getProductName() {
            return productName;
        }
    
        public void setProductName(String productName) {
            this.productName = productName;
        }
    
        public String getProductDesc() {
            return productDesc;
        }
    
        public void setProductDesc(String productDesc) {
            this.productDesc = productDesc;
        }
    
        public double getProductPrice() {
            return productPrice;
        }
    
        public void setProductPrice(double productPrice) {
            this.productPrice = productPrice;
        }
    
        @Override
        public String toString() {
            return "Product [productId=" + productId + ", productName=" + productName + ", productDesc=" + productDesc
                    + ", productPrice=" + productPrice + "]";
        }
        
        public String save(){
            System.out.println("save: " + this);
            
            ValueStack valueStack = ActionContext.getContext().getValueStack();
            Test test = new Test();
            
            test.setProductDesc("AABBCCDD");
            test.setProductName("ABCD");
            valueStack.push(test);
            
            session.put("product", this);
            
            request.put("test", test);
            
            
            return "success";
        }
        
        private Map<String, Object> session;
        private Map<String, Object> request;
    
        @Override
        public void setSession(Map<String, Object> session) {
            // TODO Auto-generated method stub
            this.session = session;
            
        }
    
        @Override
        public void setRequest(Map<String, Object> request) {
            // TODO Auto-generated method stub
            this.request = request;
            
        }
    }
    package logan.struts.study;
    
    public class Test {
        
        private String productName;
        private String productDesc;
        public String getProductName() {
            return productName;
        }
        public void setProductName(String productName) {
            this.productName = productName;
        }
        public String getProductDesc() {
            return productDesc;
        }
        public void setProductDesc(String productDesc) {
            this.productDesc = productDesc;
        }
        
    
    }

    dateils.jsp

    <%@ page language="java" contentType="text/html; charset=ISO-8859-1"
        pageEncoding="ISO-8859-1"%>
    <%@taglib prefix="s" uri="/struts-tags"%>
    <!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=ISO-8859-1">
    <title>Insert title here</title>
    </head>
    <body>
            <s:debug></s:debug>
            productId:${productId }
            <br><br>
            productName:${productName }
            <br><br>
            productDesc:${productDesc }
            <br><br>
            productPrice:${productPrice }
            <br><br>
            productPrice:<s:property value="productPrice"/>
            <br><br>
            productName1:${sessionScope.product.productName }
            <br><br>
            productName1.1:<s:property value="#session.product.productName"/>
            <br><br>
            productName2:${requestScope.test.productName }
            <br><br>
            productName2.1:<s:property value="#request.test.productName"/>
            <br><br>
            
    </body>
    </html>

    调用字段和方法

    可以利用OGNL调用:

    --任何一个Java类里面的静态字段或者方法。

    --被压入到ValueStack栈的对象上的公共字段和方法

    默认情况下,struts2不允许调用任意Java类静态方法,需要重新设置struts.ognl.allowStaticMethodAccess标记变量的值为true.

    调用静态字段或者方法需要使用如下所示的语法:

    --@fullyQualifiedClassName@fieldName;

    @java.util.Calendar@DECEMBER

    --@fullyQualifiedClassNAme@methodName(argumentList):

    @app4.Util@now()

    调用一个实例字段或者方法的语法,其中object是Object Stack栈里面的某个对象的引用:

    --.object.fieldName:[0].dataPattern

    --.object.methodName(argumentList):[0].repeat(3,"Hello");

    看代码:

    details.jsp

    <%@ page language="java" contentType="text/html; charset=ISO-8859-1"
        pageEncoding="ISO-8859-1"%>
    <%@taglib prefix="s" uri="/struts-tags"%>
    <!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=ISO-8859-1">
    <title>Insert title here</title>
    </head>
    <body>
            <s:debug></s:debug>
            productId:${productId }
            <br><br>
            productName:${productName }
            <br><br>
            productDesc:${productDesc }
            <br><br>
            productPrice:${productPrice }
            <br><br>
            productPrice:<s:property value="productPrice"/>
            <br><br>
            productName1:${sessionScope.product.productName }
            <br><br>
            productName1.1:<s:property value="#session.product.productName"/>
            <br><br>
            productName2:${requestScope.test.productName }
            <br><br>
            productName2.1:<s:property value="#request.test.productName"/>
            <br><br>
            <!-- 使用 OGNL 调用public 类的public类型的静态字段和静态方法 -->
            <s:property value="@java.lang.Math@PI"/>
            <br><br>
            <s:property value="@java.lang.Math@cos(0)"/>
            <br><br>
            <!-- 调用对象栈的方法为一个属性赋值 -->
            <s:property value="setProductName('logan')"/>
            <br><br>
            <s:property value="productName"/>
            
    </body>
    </html>

    struts.xml

    <?xml version="1.0" encoding="UTF-8" ?>
    <!DOCTYPE struts PUBLIC
        "-//Apache Software Foundation//DTD Struts Configuration 2.3//EN"
        "http://struts.apache.org/dtds/struts-2.3.dtd">
    
    <struts>
    
        <!-- 打开静态方法调用的限制 -->
        <constant name="struts.ognl.allowStaticMethodAccess" value="true"></constant>
        <package name="default" namespace="/" extends="struts-default">
            <action name="product-save" class="logan.struts.study.Product" method="save">
                <result>/details.jsp</result>
            </action>
            
            
        
        </package>
        
        
    </struts>

    访问数组类型的属性

    有些属性将返回一个对象数组而不是单个对象,可以像读取任何其他对象属性那样读取他们。这种数组型属性的各个元素以都好分隔,并且不再方括号

    可以使用下标访问数组中指定的元素:colors[0]

    可以通过调用其length字段查出给定数组中有多少个元素:colors.length

    看代码:

    <%@ page language="java" contentType="text/html; charset=ISO-8859-1"
        pageEncoding="ISO-8859-1"%>
    <%@taglib prefix="s" uri="/struts-tags"%>
    <!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=ISO-8859-1">
    <title>Insert title here</title>
    </head>
    <body>
            <s:debug></s:debug>
            productId:${productId }
            <br><br>
            productName:${productName }
            <br><br>
            productDesc:${productDesc }
            <br><br>
            productPrice:${productPrice }
            <br><br>
            productPrice:<s:property value="productPrice"/>
            <br><br>
            productName1:${sessionScope.product.productName }
            <br><br>
            productName1.1:<s:property value="#session.product.productName"/>
            <br><br>
            productName2:${requestScope.test.productName }
            <br><br>
            productName2.1:<s:property value="#request.test.productName"/>
            <br><br>
            <!-- 使用 OGNL 调用public 类的public类型的静态字段和静态方法 -->
            <s:property value="@java.lang.Math@PI"/>
            <br><br>
            <s:property value="@java.lang.Math@cos(0)"/>
            <br><br>
            <!-- 调用对象栈的方法为一个属性赋值 -->
            <s:property value="setProductName('logan')"/>
            <br><br>
            <s:property value="productName"/>
            <br><br>
            <%
                String [] names = new String[]{"aa","bb","cc","dd"};
                request.setAttribute("names", names);
            %>
            length: <s:property value="#attr.names.length"/>
            <br><br>
            names[2]:<s:property value="#attr.names[2]"/>
            
    </body>
    </html>

    访问List类型的属性

    有些属性将返回的类型是java.util.List,可以像读取任何其他属性那样读取他们,这种List的各个元素是字符串,以都好分隔,并且带方括号。

    可以使用下标访问List中指定的元素:colors[0]

    可以通过调用其size方法或专用关键字size的方法查出给定list的长度:colors.size或者colors.size()

    可以通过使用isEmpty()方法或占用关键词isEmpty来的值给定的List是不是空。colors.isEmpty或colors.isEmpty()

    还可以使用OGNL表达式来创建List,创建一个List与生命一个Java数组是相同的:{"Red","Black","Green"}

    访问Map类型的属性

    读取一个Map类型的属性将以如下所示的格式返回它所有的键值对:

    {key-1=value-1,key-2=value-2,key-3=value-3}

    如果希望检索出某个Map的值,需要使用如下格式:map[key]

    可以使用size或者size()得出某个给定的Map的键值对的个数

    可以使用isEmpty或者isEmpty()检查出某个给定Map是不是空。

    可以使用如下语法来创建一个Map:

    #{key-1=value-1,key-2=value-2,key-3=value-3}

    看代码:

    <%@page import="java.util.HashMap"%>
    <%@page import="java.util.Map"%>
    <%@ page language="java" contentType="text/html; charset=ISO-8859-1"
        pageEncoding="ISO-8859-1"%>
    <%@taglib prefix="s" uri="/struts-tags"%>
    <!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=ISO-8859-1">
    <title>Insert title here</title>
    </head>
    <body>
            <s:debug></s:debug>
            productId:${productId }
            <br><br>
            productName:${productName }
            <br><br>
            productDesc:${productDesc }
            <br><br>
            productPrice:${productPrice }
            <br><br>
            productPrice:<s:property value="productPrice"/>
            <br><br>
            productName1:${sessionScope.product.productName }
            <br><br>
            productName1.1:<s:property value="#session.product.productName"/>
            <br><br>
            productName2:${requestScope.test.productName }
            <br><br>
            productName2.1:<s:property value="#request.test.productName"/>
            <br><br>
            <!-- 使用 OGNL 调用public 类的public类型的静态字段和静态方法 -->
            <s:property value="@java.lang.Math@PI"/>
            <br><br>
            <s:property value="@java.lang.Math@cos(0)"/>
            <br><br>
            <!-- 调用对象栈的方法为一个属性赋值 -->
            <s:property value="setProductName('logan')"/>
            <br><br>
            <s:property value="productName"/>
            <br><br>
            <%
                String [] names = new String[]{"aa","bb","cc","dd"};
                request.setAttribute("names", names);
            %>
            length: <s:property value="#attr.names.length"/>
            <br><br>
            names[2]:<s:property value="#attr.names[2]"/>
            <br><br>
            <%
                Map<String,String> letters = new HashMap<String,String>();
                request.setAttribute("letters", letters);
                letters.put("AA", "a");
                letters.put("BB", "b");
                letters.put("CC", "c");
                
            %>
            <!-- 使用OGNL访问Map -->
            <s:property value="#attr.letters.size"/>
            <br><br>
            AA:<s:property value="#attr.letters['AA']"/>
            
    </body>
    </html>
  • 相关阅读:
    PyQuery
    计算 1+1/2!+1/3!+1/4!+...1/20!=?
    计算5的阶乘 5!的结果是?
    一张纸的厚度大约是0.08mm,对折多少次之后能达到珠穆朗玛峰的高度(8848.13米)?
    百马百担
    九九乘法表
    百钱买百鸡
    三角形菱形
    水仙花
    前缀表达式的计算
  • 原文地址:https://www.cnblogs.com/LoganChen/p/6974057.html
Copyright © 2020-2023  润新知