struts2框架詳解


struts2框架(1)---struts2入門

struts2框架

          如果你之前在MVC模式的時候一直都是通過servlet,獲取和返回數據,那么現在開始學習struts2框架,

  Struts是一個實現MVC設計模式的優秀的框架。它的許多優點我就不說了。

          我用自己做的一張圖說明servlet和struts2的區別。

寫一個最基本的開發步驟,完成開發。

        (1)創建WEB 工程

        (2)導入必要jar包

        (3) 編寫JSP 頁面

        (4)編寫Action 服務器端處理邏輯

        (5)進行框架配置web.xml、struts.xml

        (6)運行測試

(1)創建WEB 工程

         這步還是很正常一樣,創建一個普通web工程。如圖:

(2)導入必要jar包

      首先我要告訴你到哪里去下載這個框架:在apache官網,你百度struts2下載就可以找到了。

Struts運行必要jar包介紹:

開發中為了方便導入,可以使用app/struts2-blank.war 攜帶jar包

(3) 編寫JSP 頁面

在webRoot下新建一個Demo文件,網頁先訪問start.jsp之后通過框架返回到result頁面

 

start.jsp界面:

復制代碼
<%@ page language="java" import="java.util.*" pageEncoding="UTF-8"%>
<html>
  <head>
  </head>
  <body>
    <h1>請求發起的頁面</h1>
    <!-- 發起一個請求 訪問Struts2框架 -->
    <!-- Struts2請求  默認是以.action結尾 -->
    <a href="${pageContext.request.contextPath }/hello.action">訪問Struts2入門程序</a>
  </body>
</html>
復制代碼

result.jsp界面

復制代碼
<%@ page language="java" import="java.util.*" pageEncoding="UTF-8"%>
<html>
  <head>
  </head> 
  <body>
    <h1>處理完成的結果頁面</h1>    
  </body>
</html>
復制代碼

(4)編寫Action 服務器端處理邏輯

這里就是通過java創建一個類,該類可以說是action最普通的一個類

復制代碼
1 package com.yudian.struts;
2 public class HelloAction {
3      public String execute() throws Exception{  //這里取execute代表默認執行這個方法
4             System.out.println("我是執行的內容...");
5              return  "excutesuccess";   //有返回值,我們用來跳轉頁面
6         }
7 }
復制代碼

(5)進行框架配置web.xml、struts.xml

配置文件才是核心關鍵,先配置web.xml

復制代碼
 1 <?xml version="1.0" encoding="UTF-8"?>
 2 <web-app version="2.5" 
 3     xmlns="http://java.sun.com/xml/ns/javaee" 
 4     xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
 5     xsi:schemaLocation="http://java.sun.com/xml/ns/javaee 
 6     http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd">
 7   <display-name></display-name>    
 8   <!-- 配置Struts2的前端控制器 --><!--filter-class里面很關鍵,固定  -->
 9    <filter>
