Struts2總結 – JAVA編程語言程序開發技術文章

Struts2
1.    搭建Struts2的開發環境:
1)       導入相應的jar包;6個
2)       編寫struts的配置文件;struts.xml
3)       struts2在web中的啟動配置;web.xml
2.    第一個struts2應用
3.    actin屬性的註入message是action中的變量
<paramname="message">註入參數的值</param>
4.    編寫自定義類型轉換器:建立自定義局部類型轉換器,處理日期類型,通過繼承DefaultTypeConverter,(推薦使用StrutsTypeConverter,它繼承瞭DefaultTypeConverter)實現自己的DateTypeConverter,並且在action所在的包下創建HelloWorldAction3-conversion.properties文件;在文件中編寫對應關系:birthday=com.lcq.type.converter.DateTypeConverter
將轉換的屬性和轉換器進行綁定。如果是全局,類型轉換器就要將properties文件放置在src的根目錄下,同時修改文件的名稱為:xwork-conversion.properties,修改裡邊的內容為:要轉換的變量的類型=轉換器的名稱,
轉換器的編寫:
[java]
/**
 * 建立自定義類型轉換器,處理日期類型,通過繼承DefaultTypeConverter,實現自己的DateTypeConverter
 * @author lcq
 *
 */ 
public class DateTypeConverter extends DefaultTypeConverter { 
  
    @Override 
    public Object convertValue(Map<String, Object> context, Objectvalue, 
           Class toType) { 
       SimpleDateFormat dateFormat = new SimpleDateFormat("yyyyMMdd"); 
       try { 
           if (toType == Date.class) { 
              String[] params = (String[]) value; 
              return dateFormat.parse(params[0]); 
           } else if (toType == String.class) { 
              Date date = (Date) value; 
              return dateFormat.format(date); 
           } 
       } catch (ParseException e) { 
           // TODO Auto-generatedcatch block 
           e.printStackTrace(); 
       } 
       return super.convertValue(context, value, toType); 
    } 
  

  

例如定義的action為:
[java]
package com.lcq.action; 
  
import java.util.Date; 
  
public class HelloWorldAction3 { 
    private Date birthday; 
  
    public Date getBirthday() { 
       return birthday; 
    } 
  
    public void setBirthday(Date birthday) { 
       this.birthday = birthday; 
    } 
  
    public String addUI(){ 
    
       return "success"; 
    } 
  
    public String execute(){ 
       
       return "success"; 
    } 
  

5.    訪問和添加request/session/application屬性,並在頁面進行打印輸出
    //從struts2封裝的ActionContext中獲取request/session/application
 
[java]
ActionContext ctx = ActionContext.getContext(); 
 ctx.getApplication().put("app", "application scope"); 
 ctx.getSession().put("session", "sessionscope"); 
 ctx.put("request", "request scope"); 

jsp中:
[java]
${applicationScope.app }<br> 
       ${sessionScope.session }<br> 
       ${requestScope.request }<br> 

6.    得到request/session/application對象:
在action中利用ServletActionContext.getxxxx()方法得到
7.    文件上傳實現:
1)上傳頁面:upload.jsp
[java]
<form enctype="multipart/form-data" action="${pageContext.request.contextPath}/employee/upload.action" method="post"> 
    
    file:<input type="file"name="image"> 
    <input type="submit" value="upload"> 
    </form> 

2) xml中的配置
[html]
<action name="upload" class="com.lcq.action.FileUpLoadAction" 
           method="execute"> 
           <result name="success">/WEB-INF/page/uploadMessage.jsp</result> 
       </action> 

3)Action中的方法
[java]
public String execute() throws Exception{ 
       //構建真實的存放路徑 
       String realPath = ServletActionContext.getServletContext().getRealPath("/image"); 
       System.out.println(realPath); 
       if(image != null){ 
       File savefile = new File(new File(realPath),imageFileName); 
       if(!savefile.getParentFile().exists()){ 
           savefile.getParentFile().mkdirs(); 
       } 
       FileUtils.copyFile(image, savefile); 
       
       ActionContext.getContext().put("message", "上傳成功"); 
       
       } 
       return "success"; 

4)結果頁面輸出上傳信息
[html]
<body> 
message } 
 
</body> 

8.    多文件上傳隻要修改為:同時在action中將相應的參數變為數組即可
 
[html]
<form enctype="multipart/form-data"   action="${pageContext.request.contextPath}/employee/upload.action" method="post"> 
  
  file1:<input type="file"name="image"><br> 
     file2:<input type="file"name="image"><br> 
         file3:<input type="file"name="image"><br> 
  <input type="submit" value="upload"> 

action中
 
[java]
  private File[] image;// 定義上傳文件的文件屬性 
    private String[] imageFileName;// 得到文件的名稱 
…….. 
…….. 
…….. 
  
public String execute() throws Exception { 
       // 構建真實的存放路徑 
       StringrealPath = ServletActionContext.getServletContext().getRealPath( 
              "/image"); 
       System.out.println(realPath); 
       if (image != null) { 
           for (int i = 0; i < image.length; i++) { 
              Filesavefile = new File(new File(realPath), imageFileName[i]); 
              if(!savefile.getParentFile().exists()) { 
                  savefile.getParentFile().mkdirs(); 
              } 
              FileUtils.copyFile(image[i], savefile); 
           } 
           ActionContext.getContext().put("message", "上傳成功"); 
  
       } 
       return "success"; 
    } 

