<rt id="bn8ez"></rt>
<label id="bn8ez"></label>

  • <span id="bn8ez"></span>

    <label id="bn8ez"><meter id="bn8ez"></meter></label>

    溫故知新:struts2_03參數(shù)的傳遞

    struts2的參數(shù)傳遞和OGNL息息相關(guān),先從幾個OGNL的案例來感受一下

    OGNL的概念和作用,不贅述,直接百科傳送門:http://baike.baidu.com/view/1347280.htm。使用OGNL可以極為靈活的在頁面上對目標對象進行存取操作,而不僅僅是只是數(shù)據(jù)的展示。下面使用OGNL給出幾個常用的例子。
    測試用實體類User和Department
     1 package demo.ognlDemo;
     2 
     3 public class User {
     4 
     5     private String name;
     6     private int age;
     7     private Department department;
     8 
     9     public void hello(String name) {
    10         System.out.println("hello " + name);
    11     }
    12 
    13     public static void sayHi() {
    14         System.out.println("HI");
    15     }
    16 
    17     public User() {
    18         super();
    19     }
    20 
    21     public User(String name, int age, Department department) {
    22         super();
    23         this.name = name;
    24         this.age = age;
    25         this.department = department;
    26     }
    27    //get/set方法略
    28}

     1 package demo.ognlDemo;
     2 
     3 public class Department {
     4 
     5     private String name;
     6     private int no;
     7    
     8     //get/set方法略
     9
    } 

    下面給出測試類
     1 package demo.ognlDemo;
     2 
     3 import java.util.ArrayList;
     4 import java.util.HashMap;
     5 import java.util.List;
     6 import java.util.Map;
     7 
     8 import ognl.Ognl;
     9 import ognl.OgnlException;
    10 
    11 import org.junit.Test;
    12 
    13 
    14 public class OgnlDemo {
    15 
    16     @Test
    17     public void test01() {
    18         
    19         //定義兩個演示用的對象
    20         User u = new User();
    21         u.setAge(20);
    22         u.setName("Tom");
    23         
    24         Department dep = new Department();
    25         dep.setName("Security");
    26         dep.setNo(10);
    27         
    28         u.setDepartment(dep);
    29         
    30         //一個根map
    31         Map<String , Object> ctx = new HashMap<String, Object>();
    32         ctx.put("user", u);
    33         ctx.put("department", dep);
    34         
    35         try {
    36             //下列表達式都是在以指定對象為根進行屬性查找
    37             //以u為根
    38             System.out.println(Ognl.getValue("name", u));
    39             System.out.println(Ognl.getValue("age", u));
    40             System.out.println(Ognl.getValue("department.name", u));
    41             System.out.println("====================================");
    42             //以dep為根
    43             System.out.println(Ognl.getValue("name", dep));
    44             System.out.println(Ognl.getValue("no", dep));
    45             System.out.println("====================================");
    46             
    47             //以集合為根
    48             System.out.println(Ognl.getValue("department.name", ctx,ctx));
    49             //從根的集合中取值需要添加#來區(qū)分
    50             System.out.println(Ognl.getValue("#department.name", ctx,u));
    51             //訪問對象的方法
    52             System.out.println(Ognl.getValue("hello('Jerry')",ctx,u));
    53             //訪問靜態(tài)的方法,格式為@XXX.XXX.XXX(包名...類名)@XXX(靜態(tài)方法名)
    54             System.out.println(Ognl.getValue("@demo.ognlDemo.User@sayHi()",u));
    55             //root是根元素的鍵值,通過#root可以直接取得根元素
    56             System.out.println(Ognl.getValue("#root.name", ctx,u));
    57             System.out.println("====================================");
    58             
    59             //以一個集合為根,取得其中的某個元素
    60             List<User> users = new ArrayList<User>();
    61             User u1 = new User();
    62             u1.setName("zhangsan");
    63             User u2 = new User();
    64             u2.setName("lisi");
    65             users.add(u1);
    66             users.add(u2);
    67             System.out.println(Ognl.getValue("#root[0].name",users));
    68             
    69             //或者
    70             System.out.println(Ognl.getValue("get(0).name",users));
    71             
    72         } catch (OgnlException e) {
    73             e.printStackTrace();
    74         }
    75     }
    76 }

    下面回到struts2,struts2中的所有參數(shù)都保存在ValueStack中,而ValueStack就是一個OGNL結(jié)構(gòu)。ValueStack由兩部分組成,一個是ActionContext,類似于OGNL的Map集合,另一個是compoundRoot,類似于OGNL的根對象,使用ArrayList維護了一個棧結(jié)構(gòu)。而參數(shù)則可以通過三種方式進行傳遞。
    方法一:
    在action中添加屬性,并為屬性添加get/set方法
    這個方法實際上就是在ValueStack的根中創(chuàng)建一個action對象,取值的時候如果沒有特別指定,則默認取得棧頂?shù)膶ο蟆T谌≈档臅r候從棧頂開始依次向下獲取,根據(jù)Key值返回第一個取得的值,同時,我們也可以對ValueStack進行操作,使用ActionContext.getContext().getValueStack()獲得ValueStack,進行push,peek或者remove等操作
    方法二:
    使用ActionContext存放值
    方法三:
    使用ServletActionContext存放值

    Action:
     1 package demo.ognlDemo;
     2 
     3 import org.apache.struts2.ServletActionContext;
     4 
     5 import com.opensymphony.xwork2.ActionContext;
     6 
     7 public class DemoAction {
     8     //1:通過action屬性傳值
     9     private String name;
    10     private String age;
    11     
    12     public String execute(){
    13         
    14         name = "Tom";
    15         age = "99";
    16         
    17         //2:通過actioncontext傳值
    18         ActionContext.getContext().put("demokey"99999999);
    19         
    20         //3:通過servletActionContext進行傳值
    21         ServletActionContext.getRequest().setAttribute("servletkey"00000000);
    22         
    23         return "success";
    24     }
    25     //get/set方法略
    26
    27 }
    JSP:
     1 <%@ page language="java" contentType="text/html; charset=UTF-8" isELIgnored="false"
     2     pageEncoding="UTF-8"%>
     3 <%@taglib prefix="s" uri="/struts-tags" %>
     4 <!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
     5 <html>
     6 <head>
     7 <meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
     8 <title>struts2 Demo</title>
     9 </head>
    10 <body>
    11 
    12 對于EL表達式而言,不論值存放在什么地方,都可以取得,但是使用struts2的標簽,需要注意key值的寫法
    13 
    14 <hr>
    15 通過屬性進行傳值:<br>
    16 EL表達式 -->${name}:${age}<br>
    17 s:property標簽 --<s:property value="name"/> : <s:property value="age"/>
    18 <hr>
    19 
    20 通過actionContext進行傳值<br>
    21 EL表達式--> ${demokey}<br>
    22 s:property標簽(訪問actionContext中的數(shù)據(jù),需要在鍵值之前添加“#”) --<s:property value="#demokey"/>
    23 <hr>
    24 
    25 通過servletActionContext進行傳值<br>
    26 EL表達式 -->${servletkey}<br>
    27 s:property標簽 (訪問servletActionContext中的數(shù)據(jù),需要在鍵值之前添加“#”,并且需要注明范圍:request/session/application)--<s:property value="#request.servletkey"/>
    28 <hr>
    29 </body>
    30 </html>
    為了能查看更詳細的信息,開發(fā)過程中可以在頁面中加入調(diào)試標簽
    1 <s:debug/>
    標簽展開之后Value Stack Contents就是根的內(nèi)容,Stack Context就是集合的內(nèi)容

    上述內(nèi)容是從action到j(luò)sp的參數(shù)傳遞,下面是從jsp到action的參數(shù)傳遞
    方法一:
    通過地址欄參數(shù)進行參數(shù)傳遞,/XXX?param=YYY,在Action里可以直接通過對應(yīng)的屬性來獲取,或者直接通過servletActionContext取得request,獲取參數(shù)值。
    這種方法對于少量的參數(shù)傳遞來說沒有問題,但是碰到大量的參數(shù)或者中文,其他特殊參數(shù)的傳遞就顯得力不從心,可能需要經(jīng)過轉(zhuǎn)碼進行傳遞,不方便。
    方法二:
    表單傳遞參數(shù),較直接使用地址欄傳參安全一些,但是參數(shù)一多,仍然很頭疼。可以使用以下方法將需要獲取的值注入到指定的對象中。
    1:比如,在通常情況下,為了傳遞多個值到一個user對象中,我們可以將表單域的名字寫為
    1 <input name="user.id" id="uid"/>
    這樣一來,user的id屬性就會接收到相應(yīng)的值,以此類推,user的其他屬性值都可以參照此寫法。表單提交之后,在action中就可以使用user進行操作。
    2:或者我們可以使action實現(xiàn)ModelDriven<T>接口,這樣一來在傳遞表單的時候,表單域的name屬性就無需指定要傳遞到的對象,直接寫作
    1 <input name="id" id="uid"/>
    ModelDriven實際上就是在ValueStack中,root里的action之上又添加了一個指定的對象,該對象就是實現(xiàn)接口時指定的T,提交表單的時候,參數(shù)的值會根據(jù)root中的對象,從上到下依次填充,表單域中的屬性首先填充到ModelDrive的對象。

    上面提到的這兩種值填充,在某些情況下可能會有問題,要填充的屬性若是非String類型,比如Date類型,這樣就無法直接轉(zhuǎn)換,但是一般來說前端會使用控件來限制日期格式的輸入,然后通過String來接收日期字符串,自行轉(zhuǎn)換。struts2提供了這種問題的解決方案,雖然用的不多,但是見仁見智,轉(zhuǎn)換器有時也有它的用武之地。
    要使用struts2的轉(zhuǎn)換器,需要新建類,然后繼承StrutsTypeConverter
     1 package demo.ognlDemo;
     2 
     3 import java.text.ParseException;
     4 import java.text.SimpleDateFormat;
     5 import java.util.Date;
     6 import java.util.Map;
     7 
     8 import org.apache.struts2.util.StrutsTypeConverter;
     9 /**
    10  * 自定義的局部轉(zhuǎn)換器,將時間和字符串進行轉(zhuǎn)換
    11  * @author Administrator
    12  *
    13  */
    14 public class DateConverter extends StrutsTypeConverter{
    15 
    16     SimpleDateFormat sdf = new SimpleDateFormat("yyyy/MM/dd");
    17     
    18     /**
    19      * 字符串到對象
    20      */
    21     @SuppressWarnings("rawtypes")
    22     @Override
    23     public Object convertFromString(Map context, String[] values, Class toClass) {
    24         
    25         try {
    26             if (values.length > 0 && values.length <= 1) {
    27                 String str = values[0];
    28                 return sdf.parse(str);
    29             }
    30             return null;
    31         } catch (ParseException e) {
    32             e.printStackTrace();
    33             return null;
    34         }
    35         
    36         
    37     }
    38 
    39     /**
    40      * 對象到字符串
    41      */
    42     @SuppressWarnings("rawtypes")
    43     @Override
    44     public String convertToString(Map context, Object o) {
    45         Date d = (Date)o;
    46         return d.toString();
    47     }
    48 
    49 }
    50 
    給出一個字符串和日期相互轉(zhuǎn)換的例子,重寫父類的convertFromStringconvertToString方法,convertFromString意味著吧頁面上傳遞過來的String參數(shù)經(jīng)過加工變成自己想要的參數(shù)類型,values是參數(shù)數(shù)組,一般只有一個。convertToString意味著將參數(shù)從action傳出到頁面的時候需要進行的轉(zhuǎn)換。寫好轉(zhuǎn)換器之后,就需要配置自定義轉(zhuǎn)換器的使用,轉(zhuǎn)換器有局部和全局之分,兩種都需要定義對應(yīng)的properties文件。

    局部轉(zhuǎn)換器,也就是針對某個action用的轉(zhuǎn)換器,需要定義名為“action名稱-conversion.properties”的配置文件,并且該文件需要和對應(yīng)的action置于同一目錄,里面配置哪些屬性需要用哪個轉(zhuǎn)換器轉(zhuǎn)換。這段配置就意味著對應(yīng)action中的creDate(Date類型)的屬性,使用DateConverter轉(zhuǎn)換
    1 creDate = demo.ognlDemo.DateConverter

    全局轉(zhuǎn)換器不限于哪個action使用,對整個項目都生效,需要配置名為“xwork-conversion.properties”的配置文件,置于src目錄下,里面需要配置具體action的具體哪個屬性用哪個轉(zhuǎn)換器轉(zhuǎn)換
    1 demo.ognlDemo.XXXAction.creDate = demo.ognlDemo.DateConverter

    posted on 2014-10-30 16:38 都較瘦 閱讀(172) 評論(0)  編輯  收藏 所屬分類: MVCFramework

    <2025年5月>
    27282930123
    45678910
    11121314151617
    18192021222324
    25262728293031
    1234567

    導(dǎo)航

    統(tǒng)計

    公告

    博客定位:囿于目前的水平,博客定位在記錄自己的學(xué)習(xí)心得和隨手的練習(xí)

    常用鏈接

    留言簿

    隨筆分類

    隨筆檔案

    文章分類

    文章檔案

    搜索

    最新評論

    閱讀排行榜

    評論排行榜

    主站蜘蛛池模板: 亚洲国产精品专区| 亚洲一级毛片免费看| 亚洲人成777在线播放| 国产亚洲精品国看不卡| 成人毛片18女人毛片免费| 国产精品免费福利久久| 免费国产黄网站在线观看动图 | 亚洲欧美aⅴ在线资源| 亚洲成在人天堂一区二区| 亚洲精品色婷婷在线影院| 无码一区二区三区AV免费| 亚洲免费在线播放| 中文无码日韩欧免费视频| 国产亚洲高清在线精品不卡| 亚洲天堂2016| 亚洲国产综合第一精品小说| 亚洲AV一宅男色影视| 亚洲午夜日韩高清一区| 国产免费私拍一区二区三区 | 亚洲一区精品视频在线| 久久亚洲精品国产精品| 亚洲av无码一区二区三区网站| 亚洲伊人久久综合影院| 免费大黄网站在线观看| 国产精品视频免费一区二区三区| 毛片免费观看视频| 一二三四影视在线看片免费| 少妇无码一区二区三区免费| 国产永久免费高清在线| 花蝴蝶免费视频在线观看高清版| 久久精品成人免费观看97| 一区二区3区免费视频| 人人爽人人爽人人片A免费| 国产亚洲精品美女| 狼色精品人妻在线视频免费| 美女视频黄a视频全免费网站一区 美女视频黄a视频全免费网站色 | 亚洲欧洲日本在线| 亚洲综合色区在线观看| 久久精品亚洲福利| 亚洲欧洲精品无码AV| 亚洲国产另类久久久精品 |