隨筆 - 147  文章 - 71  trackbacks - 0
          <2009年2月>
          25262728293031
          1234567
          891011121314
          15161718192021
          22232425262728
          1234567

          常用鏈接

          留言簿(1)

          隨筆分類(146)

          隨筆檔案(147)

          文章分類(28)

          文章檔案(28)

          喜歡的Blog

          搜索

          •  

          最新評論

          閱讀排行榜

          評論排行榜

          本系列教程將詳細(xì)介紹Struts 1.x的基本原理和使用方法,讀者可以參閱Struts 2系列教程》來比較Struts 1.xStruts 2.x的相同點(diǎn)和不同點(diǎn)。
             在這篇文章中將以一個簡單的例子
          (mystruts)來演示如何使用MyEclipse來開發(fā)、運(yùn)行Struts程序,并給出了解決ActionForm出現(xiàn)亂碼問題的方法。讀者可以從本文中了解開發(fā)Struts 1.x程序的基本過程。

          一、本文給出的程序要實(shí)現(xiàn)什么功能


              mystruts是一個錄入和查詢產(chǎn)品信息的程序。為了方便起見,本例中的產(chǎn)品信息表只包括了產(chǎn)品ID、產(chǎn)品名稱和產(chǎn)品價格三個字段。mystruts的主要功能如下:
            

          1. 接受用戶輸入的產(chǎn)品ID、產(chǎn)品名稱和產(chǎn)品價格。

          2. 驗(yàn)證這些字段的合法性。如果某些字段的輸入不合法(如未輸入產(chǎn)品ID),程序會forward到一個信息顯示頁,并顯示出錯原因。

          3. 如果用戶輸入了正確的字段值,程序會將這些字段值保存到數(shù)據(jù)庫中,并顯示“保存成功”信息。

          4. 用戶輸入產(chǎn)品名稱,并根據(jù)產(chǎn)品名稱進(jìn)行模糊查詢。如果存在符合要求的產(chǎn)品信息。程序會以表格形式顯示這些產(chǎn)品的信息,同時顯示記錄數(shù)。如果未查到任何記錄,會顯示“沒有符合要求的記錄!”信息。

          二、編寫程序前的準(zhǔn)備工作

          1. 建立數(shù)據(jù)庫

              在編寫程序之前,需要建立一個數(shù)據(jù)庫(struts)和一個表(t_products),建立數(shù)據(jù)庫和表的SQL腳本如下所示:

            # 建立數(shù)據(jù)庫struts
            
          CREATE DATABASE IF NOT EXISTS struts DEFAULT CHARACTER SET GBK;

            # 建立表t_products
            
          CREATE TABLE IF NOT EXISTS struts.t_products (
              product_id 
          varchar(4NOT NULL,
              product_name 
          varchar(50NOT NULL,
              price 
          float NOT NULL,
              
          PRIMARY KEY  (product_id)
            ) ENGINE
          =InnoDB DEFAULT CHARSET=gbk;

          建立一個支持struts1.xsamples工程

             
          MyEclipse建立一個samples工程(Web工程),現(xiàn)在這個samples工程還不支持Struts1.x(沒有引入相應(yīng)的Struts jar包、struts-config.xml文件以及其他和Struts相關(guān)的配置)。然而,在MyEclipse中這一切并不需要我們手工去加入。而只需要使用MyEclipse的【New Struts Capabilities】對話框就可以自動完成這些工作。

              首先選中samples工程,然后在右鍵菜單中選擇【MyEclipse > New Struts Capabilities】,啟動【New Struts Capabilities】對話框。對默認(rèn)的設(shè)置需要進(jìn)行如下的改動:

          (1)將Struts specification改為Struts 1.2。

          (2)Base package for new classes改為struts

          (3)Default application resources改為struts.ApplicationResources。

          改完后的【New Struts Capabilities】對話框如圖1所示。



          圖1

             在設(shè)置完后,點(diǎn)擊Finish按鈕關(guān)閉對話框。在向samples工程添加支持Struts的功能后,主要對samples工程進(jìn)行了三個操作。

          1)引入了Struts 1.2 jar包(在samples的工程樹中多了一個Struts 1.2 Libraries節(jié)點(diǎn))。

          2)在WEB-INF目錄中添加了一個struts-config.xml文件。文件的默認(rèn)內(nèi)容如下面的代碼所示:

            <?xml version="1.0" encoding="UTF-8"?>
            
          <!DOCTYPE struts-config PUBLIC "-//Apache Software Foundation//DTD Struts Configuration 1.2//EN"
          "http://struts.apache.org/dtds/struts-config_1_2.dtd"
          >  
            
          <struts-config>
              
          <data-sources />
              
          <form-beans />
              
          <global-exceptions />
              
          <global-forwards />
              
          <action-mappings />
              
          <message-resources parameter="struts.ApplicationResources" />
            
          </struts-config>

          3)在WEB-INF中的web.xml文件中添加了處理Struts動作的ActionServlet的配置,代碼如下:

          <servlet>
              
          <servlet-name>action</servlet-name>
              
          <servlet-class>org.apache.struts.action.ActionServlet</servlet-class>
              
          <init-param>
                
          <param-name>config</param-name>
                
          <param-value>/WEB-INF/struts-config.xml</param-value>
              
          </init-param>
              
          <init-param>
                
          <param-name>debug</param-name>
                
          <param-value>3</param-value>
              
          </init-param>
              
          <init-param>
                
          <param-name>detail</param-name>
                
          <param-value>3</param-value>
              
          </init-param>
              
          <load-on-startup>0</load-on-startup>
            
          </servlet>
            
          <servlet-mapping>
              
          <servlet-name>action</servlet-name>
              
          <url-pattern>*.do</url-pattern>
            
          </servlet-mapping>

              到目前為止,samples工程已經(jīng)完全支持Struts了。讀者可以看到,如果不使用MyEclipse,那么上面所列出的配置文件的內(nèi)容都必須手工輸入。因此,使用MyEclipse來開發(fā)Struts程序可以省去很多配置xml文件的工作。

          三、實(shí)現(xiàn)程序的首頁(index.jsp)

              首先在<samples工程目錄>中建立一個mystruts目錄,然后在<samples工程目錄>" mystruts目錄中建立一個index.jsp文件,這個文件的內(nèi)容如下。

            <%@ page pageEncoding="GBK"%>
            
          <%-- 引用Struts tag--%>
            
          <%@ taglib uri="http://struts.apache.org/tags-html" prefix="html"%>
            
          <html>
                
          <head>
                    
          <title>主界面</title>
                
          </head>
                
          <body>
                    
          <table align="center" cellpadding="10" width="100%">
                        
          <tr>
                            
          <td align="right" width="50%">
                            
          <%-- 使用Struts tag--%>
                                
          <html:link forward="newProduct">錄入產(chǎn)品信息</html:link>
                            
          </td>
                            
          <td>
                                
          <html:link forward="searchProduct">查詢產(chǎn)品信息</html:link>
                            
          </td>
                        
          </tr>
                    
          </table>
                
          </body>
            
          </html>

              MyEclipse中啟動Tomcat(如果Tomcat處于啟動狀態(tài),在修改完配置文件后,建議在MyEclipseServers頁重新發(fā)布samples工程,以使修改生效)。在IE中輸入如下的URL

          http://localhost:8080/samples/mystruts/index.jsp

              我們發(fā)現(xiàn)在輸入上面的URL后,在IE中并未顯示正確的運(yùn)行結(jié)果,而是拋出了如下的異常:

          java.net.MalformedURLException: Cannot retrieve ActionForward named newProduct

             
          這個異常表明程序并未找到一個叫newProductforwardforward將在后面詳細(xì)地講述)。因此,可以斷定,在JSP中使用forward時,這個forward必須存在。下面我們來添加index.jsp頁面中所使用的兩個forwardnewProductsearchProduct。這兩個forward分別引向了建立產(chǎn)品信息的頁面(newProduct.jsp)和查詢產(chǎn)品信息的頁面(searchProduct.jsp)。我們可以在struts-config.xml文件中<struts-config>節(jié)點(diǎn)中添加兩個全局的forward,代碼如下:

            <global-forwards>
                <forward name="newProduct" path="/mystruts/newProduct.jsp" />
                <forward name="searchProduct" path="/mystruts/searchProduct.jsp" />
          </global-forwards>

              上面的代碼中所示的newProduct.jspsearchProduct.jsp目前并不存在(將在以后實(shí)現(xiàn)這兩個JSP頁面),現(xiàn)在重新輸入上述的URL,會得到如圖2所示的效果。



          圖2

              如果想讓index.jsp成為默認(rèn)的JSP頁面,可以在web.xml中的<welcome-file-list>節(jié)點(diǎn)中加入如下的內(nèi)容:

           <welcome-file>index.jsp</welcome-file>

              這時在IE中只要輸入如下的URL就可以訪問index.jsp頁面了。

          http://localhost:8080/samples/mystruts

          四、實(shí)現(xiàn)添加和查詢產(chǎn)品信息頁面

             
          在本節(jié)中主要實(shí)現(xiàn)了用于輸入產(chǎn)品信息(newProduct.jsp)和查詢產(chǎn)品信息(searchProduct.jsp)JSP頁面。

              newProduct.jsp頁面中有一個form,在form中含有三個文本框,用于分別輸入產(chǎn)品ID、產(chǎn)品名稱和產(chǎn)品價格。
          <samples工程目錄>"mystruts目錄中建立一個newProduct.jsp文件,代碼如下:

            <%@ page pageEncoding="GBK"%>
            
          <%@ taglib uri="http://struts.apache.org/tags-html" prefix="html"%>
            
          <html>
                
          <head>
                    
          <title>錄入產(chǎn)品信息</title>
                
          </head>
                
          <body>
                    
          <%-- 向saveProduct動作提交產(chǎn)品信息 --%>
                    
          <html:form action="saveProduct"> 
                        
          <table width="100%">
                            
          <tr>
                                
          <td align="center">
                                    產(chǎn)品編號:
                                    
          <html:text property="productID" maxlength="4" />
                                    
          <p>
                                        產(chǎn)品名稱:
                                        
          <html:text property="productName" />
                                    
          <p>
            
                                        產(chǎn)品價格:
                                        
          <html:text property="price" />
                                
          </td>
                            
          </tr>
                            
          <tr>
                                
          <td align="center">
                                    
          <br>
                                    
          <html:submit value=" 保存 " />
                                
          </td>
                            
          </tr>
                        
          </table>
                    
          </html:form>
                
          </body>
            
          </html>

              searchProduct.jsp頁面中有一個form,為了方便起見,在form中只提供了一個文本框用于對產(chǎn)品名稱進(jìn)行模糊查詢。在<samples工程目錄>" mystruts目錄中建立一個searchProduct.jsp文件,代碼如下:

            <%@ page pageEncoding="GBK"%>
            
          <%@ taglib uri="http://struts.apache.org/tags-html" prefix="html"%>
            
          <html>
                
          <head>
                    
          <title>查詢產(chǎn)品信息</title>
                
          </head>
                
          <body>
                    
          <%--  向searchProduct動作提交查詢請求 --%>
                    
          <html:form action="searchProduct">
                        
          <table width="100%">
                            
          <tr>
                                
          <td align="center">
                                    產(chǎn)品名稱:
                                    
          <html:text property="productName" />
                                
          </td>
                            
          </tr>
                            
          <tr>
                                
          <td align="center">
                                    
          <br>
                                    
          <html:submit value=" 查詢 " />
                                
          </td>
                            
          </tr>
                        
          </table>
                    
          </html:form>
                
          </body>
            
          </html>

              現(xiàn)在啟動Tomcat,并使用如下兩個URL來訪問newProduct.jspsearchProduct.jsp

          http://localhost:8080/samples/mystruts/newProduct.jsp
          http://localhost:8080/samples/mystruts/searchProduct.jsp

          IE中輸入上面的兩個URL后,并不能顯示出相應(yīng)的界面,而會拋出JspException異常,表明未找到saveProductsearchProduct動作。從這一點(diǎn)可以看出,如果在JSP中使用Struts Action,這些Action必須事先在struts-config.xml文件中定義,否則,JSP程序就無法正常訪問。在這兩個頁面所使用的動作(saveProductsearchProduct)將會在下面的部分介紹。


          五、通過模型類操作數(shù)據(jù)庫

              在這一節(jié)我們來編寫用于操作數(shù)據(jù)庫的模型類。由于本例子是Web程序,因此,建議在連接數(shù)據(jù)庫時使用數(shù)據(jù)庫連接池。在<Tomcat安裝目錄>"conf"Catalina"localhost目錄中打開samples.xml文件(如果沒有該文件,則建立一個samples.xml文件),在<Context>節(jié)點(diǎn)中加入如下的內(nèi)容:

          配置連接池(用于連接數(shù)據(jù)庫struts

            <Resource name="jdbc/struts" auth="Container"
                          type
          ="javax.sql.DataSource"
                          driverClassName
          ="com.mysql.jdbc.Driver"
                          url
          ="jdbc:mysql://localhost:3306/struts?characterEncoding=GBK"
                          username
          ="root"
                          password
          ="1234"              
                          maxActive
          ="200"
                          maxIdle
          ="50"
                          maxWait
          ="3000"/>

          本例中提供了兩個可以操作數(shù)據(jù)庫的模型類:ProductSearchProduct。其中Product用于驗(yàn)證由客戶端提交的產(chǎn)品信息,并向t_products表中寫入這些信息。而SearchProduct類用于對t_products表的product_name字段進(jìn)行模糊查詢,并返回查詢到的產(chǎn)品信息(包括產(chǎn)品ID、產(chǎn)品名稱和產(chǎn)品價格)。

             由于ProductSearchProduct都需要使用數(shù)據(jù)庫連接池來連接數(shù)據(jù)庫,因此,可以將連接數(shù)據(jù)庫的工作提出來作為一個父類(Struts)提供,代碼如下:

          package util;
          import java.sql.Connection;
          public class Struts
          {
              protected javax.naming.Context ctx = new javax.naming.InitialContext();
              protected javax.sql.DataSource ds;
             
          protected Connection conn;
             
          public Struts() throws Exception
              {
                  ds 
          = (javax.sql.DataSource) ctx.lookup("java:/comp/env/jdbc/struts");
                  conn 
          = ds.getConnection();  // 從數(shù)據(jù)庫連接池獲得一個Connection
              }
          }

              <samples工程目錄>"src目錄中建立一個Product.java文件,代碼所示:

            package mystruts.model;
            
            
          import java.sql.*;
            
          import mystruts.actionform.*;
            
            
          public class Product extends util.Struts
            {
                
          private ProductForm form;
            
                
          public Product(ProductForm form) throws Exception
                {
                    
          super();
                    
          this.form = form;
                    validate();
                }
                
          // 驗(yàn)證客戶端提交的數(shù)據(jù)
                public void validate() throws Exception
                {
                    
          if (form.getProductID().trim().equals(""))
                        
          throw new Exception("產(chǎn)品ID不能為空!");
                    
          if(form.getProductID().length() > 4)
                        
          throw new Exception("產(chǎn)品ID最長為4位!");
                    
          if (form.getProductName().trim().equals(""))
                        
          throw new Exception("產(chǎn)品名稱不能為空");
                    
          if (Float.compare(form.getPrice(), 0<= 0)
                        
          throw new Exception("產(chǎn)品價格必須大于0");
                }
                
          // 將客戶端提交的產(chǎn)品信息保存到t_products中
                public void save() throws Exception
                {
                    
          try
                    {
                        String productID 
          = form.getProductID();
                        String productName 
          = form.getProductName();
                        
          float price = form.getPrice();
                        String sql 
          = "INSERT INTO t_products VALUES('" + productID + "',"
                                
          + "'" + productName + "'," + String.valueOf(price) + ")";
                        PreparedStatement pstmt 
          = conn.prepareStatement(sql);
                        pstmt.executeUpdate();   
          // 執(zhí)行INSERT語句
                        pstmt.close();
                        conn.close();
                    }
                    
          catch (Exception e)
                    {
                        
          throw new Exception(e.getMessage());
                    }
                }
            }

              Product類中使用了一個ProductForm類,這個類是一個ActionForm類,它的功能是保存客戶端提交的數(shù)據(jù)。關(guān)于這個類將在下面詳細(xì)介紹。Product類通過構(gòu)造方法的form參數(shù)將客戶端提交的數(shù)據(jù)傳入Product類的對象實(shí)例中,并在構(gòu)造方法中驗(yàn)證這些數(shù)據(jù),如果發(fā)現(xiàn)數(shù)據(jù)不合法,就會拋出一個異常。當(dāng)客戶端提交的數(shù)據(jù)合法后,成功建立了一個Product類的對象實(shí)例,然后可以通過簡單地調(diào)用save方法將數(shù)據(jù)保存到t_products表中。

              Product類似,在<samples工程目錄>"src目錄中建立一個SearchProduct.java文件,代碼如下:

            package mystruts.model;
            
            
          import java.sql.*;
            
          import java.util.*;
            
          import mystruts.actionform.*;
            
            
          public class SearchProduct extends util.Struts
            {
                
          private ProductForm form;
            
                
          public SearchProduct(ProductForm form) throws Exception
                {
                    
          super();
                    
          this.form = form;
                }    
                
          // 查詢產(chǎn)品信息,并通過List返回查詢結(jié)果
                public List<String[]> search() throws Exception
                {
                    List
          <String[]> result = new LinkedList<String[]>();
                    String sql 
          = "SELECT * FROM t_products WHERE product_name like '%" 
          + form.getProductName() + "%'";
                    PreparedStatement pstmt 
          =  conn.prepareStatement(sql);
                    ResultSet rs 
          = pstmt.executeQuery();  // 開始執(zhí)行SELECT語句
                    while(rs.next())
                    {
                        String[] row 
          = new String[3];
                        row[
          0= rs.getString(1);
                        row[
          1= rs.getString(2);
                        row[
          2= rs.getString(3);
                        result.add(row);
                    }
                    rs.close();
                    conn.close();
                    
          return result;
                }
            }

                 SearchProduct類也使用了ProductForm類,但在SearchProduct中并不會驗(yàn)證ProductForm對象實(shí)例中的數(shù)據(jù),而只是將ProductForm對象作為傳遞查詢請求信息(實(shí)際上只需要產(chǎn)品名稱)的工具而已。

          六、實(shí)現(xiàn)控制器

             
          在這一節(jié)要實(shí)現(xiàn)的控制器是基于StrutsWeb程序的核心部分之一:控制器實(shí)質(zhì)上也是普通的Java類,但這個Java類一般要從org.apache.struts.action.Action類繼承??刂破鞯闹饕δ苁墙邮懿⑻幚韽腏SP頁面提交的數(shù)據(jù)、通過模型(Model)和數(shù)據(jù)庫交互以及forward到相應(yīng)的頁面(可以是任何頁面,如html、JSP和Servlet等)。在實(shí)現(xiàn)控制器之前,需要先實(shí)現(xiàn)一個ActionForm類, 這個類的作用是保存JSP頁面提交的數(shù)據(jù)。在<samples工程目錄>"src目錄中建立一個ProductForm.java文件,代碼如下:

            package mystruts.actionform;
            
            
          import org.apache.struts.action.*;
            
            
          public class ProductForm extends ActionForm
            {
                
          private String productID;  // 產(chǎn)品ID
                private String productName; // 產(chǎn)品名稱
                private float price;  // 產(chǎn)品價格
                public String getProductID()
                {
                    
          return productID;
                }
                
          public void setProductID(String productID)
                {
                    
          this.productID = productID;
                }
                
          public String getProductName()
                {
                    
          return productName;
                }
                
          public void setProductName(String productName)
                {
                    
          this.productName = productName;
                }
                
          public float getPrice()
                {
                    
          return price;
                }
                
          public void setPrice(float price)
                {
                    
          this.price = price;
                }
            }

              從上面的代碼可以看出,ActionForm類一般從org.apache.struts.action.ActionForm類繼承,而且在類中需要按著需要保存的數(shù)據(jù)表字段添加屬性。如產(chǎn)品ID的屬性是productName。在MyEclipse中可以只定義三個private變量,然后使用MyEclipse的Source > Generate Getters and Setters...】功能自動產(chǎn)生gettersetter方法。但在給這些屬性取名時要注意,private變量的名子和數(shù)據(jù)表的字段名沒有直接的關(guān)系,但必須和JSP頁面中的<html>標(biāo)簽的property屬性值一致,如<html:text property="productName" />表示輸入產(chǎn)品名稱的文本框,其中property屬性的值就是ProductForm類中的productName變量。如果不一致,將會拋出異常。其他和ProductForm類的屬性對應(yīng)的<html>標(biāo)簽可以查看上面的代碼。
             
          光有ActionForm類還不夠,還需要在struts-config.xml中的<struts-config>節(jié)點(diǎn)中添加如下的內(nèi)容:

          <form-beans>
               <form-bean name="saveProductForm" type=" mystruts.actionform.ProductForm" />
               <form-bean name="searchProductForm" type="mystruts.actionform.ProductForm" />
          </form-beans>

              上面的代碼所配置的兩個ActionForm實(shí)際上指的是同一個ProductForm類,但這個ProductForm類在后面要講的兩個動作里都要使用,為了更容易理解,為這個ProductForm起了兩個不同的別名(saveProductFormsearchProductForm)。
             
          下面來實(shí)現(xiàn)saveProduct動作的代碼。Struts Action類必須一般從org.apache.struts.action.Action類繼承。一般在Struts Action類需要覆蓋Action類的execute方法。這個方法有每次客戶端訪問Struts Action時調(diào)用。我們可以在方法中處理客戶端提交的數(shù)據(jù),訪問數(shù)據(jù)庫等工作。這個方法返回一個ActionForward類型的值,表明在執(zhí)行完execute后,要forward到的頁面。描述saveProduct動作的類叫SaveProductAction。代碼如下:

            package mystruts.action;
            
            
          import javax.servlet.http.*;
            
          import org.apache.struts.action.*;
            
          import mystruts.actionform.*;
            
          import mystruts.model.*;
            
            
          public class SaveProductAction extends Action
            {
                
          // 在客戶端訪問saveProduct動作時執(zhí)行該方法
                public ActionForward execute(ActionMapping mapping, ActionForm form,
                        HttpServletRequest request, HttpServletResponse response)
                {
                    ProductForm saveProductForm 
          = (ProductForm) form;
                    
          try
                    {
                        Product product 
          = new Product(saveProductForm);
                        product.save();  
          // 保存產(chǎn)品信息
                        request.setAttribute("info""保存成功!");   
                    }
                    
          catch (Exception e)
                    {
                        request.setAttribute(
          "info", e.getMessage());
                    }
                    
          return mapping.findForward("save");
                }
            }

              SaveProductAction類中使用了模型類Product驗(yàn)證并保存產(chǎn)品信息。并將操作結(jié)果信息保存在request的屬性中,key為“info”。在execute的最后,使用了ActionMapping類的findForward方法在struts-config.xml中尋找一個叫“save”的forward。這個forward是一個JSP頁,用于顯示是否將產(chǎn)品信息保存成功的信息。為了可以在struts-config.xml中查找這個forward,需要在struts-config.xml<action-mappings>節(jié)點(diǎn)中加入如下的內(nèi)容。

          <action name="saveProductForm" path="/saveProduct"scope="request" type=" mystruts.action.SaveProductAction">
              <forward name="save" path="/mystruts/save.jsp" />
          </action>

              從上面的代碼可以看出,那個用于顯示保存狀態(tài)信息的JSP頁面叫save.jsp。在<samples工程目錄>"mystruts目錄中建立一個save.jsp文件,代碼如下:

            <%@ page pageEncoding="GBK"%>
            ${requestScope.info}

              IE中輸入如下的URL

              http://localhost:8080/samples/mystruts/newProduct.jsp

             
          在文本框中輸入相應(yīng)的信息后,點(diǎn)“保存”按鈕,如果輸入的數(shù)據(jù)是合法的,就會將數(shù)據(jù)保存在t_products中,否則會顯示出錯的原因。    searchProduct動作的實(shí)現(xiàn)和saveProduct差不多,也會為三步:實(shí)現(xiàn)動作類(SearchProductAction)、在struts-config.xml中添加配置信息和實(shí)現(xiàn)用于顯示查詢結(jié)果的JSP文件。下面的代碼分別顯示了這三步所要編寫的代碼。

          SearchProductAction.java

            package mystruts.action;
            
            
          import javax.servlet.http.*;
            
          import org.apache.struts.action.*;
            
          import mystruts.actionform.*;
            
          import mystruts.model.*;
            
          import java.util.*;
            
            
          public class SearchProductAction extends Action
            {
            
                
          public ActionForward execute(ActionMapping mapping, ActionForm form,
                        HttpServletRequest request, HttpServletResponse response)
                {
                    ProductForm searchProductForm 
          = (ProductForm) form;
                    
          try
                    {
                        SearchProduct searchProduct 
          = new SearchProduct(searchProductForm);
                        List
          <String[]> result = searchProduct.search();  // 查詢產(chǎn)品信息
                        if (result.size() > 0)  // 有符合條件的產(chǎn)品信息
                        {
                            request.setAttribute(
          "result", result);
                            request.setAttribute(
          "info""記錄數(shù):" + String.valueOf(result.size()));
                        }
                        
          else  // 沒有查到任何產(chǎn)品信息
                            request.setAttribute("info""沒有符合要求的記錄!");
                    }
                    
          catch (Exception e)
                    {
                        request.setAttribute(
          "info", e.getMessage());
                    }
                    
          return mapping.findForward("search");
                }
            }

           

          struts-config.xml中配置searchProduct動作

          <action name="searchProductForm" path="/searchProduct" scope="request" type="mystruts.action.SearchProductAction">
              <forward name="search" path="/mystruts/search.jsp" />
          </action>

          search.jsp

            <%@ page pageEncoding="GBK"%>
            
          <%@ taglib uri="http://struts.apache.org/tags-logic" prefix="logic"%>
            
          <%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c"%>
            
          <html>
                
          <body>
          <%-- 從request的result中取出查詢結(jié)果 --%>
                    
          <c:set var="result" value="${requestScope.result}" />
                    
          <table width="100%">
                        
          <tr align="center">
                            
          <td>
                                ${requestScope.info}
                            
          </td>
                        
          </tr>
                        
          <tr align="center">
                            
          <td>
                                
          <logic:present name="result">
                                    
          <table border="1">
                                        
          <tr align="center">
                                            
          <td> 產(chǎn)品ID </td>
                                            
          <td> 產(chǎn)品名稱 </td>
                                            
          <td> 價格 </td>
                                        
          </tr>
                                        
          <logic:iterate id="row" name="result">
                                            
          <tr> <td> ${row[0]} </td>
                                                
          <td> ${row[1]} </td>
                                                
          <td> ${row[2]} </td>
                                            
          </tr>
                                        
          </logic:iterate>
                                    
          </table>
                                
          </logic:present>
                            
          </td>
                        
          </tr>
                    
          </table>
                
          </body>
            
          </html>

              IE中輸入如下的URL

              http://localhost:8080/samples/%20mystruts/searchProduct.jsp

             
          在“產(chǎn)品名稱”文本框中輸入產(chǎn)品名稱的一部分,程序就會查詢出所有包含輸入的產(chǎn)品名稱的產(chǎn)品信息,并將結(jié)果顯示出來。

          七、解決ActionForm的亂碼問題

           

              到現(xiàn)在為止,程序的功能部分已經(jīng)全部實(shí)現(xiàn)完了。但還存在一個問題。當(dāng)我們在產(chǎn)品名稱中輸入中文時,雖然將客戶端提交的數(shù)據(jù)成功保存到數(shù)據(jù)庫中,但是在t_products表中的product_name字段顯示的都是亂碼。產(chǎn)生這個問題的原因只有一個,就是客戶端提交的數(shù)據(jù)的編碼格式和數(shù)據(jù)庫的編碼格式不一致造成的。當(dāng)然,解決這個問題的方法有很多,但筆者認(rèn)為最容易的就是使用過濾器。所謂過濾器,就是在客戶端提交數(shù)據(jù)后,在交由服務(wù)端處理之前所執(zhí)行的一段服務(wù)端代碼(一般為Java代碼)。一個過濾器是一個實(shí)現(xiàn)javax.servlet.Filter接口的類。在本例中要使用的過濾器類叫EncodingFilter,實(shí)現(xiàn)代碼如下:

          EncodingFilter.java


            package filter;
            
          import java.io.IOException;
            
          import javax.servlet.*;
            
          public class EncodingFilter implements Filter
            {
                
          public void destroy() {  }
                
          public void doFilter(ServletRequest request, ServletResponse response,
                        FilterChain chain) 
          throws IOException, ServletException
                {
                    request.setCharacterEncoding(
          "GBK");  // 將客戶端提交的數(shù)據(jù)設(shè)為GBK編碼格式
                    // 繼續(xù)處理客戶端提交的數(shù)據(jù),如果不寫這條語句,Servlet引擎將不會處理所過濾的頁面
                    chain.doFilter(request, response);      
                }
                
          public void init(FilterConfig filterConfig) throws ServletException {   }  
            }

              Filter接口的doFilter方法是過濾器的核心方法。其中FilterChain類的doFilter方法允許繼續(xù)處理客戶端提交的數(shù)據(jù)。我們還可以使用這個方法來臨時關(guān)閉Web站點(diǎn)的某個或全部的頁面(根據(jù)過濾器的設(shè)置而定)。由于本書的數(shù)據(jù)庫使用的是GBK編碼格式,因此,需要使用ServletRequestsetCharacterEncoding方法將客戶端提交的數(shù)據(jù)也設(shè)為GBK編碼格式。

              除了實(shí)現(xiàn)過濾器類,我們還需要在web.xml中的<web-app>節(jié)點(diǎn)加入如下的配置信息才能使過濾器生效:

          web.xml中配置過濾器


          <filter>
              <filter-name>EncodingFilter</filter-name>
              <filter-class>
                  filter.EncodingFilter
              </filter-class>
          </filter>
          <filter-mapping>
              <filter-name>EncodingFilter</filter-name>
              <url-pattern>/*</url-pattern>
          </filter-mapping>

              在重新啟動Tomcat后,重新輸入一條帶中文的產(chǎn)品信息,看看是否可以將中文保存在數(shù)據(jù)庫中?
          posted on 2009-02-16 21:05 飛翔天使 閱讀(368) 評論(0)  編輯  收藏 所屬分類: Struts
          主站蜘蛛池模板: 宁安市| 利辛县| 惠东县| 仁布县| 伽师县| 农安县| 清流县| 鄂伦春自治旗| 柘荣县| 定陶县| 抚顺市| 江源县| 陇南市| 楚雄市| 遂川县| 海门市| 富民县| 樟树市| 革吉县| 景东| 柘荣县| 青铜峡市| 昌乐县| 岳阳市| 同德县| 盘锦市| 蒙山县| 澄迈县| 马公市| 佳木斯市| 渝北区| 玛多县| 民乐县| 长治市| 宁安市| 长阳| 台北市| 双桥区| 玉山县| 石河子市| 武威市|