9.    編寫自定義攔截器:
1)       繼承自Interceptor接口來實現。
[java]
public class PermissionInterceptor implements Interceptor { 
  
    public void destroy() { 
    } 
  
    public void init() { 
    } 
  
    public String intercept(ActionInvocation invocation) throws Exception { 
       Object user = ActionContext.getContext().getSession().get("user"); 
       if(user!=null) return invocation.invoke(); //如果user不為null,代表用戶已經登錄,允許執行action中的方法 
       ActionContext.getContext().put("message", "你沒有權限執行該操作"); 
       return "success"; 
    } 
  

2)       在xml中的配置為:
[html]
<interceptors> 
           <interceptor name="permission" 
              class="com.lcq.Interceptor.PermissionInterceptor" /> 
           <interceptor-stack name="permissionStack"> 
              <interceptor-ref name="defaultStack" /> 
              <interceptor-ref name="permission" /> 
           </interceptor-stack> 
       </interceptors> 
       
       <global-results> 
           <result name="success">/WEB-INF/page/message.jsp</result> 
       </global-results> 
  
       <action name="userAction" class="com.lcq.action.UserAction" 
           method="execute"> 
           <interceptor-ref name="permissionStack" /> 
       </action> 

10. 對action的所有方法進行輸入校驗
1)       要進行驗證的內容:
[html]
<body> 
    <s:fielderror/> 
    <form action="${pageContext.request.contextPath}//person/manage_save" method="post"> 
    用戶名:<input type="text"name="username">用戶名不能為空<br> 
    手機號:<input type="text"name="mobile">不能為空,並且要符合手機號的格式1,3/5/8,後面是9個數字<br> 
    <input type="submit" value="提 交"> 
    </form> 
  </body> 

2)       在action中繼承ActionSupport重寫validate()方法:
[java]
@Override 
    public void validate() {//對action的所有方法進行校驗 
       if(this.username == null || "".equals(this.username.trim())){ 
           this.addFieldError("username", "用戶名不能為空"); 
       } 
       if(this.mobile == null || "".equals(this.mobile.trim())){ 
           this.addFieldError("mobile", "手機號不能為空"); 
       }else{ 
           if(!Pattern.compile("^1[358]\\d{9}{1}quot;).matcher(this.mobile).matches()){ 
              this.addFieldError("mobile", "手機號格式不對"); 
           } 
       } 
  
    
    } 

3)       在validate方法中將錯誤信息放在錯誤集合中,轉到input頁面,所以在xml中的配置是:
[html]
<struts> 
    <package name="person" namespace="/person" extends="struts-default"> 
       <action name="manage_*" class="com.lcq.action.PersonAction" 
           method="{1}"> 
           <result name="input">/index.jsp</result> 
           <result name="message">/WEB-INF/page/message.jsp</result> 
       </action> 
    </package> 
</struts> 

4)       如果隻是對個別的方法進行校驗則隻要改正validate方法為validateXxxx()就行,其中Xxxx是要校驗的方法的名稱。
[java]
public void validateUpdate() {//對action的update()方法進行校驗 
       if(this.username == null || "".equals(this.username.trim())){ 
           this.addFieldError("username", "用戶名不能為空"); 
       } 
       if(this.mobile == null || "".equals(this.mobile.trim())){ 
           this.addFieldError("mobile", "手機號不能為空"); 
       }else{ 
           if(!Pattern.compile("^1[358]\\d{9}{1}quot;).matcher(this.mobile).matches()){ 
              this.addFieldError("mobile", "手機號格式不對"); 
           } 
       } 
  
    
    } 

11. 基於xml的輸入校驗
1)       隻要在要校驗的action所在包下建立相應的action的xml驗證文件即可,在xml中編寫:
2)       如果隻是對action中的指定方法進行校驗則隻要修改xml的文件名即可,修改為PersonAction-person-manage_update-validation.xml則該文件隻對action中的update方法進行校驗
[html]
<validators> 
    <field name="username"> 
        <field-validator type="requiredstring"> 
            <param name="trim">true</param> 
            <message>用戶名不能為空!</message> 
        </field-validator> 
    </field> 
    <field name="mobile"> 
        <field-validator type="requiredstring"> 
            <message>手機號不能為空!</message> 
        </field-validator> 
        <field-validator type="regex"> 
            <param name="expression"><![CDATA[^1[358]\d{9}$]]></param> 
            <message>手機號格式不正確!</message> 
       </field-validator> 
    </field> 
</validators> 

12. struts2對異常的處理機制,要編寫自己的異常處理類,在struts.xml中進行配置。
13. OGNL表達式語言。www.aiwalls.com
14. EL表達式:${username}可以訪問值棧(action。。。)對象中的所有屬性,是因為struts2對HttpServletRequest對象進行瞭封裝,但是不能訪問:request、application、session、parameters、attr等對象。如果要訪問這些對象,要使用#語法進行訪問,比如:#application.username或者#application[‘username’],特別註意在EL表達式中隻能使用值棧中屬性。
15. ognl表達式進行迭代和投影。並且能夠使用集合。
16. 可以不用ognl表達式,直接用jstl和el結合來代替使用。
17. 利用token標簽防止表單的重復提交問題
1)在jsp頁面的表單中添加<s:token></s:token>;
2)在對應的action中添加攔截器和不跳轉對應的頁面:
           <interceptor-ref name="defaultStack" />
           <interceptor-ref name="token" />
           <result name="invalid.token">/updatePerson.jsp</result>

摘自 liuchangqing123

發佈留言