10        <filter-name>struts2</filter-name>
11        <filter-class>org.apache.struts2.dispatcher.ng.filter.StrutsPrepareAndExecuteFilter</filter-class>
12    </filter>
13    <filter-mapping>
14        <filter-name>struts2</filter-name>
15        <url-pattern>/*</url-pattern>
16    </filter-mapping>
17   
18   
19   <welcome-file-list>
20     <welcome-file>index.jsp</welcome-file>
21   </welcome-file-list>
22 </web-app>
復制代碼

在配置struts.xml,注意了這個是放在src下面而不是包下面

復制代碼
 1 <?xml version="1.0" encoding="UTF-8"?>
 2 <!DOCTYPE struts PUBLIC
 3     "-//Apache Software Foundation//DTD Struts Configuration 2.3//EN"
 4     "http://struts.apache.org/dtds/struts-2.3.dtd">
 5 
 6 <struts>
 7     <package name="default"  extends="struts-default">
 8      <!-- 3.默認Action  和Action的默認處理類 -->
 9         <!-- 1.初步認識Struts2 --><!-- 這里hello一定要和jsp中hello。action一致才能找到 -->
10        <action name="hello" class="com.yudian.struts.HelloAction">
11             <result name="excutesuccess">/demo/result.jsp</result>
12        </action>  <!-- result代表如果返回值為 excutesuccess則跳轉頁面-->            
13     </package>
14 </struts>
復制代碼

(6)運行測試

先通過瀏覽器訪問start界面:

當點擊:訪問Struts2入門程序連接直接跳轉到了result.jsp

運行結果:

這上面是一個最基本的struts框架的運用,很簡單,主要是供大家理解,關於每一個細節我會在接下面慢慢補充.

歡迎大家的留言給出指點意見,謝謝!

Struts2系列筆記(2)---struts.XML

Struts2.xml

本篇博客主要講struts.xml中package下的標簽和標簽屬性,主要分以下四個部分說明:

  (1)action的配置基本屬性

  (2)同一個Action類中不同方法滿足不同的action邏輯

  (3)通配符解決多業務問題

  (4)配置處理結果:

(1)action的配置基本屬性

復制代碼
 1  <!--首先聲明本片文章基本還是參考http://www.cnblogs.com/Nouno/p/5683447.html的博客,特此說明-->
 2 <?xml version="1.0" encoding="UTF-8"?>  
 3   <!DOCTYPE struts PUBLIC  
 4       "-//Apache Software Foundation//DTD Struts Configuration 2.3//EN"  
 5       "http://struts.apache.org/dtds/struts-2.3.dtd">  
 6   <struts>  
 7       <!-- /primer/helloWorldAction.action  
 8           package:包  
 9               * name:包名,唯一的,必選項  
10               * namespace:命名空間,唯一的,相當於房間號。可選項,省略情況下是"/"。頁面中請求連接的前半部分  
11               * extends:繼承  
12                  * extends="struts-default":struts2框架底層提供的核心包struts2-core-2.3.3.jar下的struts-default.xml文件  
13                  * 為什么要繼承這個struts-default.xml文件?  
14                      * 因為struts2框架底層提供的struts-default.xml聲明了所有的攔截器和攔截器棧,  
15                                 知道在struts2框架運行時執行struts-default.xml文件中的攔截器棧。  
16                      * 如果不繼承struts-default.xml文件,就沒有辦法使用struts2框架提供的所有攔截器  
17          -->  
18       <package name="primer" namespace="/" extends="struts-default">  
19            
20          <!--   
21                   如果找不到對應的action名的時候,配置默認要執行的action   
22                 * name:指定action的名稱  
23          -->   
24          <default-action-ref name="error"></default-action-ref> 
25 27 <action name="error" class="com.yyc.struts.action.ErrorAction"> 28 <result name="error">/error.jsp</result> 29 </action> 30 <!-- 31 action: 32 * name:對應頁面中請求連接的后面半部分,這里表示jsp請求鏈接為hello.action才會和它匹配 33 * class:對應要執行的類的完整路徑 ,表示Action類的完整路徑,相當於之前的servlet類 34 *method:對應的class類中要執行的方法,默認執行method="execute()" 35 --> 36 <action name="hello" class="cn.yht.primer.HelloWorldAction" method="execute()"> 37 <!-- 38 result:結果類型 ,可以用來把Action類處理好的數據跳轉到某界面 39 * name:對應的是執行的類的方法的返回值 40 public String execute() throws Exception { 41 System.out.println("HelloWorldAction ************* execute()"); 42 return "success"; 43 } 44 * 默認判斷name="success",后半部分的文本內容:要轉向到的頁面 45 --> 46 <result name="success">/primer/success.jsp</result> 47 </action> 48 <!-- 49 沒有為action指定class 50 * 在struts2框架底層的struts-default.xml文件中,配置了默認執行的類 51 com.opensymphony.xwork2.ActionSupport 52 public String execute() throws Exception { 53 return SUCCESS; 54 } 55 * 實際上,默認執行的是底層提供的ActionSupport類的execute()方法 56 * result結果類型,默認是根據struts2框架底層提供的ActionSupport類的execute()方法返回值,進行跳轉 57 --> 58 <action name="actionNoClass"> 59 <result name="success">/primer/success.jsp</result> 60 </action> 61 </package> 62 </struts>
復制代碼

(2)同一個Action類中不同方法滿足不同的action邏輯

復制代碼
 1 <!--這個Action中有兩個方法
 2 public class ProductAction extends ActionSupport {
 3     public String add(){
 4         System.out.println("添加商品");
 5         return NONE;
 6     } 
 7     public String del(){
 8         System.out.println("刪除商品");
 9         return NONE;
10     }  
11 }-->
12 
13 <!-- 多個業務需求 -->
14        <action name="addBook" class="com.guigu.struts.action.BookAction" method="add"></action>
15        <action name="delBook" class="com.guigu.struts.action.BookAction" method="del"></action>
16 <!--這樣確實能夠實現一個Action類中的不同方法,都能被調用
17    但是你也許會注意到,每調用一個方法都需要配置action-->
復制代碼

(3)通配符解決多業務問題

復制代碼
 1 <!--這里是jsp文件  
 2      <h1>客戶管理</h1>
 3      <a href="${pageContext.request.contextPath }/customer_add">添加客戶</a><br/>
 4      <a href="${pageContext.request.contextPath }/customer_del">刪除客戶</a><br/>
 5      <a href="${pageContext.request.contextPath }/customer_edit">修改客戶</a><br/>
 6      <a href="${pageContext.request.contextPath }/customer_find">查詢客戶</a><br/>
 7      -->
 8  <!-- 使用通配符解決多業務問題 -->
 9        <!-- method 屬性{1}是取第一個* ,這樣就只需要寫一個action就可以了,我們只要在Action類中寫好相對應的方法即可-->
10        <action name="customer_*" class="com.guigu.struts.action.CustomerAction" method="{1}">
11           <result >/demo1/{1}.jsp</result>
12        </action>
復制代碼

(4)配置處理結果: 

Struts2的Action處理用戶請求結束后,返回一個普通字符串-邏輯視圖名,必須在struts.xml文件中完成邏輯視圖和物理視圖資源的映射,才可讓系統轉到實際的視圖資源。

Struts2通過在struts.xml文件中使用<result …/>元素來配置結果。Struts2提供了兩種結果。

     a.局部結果:將<result …/>作為<action …>元素的子元素配置。

     b.全局結果:將<result …/>作為<global-results …>元素的子元素配置。

在package元素中配置<global-results>子元素:

復制代碼
<!--全局result(global-results)
有很多時候一個<result>可供很多<action>使用,這時可以使用<global-results>標簽來定義全局的<result>l。執行順序:當一個Action返回的String沒有相應的<result>與之對應,Struts2就會查找全局的<result>。-->

<global-results>

<result name="error">/Error.jsp</result>
<result name="invalid.token">/Error.jsp</result>
<result name="login" type="redirect-action">Logon!input</result>

</global-results>
復制代碼

歡迎大家留言指點!

Struts2框架(3)---Action類的3種書寫方式

Action類的3種書寫方式

 本文主要寫有關寫Action類的3種書寫方式:

      (1)第一種 Action可以是POJO (簡單模型對象)  不需要繼承任何父類 也不需要實現任何接口

    (2)實現Action接口

    (3)繼承ActionSupport(推薦)

那我們先來書寫第一種:

          (1)第一種 Action可以是POJO (簡單模型對象)  不需要繼承任何父類 也不需要實現任何接口

復制代碼
1 //這里其實就是一個普通的類,類里面的方法可以任意寫,如果寫execute()方法那就代表默認執行它
2 public class RequestAction1 {   
3     //提供滿足條件的方法   excute方法
4     //public 范圍的    帶有String返回值的 無參的方法
5     public String execute(){
6         System.out.println("測試方式一");
7         return null;//null表示不進行跳轉
8     }
9 }
復制代碼

     (2)實現Action接口

復制代碼
 1 import com.opensymphony.xwork2.Action;
 2 public class RequestAction2  implements Action{
 3 
 4     public String execute() throws Exception {
 5         System.out.println("方式二 實現Action接口 成功執行....");
 6         return SUCCESS;
 7     }
 8 }
 9 /**
10  * Action接口中一共有5個五種邏輯視圖 和一個方法分別如些:
11  * public abstract interface com.opensymphony.xwork2.Action {
12                                                                數據處理成功(成功的跳轉頁面)
13       public static final java.lang.String SUCCESS = "success";
14                                                               頁面不進行跳轉 return null 
15       public static final java.lang.String NONE = "none";
16                                                                數據處理發送錯誤(錯誤頁面)
17       public static final java.lang.String ERROR = "error";
18                                                         用戶處理數據 數據有誤 用於表單的校驗
19       public static final java.lang.String INPUT = "input";
20                                                                       主要是權限認證
21       public static final java.lang.String LOGIN = "login";
22 
23   public abstract java.lang.String execute() throws java.lang.Exception;
24  }
25  */
復制代碼

       (3)繼承ActionSupport(推薦)

復制代碼
 1 import com.opensymphony.xwork2.Action;
 2 import com.opensymphony.xwork2.ActionSupport;
 3 //為什么推薦ActionSupport,在Action中如果使用基礎ActionSupport的方式 可以使用表單的校驗 錯誤信息的設置 和國際化信息 三個重要的功能。
 4 public class RequestAction3 extends ActionSupport {
 5     @Override
 6     public String execute() throws Exception {
 7         System.out.println("方式三 繼承ActionSupport完成 書寫"); 
 8         return super.execute();//返回SUCCESS
 9     }
10 }
11 /**ActionSupport類的特點,點進去發現它實現了許多的接口
12  * public class ActionSupport implements Action, Validateable, 
13  * ValidationAware, TextProvider, LocaleProvider, Serializable
14  * 這么多接口說明它不簡單
15  * 
16  */
復制代碼

