【JavaEE筆記】Struts2 (三) ognl、值棧操作等
阿新 • • 發佈:2019-01-29
一. ognl概述
1. 在web階段,學習過EL表示式,EL表示式在JSP中獲取域物件裡面的值
2. ognl是一種表示式,這個表示式功能更加強大
i.在struts2裡面操作值棧資料ii. 一般把ognl在struts2操作,和struts2標籤一起使用操作值棧
3. OGNL不是struts2的一部分,單獨的專案,經常和struts2一起使用
i. 使用ognl時候首先要匯入jar包,struts2提供的jar包
二. ognl入門案例
1. 使用ognl+struts2標籤實現計算字串長度
支援物件方法的呼叫,例如 objName.methodName()i. 在Java程式碼中呼叫字串 .length() 方法
2. 使用struts2標籤
i. 使用jstl時候,匯入jar包後,在jsp頁面中引入標籤庫
ii. 使用struts2標籤的時候,在jsp頁面中引入標籤庫
<%@ taglib uri="/struts-tag" prefix="s" %> <!--引入標籤庫 -->
iii. 使用struts2標籤 實現操作
<body> <!-- 使用ognl+struts2標籤實現字串長度 value屬性值:ognl表示式 --> <s:property value="'abcdefg'.length()"/> </body>
三. 值棧
1. 什麼是值棧?
i. 之前在web階段,在servlet裡面進行操作,把資料放到域物件裡面,在頁面中使用EL表示式獲取到,域物件在一定範圍內,存值和取值。
ii. 在struts2裡面提供本身一種儲存的機制,類似於域物件,是值棧,可以存值和取值
1) 在action裡面把資料放到值棧裡面,在頁面裡面獲取到值棧資料
iii. action和servlet區別?
1) servlet:預設在第一訪問時候建立,建立一次,單例項物件。2) action:訪問時候建立,每次訪問action,都會建立action物件,建立多次,多例項物件。
iv. 值棧儲存位置
1) 每次訪問action時候,都會建立action物件。2) 在每個action物件裡面都有一個值棧物件。
四. 如何獲取值棧物件
1. 獲取值棧物件有多種方式
i. 使用ActionContext類裡面的方法得到值棧物件。
//1.獲取ActionContext物件 ActionContext context = ActionContext.getContext(); //2.呼叫方法得到值棧物件 ValueStack stack1 = context.getValueStack();
ii. 每一個action物件中只有一個值棧物件
五. 值棧內部結構
1. 值棧分為兩部分
i. 第一部分 root,結構是 list集合
1) 一般操作都是 root裡面的資料
ii. 第二部分 context,結構是 map集合
2. struts2裡面標籤 s:debug 使用這個標籤可以檢視值棧結構和儲存值
i. 訪問action,執行action的方法有返回值,配置返回值到 jsp頁面中,在 jsp頁面中使用這個標籤
1) 點選超連結看到結構
ii. 在acion沒有做任何操作,棧頂元素是action 引用
1) action 物件裡面有值棧物件2) 值棧物件裡面有action引用
六. 向值棧放資料
1. 向值棧放資料的多種方式
i. 獲取值棧物件,呼叫值棧物件裡面的 set 方法
//第一種 使用值棧物件裡面的set方法 //1.獲取值棧物件 ActionContext context = ActionContext.getContext(); ValueStack stack1 = context.getValueStack(); //2.呼叫方法set方法 stack1.set("username", "yangfan");
ii. 獲取值棧物件,呼叫值棧物件裡面的 push方法
//第一種 使用值棧物件裡面的set方法 //1.獲取值棧物件 ActionContext context = ActionContext.getContext(); ValueStack stack1 = context.getValueStack(); //2.呼叫方法set方法 stack1.set("username", "yangfan"); //3.呼叫方法push方法 stack1.push("abc");
iii. 在action 定義變數,生成變數的get方法(主要)
public class ValueStackAcion extends ActionSupport { //1.定義變數 private String name; //2.生成變數get方法 public String getName() { return name; } @Override public String execute() throws Exception { //在執行方法裡面向變數設定值 name = "hello"; return "success"; } }
2. 向值棧放物件
i. 定義物件變數ii. 生成變數的get方法iii. 在執行的方法裡面向物件中設定值
import org.fan.entity.User; import com.opensymphony.xwork2.ActionContext; import com.opensymphony.xwork2.ActionSupport; import com.opensymphony.xwork2.util.ValueStack; public class ObjectAcion extends ActionSupport { //1.定義物件變數 private User user = new User(); //2.生成get方法 public User getUser() { return user; } @Override public String execute() throws Exception { //3.向值棧的User裡面放資料 user.setUsername("yangfan"); user.setPassword("123123"); user.setAddress("西安"); return "success"; } }
3. 向值棧放 list集合
i. 定義list集合變數ii. 生成變數的get方法iii. 在執行的方法裡面向list集合設定值
import java.util.ArrayList; import java.util.List; import org.fan.entity.User; import com.opensymphony.xwork2.ActionSupport; public class ListAction extends ActionSupport { //1.定義List變數 private List<User> list = new ArrayList<>(); //2.get方法 public List<User> getList() { return list; } @Override public String execute() throws Exception { //3.向list裡面放值 User user1 = new User(); user1.setUsername("Ying"); user1.setPassword("123456"); user1.setAddress("北京"); User user2 = new User(); user2.setUsername("yangfan"); user2.setPassword("123123"); user2.setAddress("西安"); list.add(user1); list.add(user2); return "success"; } }
七. 從值棧獲取資料
使用struts2標籤+ognl表示式獲取值棧資料
<s:property value="ognl表示式"/>
1. 從值棧獲取字串
i. 向值棧中放字串
import com.opensymphony.xwork2.ActionSupport; public class ValueStackAction extends ActionSupport { private String username; public String getUsername() { return username; } public String execute() throws Exception { username = "itcast"; return "success"; } }
ii. 在jsp中使用struts2標籤+ognl表示式獲取
<!-- 1.獲取字串的值 --> <s:property value="username"/>
2. 從值棧獲取物件
i. 向值棧中放物件
import org.fan.entity.User; import com.opensymphony.xwork2.ActionSupport; public class ObjectStackAction extends ActionSupport { private User u = new User(); public User getU() { return u; } public String execute() throws Exception { u.setUsername("yang"); u.setPassword("123123"); u.setAddress("西安"); return "success"; } }
ii. 在頁面中獲取
<!-- 2.獲取物件 --> <s:property value="u.username"/> <s:property value="u.password"/> <s:property value="u.address"/>
3. 從值棧獲取 list集合
i. action
import java.util.ArrayList; import java.util.List; import org.fan.entity.User; import com.opensymphony.xwork2.ActionSupport; public class ListStackAction extends ActionSupport { //1.定義list變數 private List<User> list = new ArrayList<>(); //2.get方法 public List<User> getList() { return list; } public String execute() throws Exception { //3.向list放資料 User user1 = new User(); user1.setUsername("Ying"); user1.setPassword("123456"); user1.setAddress("北京"); User user2 = new User(); user2.setUsername("yangfan"); user2.setPassword("123123"); user2.setAddress("西安"); list.add(user1); list.add(user2); return "success"; } }
ii. jsp
<!-- 3.獲取值棧中 list集合資料 --> 第一種方式 <br> <s:property value="list[0].username"/> <s:property value="list[0].password"/> <s:property value="list[0].address"/><br> <s:property value="list[1].username"/> <s:property value="list[1].password"/> <s:property value="list[1].address"/><br> 第二種方式 <br> <!-- 使用struts2裡面的標籤 類似JSTL裡面的 foreach標籤 --> <!-- 遍歷list得到list裡面每個user物件--> <s:iterator value="list"> <s:property value="username"/> <s:property value="password"/> <s:property value="address"/><br> </s:iterator> 第三種方式 <br> <!--遍歷值棧list集合 得到每個物件 機制:把每次遍歷出來的user物件放到context裡面 獲取context裡面資料的特點:寫ognl表示式,使用特殊符號 # --> <s:iterator value="list" var="user"> <s:property value="#user.username"/> <s:property value="#user.password"/> <s:property value="#user.address"/><br> </s:iterator>
4.其他操作
i. 使用set方法向值棧放的資料的獲取
ii. 使用push方法向值棧放資料的獲取
1) 使用push方法設定值,沒有名稱,就只有設定的值。
2) 向值棧中放資料,把向值棧中放的資料存到陣列中,陣列名稱 top,根據陣列獲取值。
八. EL表示式獲取值棧資料(為什麼?)
1. EL表示式獲取域物件
2. 向域物件裡面放值使用setAttribute方法,獲取值使用getAttribut方法
3. 底層增強request物件裡面的方法getAttribute方法
i. 首先從request域獲取值,如果獲取到,直接返回。
ii. 如果從request域獲取不到值,到值棧中把值獲取出來,把值放到域物件裡面。
4. 關鍵性原始碼
九. ognl表示式 #、% 使用
1. # 的使用
i. 使用#獲取context裡面資料
ii. # 操作
1) java
import javax.servlet.http.HttpServletRequest; import org.apache.struts2.ServletActionContext; import com.opensymphony.xwork2.ActionSupport; public class ContextAction extends ActionSupport { @Override public String execute() throws Exception { //1.獲取request HttpServletRequest request = ServletActionContext.getRequest(); request.setAttribute("req", "123123"); return "success"; } }
2) jsp
<!-- 獲取context裡面資料 寫ognl時候 首先新增符號 # #context的key的名稱.域物件名稱 --> <s:property value="#request.req"/>
2. % 的使用
i. 在struts2標籤中使用ognl表示式,如果直接在struts2表單標籤裡面使用ognl表示式不識別,只有 % 之後才會識別。
<s:textfield name="username" value="%{#request.req}"></s:textfield>