關於action類的創建我就說這么多!請大家多指點!

Struts2框架(4)---Action類訪問servlet

Action類訪問servlet

Action類有三種方式servlet:

      (1)間接的方式訪問Servlet API  ---使用ActionContext對象

      (2)  實現接口,訪問Action時完成注入

      (3)直接通過ServletActionContext獲得Servlet的API

下面我來講第一種:

  (1)間接的方式訪問Servlet API  ---使用ActionContext對象

   Struts2中提供了一個ActionContext類(當前Action的上下文對象),通過這個類可以訪問Servlet API。下面是該類中提供的幾個常用方法: 

     1.public static ActionContext getContext() :獲得當前Action的ActionContext實例。
     2.public Object get(Object key) :此方法類似於調用HttpServletRequest的getAttribute(String name)方法。
     3.public void put(Object key, Object value) :此方法類似於調用HttpServletRequest 的setAttribute(String name, Object o)。 
     4. public Map getParameters() :獲取所有的請求參數。類似於調用HttpServletRequest對象的getParameterMap() 方法。  
     5. public Map getSession() :返回一個Map對象,該Map對象模擬了HttpSession實例。 
     6. public void setSession(Map session) : 直接傳入一個Map實例,將該Map實例里的key-value對轉換成session的屬性名-屬性值對。 
     7. public Map getApplication() :返回一個Map對象,該對象模擬了該應用的ServletContext實例。 

     8. public void setApplication(Map application) :直接傳入一個Map實例,將該Map實例里  

             的key-value對轉換成application的屬性名- 屬性值對。 

 

 

 

 

 

 

 

 

 

 

復制代碼
 1 import java.util.Map
 2 import com.opensymphony.xwork2.ActionContext;
 3 import com.opensymphony.xwork2.ActionSupport;
 4 public class LoginAction1  extends ActionSupport{
 5  
 6     public String login() throws Exception{
 7         //獲取ActionContext
 8         ActionContext actionContext =ActionContext.getContext();
 9         //1.獲取表單的請求參數
10         Map<String, Object> parameters=actionContext.getParameters();
11         //因為用戶名username可能有多個,所以返回數組
12         String [] values =(String[]) parameters.get("username");
13         System.out.println("用戶名是:"+values[0]);
14         
15         //2.存取request 的Attribute
16         actionContext.put("company", "雨點的名字"); //相當於request.setAttribute("","");
17         System.out.println(actionContext.get("company"));
18         
19         //3.存取session 的Attribute
20         Map<String, Object> sessionMap=actionContext.getSession();
21         sessionMap.put("age", 11);//相當於session.setAttribute("","");
22         System.out.println(sessionMap.get("age"));
23         
24         //4.存取application的Attribute
25          Map<String, Object> applicationMap=actionContext.getApplication();
26          applicationMap.put("info", "下周考試第二階段");
27          System.out.println(applicationMap.get("info"));       
28         return SUCCESS;      
29     }
30 }
復制代碼

 (2)  實現接口,訪問Action時完成注入

   如果是實現結構注入一般需要實現3個接口

(1)ServletContextAware:      實現此接口的Action可直接訪問Web應用的ServletContext實例;

(2)ServletRequestAware: 實現此接口的Action可直接訪問Web應用的HttpServletRequest實例;

(3)ServletResponseAware:   實現此接口的Action可直接訪問Web應用的HttpServletResponset實例

 

 

 

 

 

 

復制代碼
 1 import java.util.Map;
 2 
 3 import javax.servlet.ServletContext;
 4 import javax.servlet.ServletResponse;
 5 import javax.servlet.http.HttpServletRequest;
 6 import javax.servlet.http.HttpServletResponse;
 7 import org.apache.struts2.interceptor.RequestAware;
 8 import org.apache.struts2.interceptor.ServletRequestAware;
 9 import org.apache.struts2.interceptor.ServletResponseAware;
10 import org.apache.struts2.util.ServletContextAware;
11 
12 import com.opensymphony.xwork2.ActionContext;
13 import com.opensymphony.xwork2.ActionSupport;
14 
15 public class LoginAction2 extends ActionSupport implements ServletRequestAware,
16      ServletContextAware,ServletResponseAware {
17    
18     private HttpServletRequest request;
19     
20     private ServletContext context;
21     
22     private HttpServletResponse response;
23     
24     public String login() throws Exception{
25         //1.獲取表單的請求參數
26         System.out.println(request.getParameter("username"));
27         
28         //2.存取request 的Attribute
29         request.setAttribute("company","hzgg" );
30         
31         //3.存取session 的Attribute
32         request.getSession().setAttribute("age", 50);
33         
34         //4.存取application的Attribute
35         context.setAttribute("info", "今天下午你們可以出去玩");
36         
37         return SUCCESS;
38         
39     }
40      //實現ServletRequestAware接口必須實現的方法
41     public void setServletRequest(HttpServletRequest request) {
42         this.request=request;
43     }
44      //實現ServletContextAware接口必須實現的方法
45     public void setServletContext(ServletContext context) {
46         this.context=context;
47     }
48      //實現ServletResponseAware接口必須實現的方法
49     public void setServletResponse(HttpServletResponse response) {
50         this.response=response;
51     }
52 
53 }
復制代碼

   (3)使用ServletActionContext工具類訪問Servlet API

  在ServletActionContext工具類中常用的幾個方法(都是靜態方法):

(1)PageContext getPageContext():          取得應用的PageContext對象;
(2)HttpServletRequest getRequest():       取得該應用的HttpServletRequest對象;
(3)HttpServletRequest getResponse():    取得該應用的HttpServletResponse對象;
(4)ServletContext getServletContext():   取得該應用的ServletContext對象。

 

 

 

 

 

復制代碼
 1 import org.apache.struts2.ServletActionContext;
 2 import com.opensymphony.xwork2.ActionSupport;
 3 
 4 public class LoginAction3 extends ActionSupport {
 5 
 6     public String login() throws Exception {
 7         // 1.獲取表單的請求參數
 8        String username= ServletActionContext.getRequest().getParameter("username");
 9        System.out.println(username);
10        
11        // 2.存取request 的Attribute
12        ServletActionContext.getRequest().setAttribute("company", "haha");
13 
14         // 3.存取session 的Attribute
15        ServletActionContext.getRequest().getSession().setAttribute("age", 40);
16 
17         // 4.存取application的Attribute
18        ServletActionContext.getServletContext().setAttribute("info", "今天下課你們可以約會去了");
19 
20         return SUCCESS;
21     }
22 }
復制代碼

下面我來寫一個用第三種方法實現訪問servlet,從jsp到struts.xml在到Action類,最后從頁面顯示結果供大家學習:

jsp界面:

start.jsp

復制代碼
<%@ page language="java" import="java.util.*" pageEncoding="UTF-8"%>
<html>
   <head>
  </head>
  <body>
    <form action="${pageContext.request.contextPath }/hello.action">
            姓名:<input type="text">
            <input type="submit" value="提交">
    </form>
  </body>
</html>
復制代碼

struts.xml

復制代碼
 1 <?xml version="1.0" encoding="UTF-8"?>
 2 <!DOCTYPE struts PUBLIC
 3       "-//Apache Software Foundation//DTD Struts Configuration 2.3//EN"
 4       "http://struts.apache.org/dtds/struts-2.3.dtd">
 5    <struts>
 6       <package name="default"  extends="struts-default">
 7         <action name="hello" class="com.guigu.struts.action2.LoginAction3" method="login">
 8            <result>/result.jsp</result>
 9         </action>            
10       </package>
11  </struts>
復制代碼
result.jsp
復制代碼
<%@ page language="java" import="java.util.*" pageEncoding="UTF-8"%>
<html>
  <head>
  </head>
  <body>
   <p>${company}</p>
   <p>${age}</p>
   <p>${info}</p>
  </body>
</html>
復制代碼

  運行結果如下:

當點擊提交的時候

  

發現數據已經從Action類中轉發到了界面

這篇文章就講到這里,歡迎大家指點和點評!

Struts2框架(5)---result結果集

result結果集

上一篇文章主要講Struts2框架(4)---Action類訪問servlet這篇主要講result結果集

在Struts.xml中的result元素指的是:指定動作類的動作方法執行完后的結果視圖.

(1)局部結果和全局結果

他有兩個屬性: 

  name:字符串,與動作方法返回的值一致。默認是success

  type:指定處理結果的結果類型的別名。默認值是dispatcher

 首先處理結果分為兩種,一種是局部結果一種是全局結果。

  局部結果:

 <action name="login" class="com.study.struts.action2.LoginAction" method="login">
       <!--在action內配置的是針對某個Action起作用的局部的配置 -->
         <result name="success" >/demo2/result.jsp</result> 
 </action>

 全局結果:

復制代碼
 <!--全局結果視圖:包中所有的action都能使用同一個視圖 -->
      <global-results>
       <!--  <result name="success">/index.jsp</result> -->
        <!-- a.默認的結果集類型 -->
       <result name="error" type="dispatcher">/error.jsp</result> 
        <!-- b.轉發到另外一個Action -->
       <!--  <result name="success" type="chain">hello</result> -->
       <!-- c.重定向到jsp頁面 -->
        <!-- <result name="success" type="redirect">/index.jsp</result> -->
        <!-- d.重定向到action -->
        <!-- <result name="success" type="redirectAction">hello</result> -->
      </global-results> 
復制代碼

這里同時要思考一個問題,如果你返回的是success,但在全局和局部都配置了,那么會執行哪個呢?

    按照規則,先看局部變量是否配置,配置了就執行局部變量的,而且一般成功的結果集不會配置成全局的,只有在錯誤(error)的時候可能配置全局

(2)結果類型

在struts-default.xml 配置常用結果類型有10種:

 

 當然在我們實際開發中運用的比較多的也就4.5種,這里我就寫4種

舉例:

復制代碼
 1        <action name="main">
 2             <result type="dispatcher">/main.jsp</result>
 3         </action>
 4         
 5         <action name="main2">
 6             <result type="redirect">/main2.jsp</result>
 7         </action>
 8         
 9         <action name="main3">
10             <result type="chain">main3</result>
11         </action>
12         
13         <action name="main4">
14             <result type="redirectAction">main4</result>
15         </action>
復制代碼

    a)  dispatcher(默認)    forward到一個JSP或者HTML或者其他結果頁面,不能是Action     

          請求轉發,底層調用RequestDispatcher的forward() 方法,dispatcher是result的type屬性默認值,通常用於轉向一個JSP。  

   b)  redirect                    重定向到結果視圖   重定向到一個URL  

          重定向,新頁面無法顯示Action中的數據,因為底層調用  response.sendRedirect("")方法,無法共享請求范圍內的數據。

   c)   chain                      服務器forward(轉發)到一個另一個Action     

        將action的帶着原來的狀態請求轉發到新的action,兩個action共享一個ActionContext,actionName指定轉向的新的Action的名字,method指定轉向哪個方法,

        namespace指定新的Action的名稱空間,不寫表示與原Action在相同的名稱空間;

   d) redirectAction          重定向到另外一個Action 

      重定向到另一個Action,參數與chain用法相同,允許將原Action中的屬性指定新名稱帶入新Action中,可以在Result標簽中添加 <param name=”b”>${a} </param>,

      這表示原Action中的變量a的值被轉給b,下一個Action可以在值棧中使用b來操作

(3)重定向和轉發的區別? 

   1 請求轉發只能將請求轉發給同一個WEB應用中的組件,而重定向還可以重新定向到同一站點不同應用程序中的資源,甚至可以定向到一絕對的URL。

   2 重定向可以看見目標頁面的URL,轉發只能看見第一次訪問的頁面URL,以后的工作都是有服務器來做的。

   3 請求響應調用者和被調用者之間共享相同的request對象和response對象,重定向調用者和被調用者屬於兩個獨立訪問請求和響應過程。

   4 重定向跳轉后必須加上return,要不然頁面雖然跳轉了,但是還會執行跳轉后面的語句,轉發是執行了跳轉頁面,下面的代碼就不會在執行了。

 (4) 結果類型中redirect和redirectAction
  首先要知道:
  只要是重定向,那么之前凡是保存在request里面的東西就全都消失了
  因為重定向實際是發送第二個請求,故請求中的東西也就不會出現在第二個請求里面了
  也就是說重定向是不共享request的東西,重定向后的頁面中無法接收request里的東西
  區別:

  redirect是在處理完當前Action之后,重定向到另外一個實際的物理資源
  redirectAction也是重定向,但它重定向到的是另外一個Action

 (5)思考,在我們實際開發中是么時候使用重定向什么時候轉發?

 我個人觀點:就是你在request作用域進行相關操作后,需要從數據庫返回進行回顯的話,比如說你在點擊修改的時候就需要把信息回顯,這就建議轉發,因為用重定向是無法得到回顯數據

還有你要跳轉到外部網站,比如www.baidu.com,那你就不能用轉發,就指定用重定向,這個上面第一點就說了。

本文章就講到到這里,如果哪里有不足,或者可以修改的更好,歡迎留言指出。

Struts框架(6)---action接收請求參數

action接收請求參數

      在web開發中,去接收請求參數來獲得表單信息非常的常見,自己也總結整理了有關Struts2通過action接收請求參數的幾種方法。

      Struts2 提供三種數據封裝的方式:

            (1)  Action 本身作為model對象,通過成員setter封裝

            (2)  創建獨立model對象,頁面通過ognl表達式封裝

            (3)   使用ModelDriven接口,對請求數據進行封裝(推薦)

     下面我們來講解第一種:

          (1)   Action類本身作為model對象通過成員的setter方法封裝(屬性驅動)

            setXxx()的xxx必須與請求的參數名一樣。就是指和form表單中的name對應的屬性要一致

    action類的代碼:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
import  java.util.Arrays;
import  com.ssh.struts2.model.User;
import  com.opensymphony.xwork2.ActionSupport;
/*
  * 通過這種方法最簡單,但也有缺點如果要把數據封裝到model對象中然后傳遞給業務層和數據層 
  *    還需要單獨定義model對象進行傳遞數據           
  */
public  class  RegisterAction1  extends  ActionSupport {
   
     private  String username;   
     private  String [] hobby;
     
     @Override
     public  String execute()  throws  Exception {
         //獲取表單的數據
         System.out.println( "用戶名是:" +username);
         System.out.println( "興趣愛好是:" +Arrays.toString(hobby));        
         return  null ;
     }
    //這里必須提供set方法,get方法可有可無
     public  void  setUsername(String username) {
         this .username = username;
     }
     public  void  setHobby(String[] hobby) {
         this .hobby = hobby;
     }   
}
/*當你在界面中用戶名輸入:zhangsan,興趣愛好選擇:體育和讀書那么運行結果如下:
  * 用戶名是:zhangsan
  * 興趣愛好是:[sport, read]
  */

struts.xml

1
2
3
4
5
6
7
8
9
10
<? 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"  extends="struts-default">    
         < action  name="register1" class="com.ssh.struts2.action.RegisterAction1">
         </ action >             
     </ package >
</ struts >

register.jsp

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
<%@ page language="java" import="java.util.*" pageEncoding="UTF-8"%>
< html >
   < head >
   </ head >
   < body >
      < h4 >注冊表單1 </ h4 >
      < form  action="${pageContext.request.contextPath }/register1.action" method="post">
            用戶名:< input  type="text" name="username">< br />
           愛好:< input  type="checkbox" name="hobby" value="sport">體育
           < input  type="checkbox" name="hobby" value="music">音樂
           < input  type="checkbox" name="hobby" value="read">讀書  < br />    
           < input  type="submit" value="注冊">
      </ form >
   </ body >
</ html >

  網頁:

      (2)  創建獨立model對象,頁面通過ognl表達式封裝

       該方法首先要創建一個專門的領域對象進行封裝

   User領域對象 

復制代碼
import java.util.Arrays;
public class User {

    private String username;      
    private String [] hobby;
//為這兩個常量提供set和get方法和toString方法
復制代碼

  Action類

 

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
import  com.ssh.struts2.model.User;
import  com.opensymphony.xwork2.ActionSupport;
 
public  class  RegisterAction2  extends  ActionSupport{
     //直接定義model對象
     private  User user;
     @Override
     public  String execute()  throws  Exception {
         System.out.println( "user:" +user);
         return  NONE;
     }  
     /*
      * 必須提供get方法 
      *  封裝第一個參數 創建一個新的User對象    然后把username屬性封裝到這個創建的user對象中    User user =new User();user.setUserName("");
      *  封裝第二個參數    已經存在user對象   User  user =getUser();     user.setPassword(");
      */
     public  User getUser() {
         return  user;
     }
     public  void  setUser(User user) {
         this .user = user;
     }   
}
/*
  * 如果jsp界面輸入:用戶名:aa 興趣愛好:體育讀書
  * 后台輸出:user:User [username=aa, hobby=[sport, music]]
  */

 

register.jsp

復制代碼
 1 <%@ page language="java" import="java.util.*" pageEncoding="UTF-8"%>
 2 <html>
 3   <head>
 4   </head>
 5   <body>
 6   <!-- 用ognl表達式要注意的一點就是,標簽的屬性name在取名字的時候是:領域對象.屬性 
 7    user.username這里user是具體的對象,username是領域對象的屬性-->
 8      <h4>注冊表單1 </h4>
 9      <form action="${pageContext.request.contextPath }/register2.action" method="post">
10            用戶名:<input type="text" name="user.username"><br/>
11           愛好:<input type="checkbox" name="user.hobby" value="sport">體育
12           <input type="checkbox" name="user.hobby" value="music">音樂
13           <input type="checkbox" name="user.hobby" value="read">讀書  <br/>     
14           <input type="submit" value="注冊">
15      </form>
16   </body>
17 </html>
復制代碼

     說明:struts2首先通過反射技術調用User的默認構造器創建User對象,然后通過反射技術調用User中與請求參數同名的屬性的setter方法來獲取請求參數值。在這里需要注意的一點是:User對象一定要有默認的構造器。

采用復合類型接收請求參數的好處,可以減少action中的setter和getter方法,同時可以把相應的屬性組合成一個類,這樣使代碼更好清晰,代碼有更好的結構。

   (3)使用ModelDriven接口,對請求數據進行封裝

 第三種方法比較方便,和方法(1)不同在於它也要先創建一個領域對象類進行對象的封裝。其它和方法(1)一樣

  Action類

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
import  com.ssh.struts2.model.User;
import  com.opensymphony.xwork2.ActionSupport;
import  com.opensymphony.xwork2.ModelDriven;
//實現ModelDriven<User>接口
public  class  RegisterAction3  extends  ActionSupport  implements  ModelDriven<User> {
     /**
      * 方式三 使用模型驅動
      */
     //這里需要注意,方法2中的user對象不需要自己創建,而這里必須手動初始化
     private  User user = new  User();
 
     public  User getModel() {
         return  user;
    
     @Override
     public  String execute()  throws  Exception {
         System.out.println( "user:" +user);
         return  NONE;
    
}
/*
  * 如果jsp界面輸入:用戶名:aa 興趣愛好:體育讀書
  * 后台輸出:user:User [username=aa, hobby=[sport, music]]
  */

  

 最后我們來思考兩個問題,也是常見的筆面試題:

     問題一:Action封裝數據會不會有線程問題? 

     問題二:在使用第一種方式進行封裝的時候數據封裝到Action 屬性中不能把Action傳遞給業務層數據如何傳遞?

  謝謝大家瀏覽,歡迎大家指點!

Struts2系列筆記(7)---Struts2類型轉換

Struts2類型轉換     

       struts2中內置了大量的類型轉換器用來完成數據類型轉換的問題,這篇隨筆主要通過兩個方面來寫Struts類型轉換

       1:Struts2內置的類型轉換器

       2:如何自定義類型轉換器

      那么首先我們來學習有關Struts2內置的類型

         1:Struts2內置的類型轉換器

Struts2的內置類型轉換器,可以為你處理大多數的類型轉換,這包括了以下類型和String類型之間的轉換!

1.String

將int,double,boolean,String類型的數組或java.util.Date類型轉換成字符串。

2:boolean和Boolean

在字符串與boolean之間轉換

3:char/Character

在字符串和字符之間轉換

4:int/Integer,float/Float,long/Long,double/Double 

在字符串與數值類型之間進行轉換 

5:date

在字符串和日期類型之間進行轉換,默認格式是:YYYY-MM-DD

6:數組

由於數組本身就有類型,可以將多個同名參數,轉換到數組中(在之前總結的興趣愛好多選擇,如果你選擇多個,同時他們name屬性相同就自動變為數組)

7:集合

支持將數據保存到 List 或者 Map 集合

關於內置類型轉換器舉例:

 Action類

復制代碼
 1 import java.util.Date;
 2 import com.opensymphony.xwork2.ActionSupport;
 3 
 4 public class CustomerAction extends ActionSupport {
 5 
 6     private String username;
 7 
 8     private int age;
 9 
10     private Date birthday;
11 
12     @Override
13     public String execute() throws Exception {
14         System.out.println("客戶姓名是:" + username + ",年齡是:" + age + ",生日:" + birthday);
15 
16         return NONE;
17     }
18     public void setUsername(String username) {
19         this.username = username;
20     }
21     public void setAge(int age) {
22         this.age = age;
23     }
24     public void setBirthday(Date birthday) {
25         this.birthday = birthday;
26     }
27 }
28 /*控制台輸出結果:客戶姓名是:zhangsan,年齡是:12,生日:Tue Jul 09 00:00:00 CST 1996
29 */
復制代碼

 jsp界面

復制代碼
 1 <%@ page language="java" import="java.util.*" pageEncoding="UTF-8"%>
 2 <html>
 3   <head>
 4   </head>
 5   <body>
 6     <form action="${pageContext.request.contextPath }/customer.action">
 7      客戶姓名:<input type="text" name="username"><br/>
 8      年齡:<input type="text" name="age"><br/>
 9      生日:<input type="text" name="birthday"><br/>
10      <input type="submit" value="提交">     
11     </form>    
12   </body>
13 </html>
復制代碼

 界面輸入:這里年齡只能輸入合法年齡,日期的默認格式:yyyy-MM-dd,如果你輸入不合規則網頁會報錯,比如你輸入1996/7/9頁面就會報錯

     2:如何自定義類型轉換器

       為什么需要自定義類型轉換器,這個問題相信大家都知道,就像我上面所說的,日期的默認格式是yyyy-MM-dd,那如果你想輸入yyyy/mm/dd或者其它的

這個時候就需要你修改你自己的類型轉換器,否則會報錯。下面我寫一個有關自定義類型轉換器的方法: 繼承StrutsTypeConverter

DateConverter 
復制代碼
 1 import java.text.DateFormat;
 2 import java.text.ParseException;
 3 import java.text.SimpleDateFormat;
 4 import java.util.Date;
 5 import java.util.Map;
 6 
 7 import javax.xml.bind.TypeConstraintException;
 8 import org.apache.struts2.util.StrutsTypeConverter;
 9 
10 public class DateConverter extends StrutsTypeConverter {
11     //為方便支持多種日期格式的轉換,可增加時間格式
12     private final DateFormat [] dateformats={
13             new SimpleDateFormat("yyyy-MM-dd"),
14             new SimpleDateFormat("yyyy年MM月dd日"),
15             new SimpleDateFormat("yyyy.MM.dd"),
16             new SimpleDateFormat("yyyy/MM/dd")
17     };
18     /* 將一個或多個字符串值轉換為指定的類型
19      * 
20      */
21     @Override
22     public Object convertFromString(Map arg0, String[] values, Class toType) {
23         //從表單獲取的日期字符串
24         String dateStr = values[0];//思考:這里為什么是數組而不是字符串?我自己也沒有搞明白,希望大神看到后宰評論區給予解答,謝謝
25         for(int i = 0;i<dateformats.length;i++){//遍歷日期類型進行轉換
26             
27             try { //SimpleDateFormat類中parse()方法用於將輸入的特定字符串轉換成Date類的對象
28                 return dateformats[i].parse(dateStr);
29             } catch (Exception e) {
30                 continue; //很關鍵
31             }
32         }
33         throw new TypeConstraintException("遍歷結束仍沒有指定的類型轉換");
34     }
35 
36     /* 將指定對象轉化為字符串
37      * method:這個方法是用來回顯用的,就是你需要回顯成什么樣的格式就可以設置什么樣的格式
38      */
39     @Override
40     public String convertToString(Map context, Object object) {
41         Date date = (Date) object;
42         //指定輸出的格式
43         return new SimpleDateFormat("yyyy年MM月dd日").format(date);
44     }
45 }
46 /*主要講這里的continue,就是如果你是輸入的是1992-2-2,那么dateformats[0]和你直接匹配
47  * 那么直接返回,當如果你開始輸入的是1992/2/2那么就和dateformats[0]不匹配,那么出現異常執行
48  * catch中的內容,而catch中是continue代表終止本次循環進入下一次循環,那么有和dateformats[1]
49  * 進行匹配,如果都不匹配才會異常,所以這里用的太關鍵了
50  *
復制代碼

 Aation(類)

復制代碼
 1 import java.util.Date;
 2 import com.opensymphony.xwork2.ActionSupport;
 3 
 4 public class RegisterAction1 extends ActionSupport {  
 5     private Date brithday1;
 6     private Date brithday2;
 7     private Date brithday3;
 8     private Date brithday4;
 9     /*
10      * 為上面四個提供set和get方法
11      */
12 
13     @Override
14     public String execute() throws Exception {
15         //獲取表單的數據
16        System.out.println("生日1"+brithday1);
17        System.out.println("生日2"+brithday2);
18        System.out.println("生日3"+brithday3);
19        System.out.println("生日4"+brithday4);     
20         return SUCCESS;
21     }
22 } 
23 /*后台輸出結果:
24  * 生日1Sun Feb 02 00:00:00 CST 1992
25  * 生日2Sun Feb 02 00:00:00 CST 1992
26  * 生日3Sun Feb 02 00:00:00 CST 1992
27  * 生日4Sun Feb 02 00:00:00 CST 1992 
28  */
復制代碼

register.jsp(登錄界面)

復制代碼
 1 <html>
 2   <head>
 3     <title>注冊</title>
 4   </head> 
 5   <body>
 6      <!-- 這里有四個生日 -->
 7      <form action="${pageContext.request.contextPath }/register1.action" method="post">
 8             生日1:<input type="text" name="brithday1"><br/><br/>
 9             生日2:<input type="text" name="brithday2"><br/><br/>
10             生日3:<input type="text" name="brithday3"><br/><br/>
11             生日4:<input type="text" name="brithday4"><br/><br/>
12           <input type="submit" value="注冊">
13      </form>
14   </body>
15 </html>
復制代碼

struts.xml

復制代碼
 1 <?xml version="1.0" encoding="UTF-8" ?>
 2 <!DOCTYPE struts PUBLIC
 3     "-//Apache Software Foundation//DTD Struts Configuration 2.3//EN"
 4     "http://struts.apache.org/dtds/struts-2.3.dtd">
 5 <struts>
 6     <!-- 開發者模式 -->
 7     <constant name="struts.devMode" value="true"></constant>
 8     
 9     <package name="default"  extends="struts-default">    
10         <action name="register1" class="com.guigu.struts2.action.RegisterAction1">
11            <result>/result.jsp</result>
12         </action>
13     </package>
14 </struts>
復制代碼
result.jsp
復制代碼
 1 <%@ page language="java" import="java.util.*" pageEncoding="UTF-8"%>
 2 <%@ taglib uri="/struts-tags"  prefix="s"%>
 3 <html>
 4   <head>
 5   </head>
 6   <body>
 7   <!-- 回顯的時候發現盡管前面輸入格式不一樣,但輸出格式是一樣的 -->
 8   生日1:<s:property value="brithday1"/><br/>
 9   生日2:<s:property value="brithday2"/><br/>
10   生日3:<s:property value="brithday3"/><br/>
11   生日4:<s:property value="brithday4"/><br/> 
12   </body>
13 </html>
復制代碼
界面:

最終返回界面:

注意:這中間還有很重要的東西需要配置:配置轉換器

4、配置轉換器
     Struts2提供了兩種方式配置轉換器
方式一:應用於全局范圍的類型轉換器,在src目錄下創建xwork-conversion.properties
     轉換類全名=類型轉換器類全名
    java.util.Date=com.sytudy.struts2.action.DateConverter  (前面是你需要轉換的類型,后面是 類型轉換器類
方式二:應用於特定類的類型轉換器,在特定類的相同目錄下創建一個名為ClassName-conversion.properties的屬性文件
     特定Action類的屬性名=類型轉換器類全名  

  這篇文字就講到這里,如果哪里有不足,歡迎大家指點,謝謝

 

Struts2框架(8)---Struts2的輸入校驗

Struts2的輸入校驗

在我們項目實際開發中在數據校驗時,分為兩種,一種是前端校驗,一種是服務器校驗:

   客戶端校驗:主要是通過jsp寫js腳本,它的優點很明顯,就是輸入錯誤的話提醒比較及時,能夠減輕服務器的負擔,但是客戶端校驗並不是安全的,簡單來講就是防君子防不了小人。

   服務器端校驗:最大特點就是數據安全,但是如果只有服務器端校驗,會大大增加服務器端的負擔。

所以一般在我們開發中,是客戶端和服務器端校驗相結合作用的。

那這篇文章,我只講服務器端校驗,在Struts2支持兩種校驗方式:

    代碼校驗 :在服務器通過編輯java代碼完成數據校驗

   配置校驗: xml配置校驗 通過xml配置文件完成數據的校驗

(1)代碼校驗:

    代碼校驗分為三個步驟:  

步驟一、封裝數據

步驟二、實現要校驗的Action  必須繼承ActionSupport

步驟三、覆蓋Validate方法  然后完成業務邏輯數據的校驗

用戶界面 register.jsp

復制代碼
 1 <%@ page language="java" import="java.util.*" pageEncoding="UTF-8"%>
 2 <%@ taglib uri="http://java.sun.com/jsp/jstl/core"  prefix="c"%>
 3 <%@ taglib uri="/struts-tags" prefix="s" %>
 4 <html>
 5   <head>
 6     <title>用戶注冊</title>
 7   </head> 
 8   <body style="text-align: center;">
 9     <table align="center" width="50%">
10         <tr>
11             <td style="color: red">
12                 <!-- <s:fielderror></s:fielderror>  --> <!-- 這里是顯示錯誤的地方 -->
13             </td>
14         </tr>  
15     </table>
16   
17         <form action="${pageContext.request.contextPath }/login" method="post"  >
18         
19             用戶名:<input type="text"  name="username"><br><br>
20             密     碼:<input type="text"  name="password"><br><br>
21                     確認密碼:<input type="text"  name="password2"><br><br>
22                         <input type="reset" value="清空">
23                         <input type="submit" value="注冊">
24                 
25         </form>
26   </body>
27 </html>
復制代碼

struts.xml

復制代碼
 1 <?xml version="1.0" encoding="UTF-8" ?>
 2 <!DOCTYPE struts PUBLIC
 3     "-//Apache Software Foundation//DTD Struts Configuration 2.3//EN"
 4     "http://struts.apache.org/dtds/struts-2.3.dtd">
 5 <struts>  
 6       <!-- 配置常量信息 -->
 7       <constant name="struts.devMode" value="true"></constant>       
 8       
 9      <package name="struts2" extends="struts-default" >
10          <action name="login" class="com.study.Login.RegisterAction">
11          <result name="success">/success.jsp</result>
12          <!-- 在input視圖中可以通過<s:fielderror/>顯示失敗信息 -->
13          <result name="input">/register.jsp</result>
14          </action>
15      </package>         
16 </struts>
復制代碼
RegisterAction.java
復制代碼
 1 import com.opensymphony.xwork2.ActionSupport;
 2 public class RegisterAction extends ActionSupport{
 3 
 4     private String username;
 5     private String password;
 6     private String password2;
 7     //這里我通過set方法封裝數據    
 8   public void setUsername(String username) {
 9         this.username = username;
10     }
11     public void setPassword(String password) {
12         this.password = password;
13     }
14     public void setPassword2(String password2) {
15         this.password2 = password2;
16     }
17 
18     @Override
19     public String execute() throws Exception {
20         return NONE;
21     }
22     
23     //在服務器端需要完成對數據的校驗
24     @Override
25     public void validate() {
26         //測試是否得到屬性值,證實已經得到
27     System.out.println(username+"---"+password+"---"+password2);
28     if(username==null || username.length()<6 || username.length()>20){
29         //把錯誤信息保存到字段中
30         this.addFieldError("username", "有戶名輸入不合法");
31     }
32     
33     if(password==null || password.length()<6 || password.length()>20){
34         //把錯誤信息保存到字段中
35         this.addFieldError("password", "密碼輸入不合法");
36     }else if( password2==null || password2.length()<6 || password2.length()>20){
37         this.addFieldError("password2", "密碼輸入不合法");
38     }else if(!password.equals(password2)){
39         this.addFieldError("password2", " 兩次密碼不一致");
40     }
41     
42         super.validate();
43     }
44 }
復制代碼
運行結果:

 (2)框架校驗

 框架校驗也就是通過XML配置方式進行數據校驗 ,這也是我們在企業開發的主流校驗。

XML校驗原理: 將很多規則代碼已經寫好只需要在xml文件中定義需要使用的校驗規則即可。,所以大大減少了我們的開發時間。

 我先把步驟寫一下:

     步驟一:編寫JSP

     步驟二:編寫Action 繼承ActionSupport或者Validateable接口

   步驟三:封裝請求參數

   步驟四:編寫xml校驗規則文件

    Xml校驗文件的命名規則:   Action類名-validation.xml 對Action中所有的方法都執行校驗

      舉例命名規則RegisterAction-validation.xml

       同時要滿足:Xml校驗文件和Action類要在同一包下

 步驟一: register.jsp

  register.jsp

   步驟二:RegisterAction.java

復制代碼
import com.opensymphony.xwork2.ActionSupport;
import com.opensymphony.xwork2.ModelDriven;
public class RegisterAction extends ActionSupport implements ModelDriven<User>{

 //手動創建一個對象
    private User user =new User();

    @Override
    public String execute() throws Exception {
        return NONE;
    }

    public User getModel() {
        return user;
    }        
}
復制代碼

步驟三:封裝請求參數

上面手動校驗的案例我是用set方法封裝數據,那這里我采用的是使用ModelDriven接口,對請求數據進行封裝,

在之前我講過封裝數據的三種方法不清楚的可以看下這篇文章:Struts框架(6)---action接收請求參數

User.java

復制代碼
 1 import java.util.Date;
 2 public class User {
 3     
 4     private String username;
 5     private String password;
 6     private String password2;
 7     private Integer age;
 8     private String email;
 9     private Date birthday;
10     private Date graduation;
11     
12     /*
13      * 給屬性提供get和set方法
14      */
15 }
復制代碼

 步驟四:RegisterAction-validation.xml

復制代碼
<!DOCTYPE validators PUBLIC
        "-//Apache Struts//XWork Validator 1.0.2//EN"
        "http://struts.apache.org/dtds/xwork-validator-1.0.2.dtd">
 <validators>
  <!--dtd約束在xwork-core-**.jar包中 -->   
      <field name="username">
              <field-validator type="requiredstring">
                  <param name="trim">true</param>
                  <message>用戶民不能為空</message>
              </field-validator>
              
              <field-validator type="stringlength">
                <param name="minLength">6</param>
                <param name="maxLength">15</param>
                <message>有戶名長度必須在 ${minLength} 和 ${maxLength}之間 </message>
              </field-validator>
      </field> 
      
      
        <field name="password">
              <field-validator type="requiredstring">
                  <param name="trim">true</param>
                  <message>密碼不能為空</message>
              </field-validator>
              
              <field-validator type="stringlength">
                <param name="minLength">6</param>
                <param name="maxLength">15</param>
                <message>密碼必須在 ${minLength}和${maxLength}之間 </message>
              </field-validator>
       </field> 
       
      <field name="password2">
          <field-validator type="fieldexpression">
             <param name="expression"><![CDATA[password==password2]]></param>
             <message>兩次密碼不一致</message>
          </field-validator>
      </field>
      
      <field name="age">
          <field-validator type="required">
              <param name="trim">true</param>
              <message>年齡不能為空</message>
          </field-validator>
          <field-validator type="int">
              <param name="min">1</param>
              <param name="max">150</param>
              <message>年齡必須在 ${min} 和 ${max}之間</message>
          </field-validator>
        
      </field>
      
      <field name="email">
           <field-validator type="email">
               <message>不是一個合法的郵箱地址</message>
           </field-validator>
      </field>
      
       <field name="birthday">
          <field-validator type="date">
              <param name="min">2001-01-01</param>
              <param name="max">2003-12-31</param>
              <message>生日必須在 ${min} 和${max}之間</message>
          </field-validator>        
      </field> 
      
 </validators>
復制代碼

struts.xml不需要任何改變,和之前一樣就可以了

運行結果:

   如果你覺得提示錯誤的位置有點丑,那你可以運用Struts2的<s:form>標簽,效果會更好

現在兩種方式都講了,現在對xml配置的要點一些知識要點進行歸納。

xml校驗文件詳解:  

<validators>: 根元素

<field>:指定action中要校驗的屬性,name屬性指定將被驗證的表單字段的名字

<field-validator>:指定校驗器, type 指定驗證規則

     上面指定的校驗器requiredstring是由系統提供的,系統提供了能滿足大部分驗證需求

      的校驗器,這些校驗器的定義可以在xwork-2.x.jar中的

      com.opensymphony.xwork2.validator.validators下的default.xml中找到。

<param>:子元素可以向驗證程序傳遞參數

<message>:子元素為校驗失敗后的提示信息,如果需要國際化,可以為message

                          指定key屬性,key的值為屬性文件中的key。

struts2校驗規則:

系統提供的校驗器如下:

required (必填校驗器,要求被校驗的屬性值不能為null)

requiredstring (必填字符串校驗器,要求被校驗的屬性值不能為null,並且長度大於0,默認情況下會對字符串去前后空格)

stringlength(字符串長度校驗器,要求被校驗的屬性值必須在指定的范圍內,否則校驗失敗,minLength參數指定最小長度,maxLength參數指定最大長度,trim參數指定校驗field之前是否去除字符串前后的空格)

regex(正則表達式校驗器,檢查被校驗的屬性值是否匹配一個正則表達式,expression參數指定正則表達式,caseSensitive參數指定進行正則表達式匹配時,是否區分大小寫,默認值為true)

int(整數校驗器,要求field的整數值必須在指定范圍內,min指定最小值,max指定最大值)

double(雙精度浮點數校驗器,要求field的雙精度浮點數必須在指定范圍內,min指定最小值,max指定最大值)

fieldexpression(字段OGNL表達式校驗器,要求field滿足一個ognl表達式,expression參數指定ognl表達式,該邏輯表達式基於ValueStack進行求值,返回true時校驗通過,否則不通過)

email(郵件地址校驗器,要求如果被校驗的屬性值非空,則必須是合法的郵件地址)

url(網址校驗器,要求如果被校驗的屬性值非空,則必須是合法的url地址)

date(日期校驗器,要求field的日期值必須在指定范圍內,min指定最小值,max指定最大值)

conversion(轉換校驗器,指定在類型轉換失敗時,提示的錯誤信息)

visitor(用於校驗action中復合類型的屬性,它指定一個校驗文件用於校驗復合類型屬性中的屬性)

expression(OGNL表達式校驗器,它是一個非字段校驗器, expression參數指定ognl表達式,該邏輯表達式基於ValueStack進行求值,返回true時校驗通過,否則不通過,該校驗器不可用在字段校驗器風格的配置中)

 

最后講一個細節:

編寫校驗文件時,不能出現幫助信息

在編寫ActionClassName-validation.xml校驗文件時,如果出現不了幫助信息,可以按下面方式解決:

windwos->preferences->myeclipse->files and editors->xml->xmlcatalog

點“add”,在出現的窗口中的location中選“File system”,然后在xwork-2.1.2解壓目錄的src\java目錄中選擇xwork-validator-1.0.3.dtd,

回到設置窗口的時候不要急着關閉窗口,應把窗口中的Key Type改為URI 。Key改為http://struts.apache.org/dtds/xwork-validator-1.0.2.dtd 

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM