一、 橋梁(Bridge)模式
posted @ 2006-09-18 13:38 Binary 閱讀(3289) | 評論 (2) | 編輯 收藏
VincentVicent's blog
隨筆 - 74, 文章 - 0, 評論 - 5, 引用 - 0
|
一、 橋梁(Bridge)模式
摘要: 一、?橋梁(Bridge)模式
橋梁模式是一個非常有用的模式,也是比較復雜的一個模式。熟悉這個模式對于理解面向對象的設計原則,包括"開-閉"原則(OCP)以及組合/聚合復用原則(CARP)都很有幫助。理解好這兩個原則,有助于形成正確的設計思想和培養良好的設計風格。
注:《Java與模式》一書認為Bridge模式不是一個使用頻率很高的模式,我不太贊同,我認為Bridge模式中... 閱讀全文
posted @ 2006-09-18 13:38 Binary 閱讀(3289) | 評論 (2) | 編輯 收藏 Hibernate Validator 簡介在項目的業務屬性中,你是不是要經常驗證屬性的取值范圍呢. 想要了解比較優美的解決方案嗎??????????? 看看Hibernate Validator 是怎么做的吧.一見到她,相信你就會說: Oh God, 這就是我需要的.
任何獲得Matrix授權的網站,轉載請保留以下作者信息和鏈接:
用Annotations 給類或者類的屬性加上約束(constraint),在運行期檢查屬性值是很優雅的.Hibernate Validator就是這樣的一個框架.該框架是十分容易的(就像參考文檔中宣稱的那樣),幾乎沒有什么學習曲線,Validator 是一個驗證框架 不需要和Hibernate的其他部分綁定就可以使用,只要在你的項目中添加Hibernate-annotations.jar庫就可以了.那么下面就讓我們看看怎么使用吧.
上面是兩個用 Validator Annotations 注釋的 類. 每個屬性都用 約束限制了.? 下面看看測試的類吧:
程序的輸出如下 InvalidValue 的長度是:4 . 驗證消息是: 必須大于等于 1 . PropertyPath 是:age . PropertyName 是: age. Value 是: 0 Bean 是: test.annotation.validator.Person@dd87b2 BeanClass 是:class test.annotation.validator.Person InvalidValue 的長度是:4 . 驗證消息是: 長度必須介于 4 與 2147483647 之間 . PropertyPath 是:name . PropertyName 是: name. Value 是: ice Bean 是: test.annotation.validator.Person@dd87b2 BeanClass 是:class test.annotation.validator.Person InvalidValue 的長度是:4 . 驗證消息是: 必須大于等于 1 . PropertyPath 是:address.num . PropertyName 是: num. Value 是: 0 Bean 是: test.annotation.validator.Address@197d257 BeanClass 是:class test.annotation.validator.Address InvalidValue 的長度是:4 . 驗證消息是: 長度必須介于 3 與 8 之間 . PropertyPath 是:address.street . PropertyName 是: street. Value 是: 1 Bean 是: test.annotation.validator.Address@197d257 BeanClass 是:class test.annotation.validator.Address 可以看出不滿足約束的值都被指出了. 同時該句: 我們只驗證了 Person. 在Person里面的Address的屬性 由于有 InvalidValue 的長度是:2 . 驗證消息是: 必須大于等于 1 . PropertyPath 是:age . PropertyName 是: age. Value 是: 0 Bean 是: test.annotation.validator.Person@18fef3d BeanClass 是:class test.annotation.validator.Person InvalidValue 的長度是:2 . 驗證消息是: 長度必須介于 4 與 2147483647 之間 . PropertyPath 是:name . PropertyName 是: name. Value 是: ice Bean 是: test.annotation.validator.Person@18fef3d BeanClass 是:class test.annotation.validator.Person
InvalidValue 的長度是:1 . 驗證消息是: 必須大于等于 1 . PropertyPath 是:age . PropertyName 是: age. Value 是: 0 Bean 是: test.annotation.validator.Person@1457cb BeanClass 是:class test.annotation.validator.Person
然后在你的類中應用@ 在我們的Person.java類 添加@
InvalidValue 的長度是:3 . 驗證消息是:
bean must be serialiable
. PropertyPath 是:null .
PropertyName 是: null. Value 是: test.annotation.validator.Person@1a73d3c Bean 是: test.annotation.validator.Person@1a73d3c
BeanClass 是:class test.annotation.validator.Person
validator.assertFalse= assertion failed validator.assertTrue= assertion failed validator.future= must be a future date validator.length= length must be between {min} and {max} validator.max= must be less than or equal to {value} validator.min= must be greater than or equal to {value} validator.notNull= may not be null validator.past= must be a past date validator.pattern= must match "{regex}" validator.range= must be between {min} and {max} validator.size= size must be between {min} and {max} #下面是自定義的消息 Serializable= Bean not Serializable? //加上自己定義的國際化消息.
myMsg=該字符串的長度不符合規定范圍范圍 并且還要在 @Length 注釋中提供message的引用的key 如下 @Length(min = 4,message = "{ myMsg }")
看到這里其實不用我在多說了 大家都知道怎么用,什么時候用. 作為一篇介紹性文章我還是在此給出一個最常用的例子吧,更好的使用方式大家慢慢挖掘吧. 比如 : 你現在在開發一個人力資源(HR)系統 (其實是我們ERP課程的一個作業 ^_^), 里面要處理大量的數據,尤其是在輸入各種資料時 如 登記員工信息. 如果你公司的員工的年齡要求是18 -- 60 那么你所輸入的年齡就不能超出這個范圍. 你可能會說這很容易啊 , 不用Validator就可以解決啊.這保持數據前驗證就可以啦 如if ( e.getAge() > 60 || e.getAge() < 18 ) ........ 給出錯誤信息 然后提示重新輸入不就OK啦 用得著 興師動眾的來個第三方框架嗎? 是啊 當就驗證這一個屬性時, 沒有必要啊 ! 但是一個真正的HR 系統,會只有一個屬性要驗證嗎? 恐怕要有N多吧 你要是每一個都那樣 寫一段驗證代碼 是不是很煩啊 ,況且也不方便代碼重用. 現在考慮一些 Validator 是不是更高效啊,攔截到 約束違例的 屬性 就可以直接得到 國際化的消息 可以把該消息顯示到一個彈出對話框上 提示更正? ! Validator的用處不只這一種 ,你可以想到如何用呢 ! 歡迎發表你的高見!! OK 到此 我們的 Hibernate Validator 之旅就要先告一段落了 . 希望這是令你心曠神怡的一次寒冬之旅, 把你學到的應用到你的項目中吧,一定會提高你的生產率的. 相信我 ,沒錯的? ^_^ ! posted @ 2006-09-01 14:05 Binary 閱讀(459) | 評論 (0) | 編輯 收藏 Hibernate Annotations 實戰(二)
-- hbm.xml 與 Annotations 性能比較
任何獲得Matrix授權的網站,轉載請保留以下作者信息和鏈接:
我在前面一篇文章<Hibernate Annotations 實戰-- 從 hbm.xml 到 Annotations>: 中,有很多開發者在談論中提到,有沒有必要從 hbm.xml 往 Annotations 上轉移. 那么在這篇文章中我們就來討論一下 hbm.xml 與 Annotations的優缺點,看看那種情況最適合你. 首先,討論一下 xml 配置文件的優點, 個人認為主要優點就是當你改變底層配置時 不需要改變和重新編譯代碼,只需要在xml 中更改就可以了,例如 Hibernate.cfg.xml 當你要更改底層數據庫時, 只要更改配置文件就可以了.Hibernate會為你做好別的事情. 那么xml的缺點呢,個人認為有以下幾點:
其中第一 二點 借助于先進的IDE 可能不是什么問題. 但是對初學者還是個問題 ^_^. 下面我們看看 Annotations的 特性吧! 可以解決xml遇到的問題,有以下優點
關于 映射文件是使用 hbm.xml 文件還是使用 Annotations 我們來看看2者的性能吧. 先聲明一下,個人認為映射文件一旦配置好就不會在很大程度上改變了.所以使用xml文件并不會帶來很大的好處.如果你認為 映射文件在你的項目中也經常變化,比如一列String數據 ,今天你使用 length="16" 明天你認為 該數據的長度應該更長才能滿足業務需求 于是改為length="128" 等等類似的問題 . 如果你經常有這方面的變動的話,下面的比較你可以不用看了 , 你應該使用 xml文件 因為Annotations 無法很好的滿足你的要求. 現在讓我們就來看看2者的性能比較吧. (說明: 這里只是比較查找 插入 的時間快慢,沒有比較除運行時間以外的其他性能,如 內存占用量 等等) 先來看看測試程序和配置. 首先在 Hibernate.cfg.xml 文件中去掉了 <property name="hibernate.hbm2ddl.auto">update</property> 這一行, 因為在前面的實驗中以及建立了數據庫表了 不再需要更新了.如果你是第一次運行該例子 還是要該行的. Test.java 如下:
Annotations 包中的Person.java 如下
其他的代碼幾乎沒有改變: 下面的每種類型的測試都測試了3次以上, 取中間的測試時間. 測試機器配置: CPU:? AMD Athlon (xp) 2000+ 內存: 784880KB 硬盤: 三星 SP0812N 讀取一次??的比較:(單位: 毫秒)
?? 讀取100次的比較:
插入100次的比較:
從上面的三次對比中大家可以看到 初始化的部分幾乎兩者是一樣的, 在數據操作上面 使用xml文件 總是比使用Annotations 慢一點.在我們只操縱一個只有幾個屬性的小持久化類的操作中就有 幾十毫秒的差距. 幾十毫秒在計算機中算不算很大 大家應該都知道,我就不在多說了. 總結: 經過 xml 文件 和Annotations 的優缺點和 性能上的對比.現在使用那個作為你持久化映射策略.我相信大家都會正確選擇的. 測試后記: 經過多次測試 感覺有時候很不穩定 ,有的時候很穩定不知道是測試有問題還是別的問題.大家可以自己測試一下. 有什么新的發現 請大家討論討論. posted @ 2006-09-01 14:04 Binary 閱讀(342) | 評論 (0) | 編輯 收藏 第一個Hibernate with Annotation程式
Hibernate是ORM的解決方案,其底層對數據庫的操作依賴于JDBC,所以您必須先取得JDBC驅動程序,在這邊所使用的是MySQL,所以您必須至 MySQL? Connector/J 取得MySQL的JDBC驅動程序。
接下來至 Hibernate 官方網站 取得Hibernate 3.2、Hibernate Annotations 3.2。 您必須安裝JDK 5.0才可以使用Hibernate Annotations的功能。 解開Hibernate 3.2的zip檔案后,當中的hibernate3.jar是必要的,而在lib目錄中還包括了許多jar檔案,您可以在 Hibernate 3.0官方的參考手冊 上找到這些jar的相關說明,其中必要的是 antlr、dom4j、CGLIB、asm、Commons Collections、Commons Logging、 EHCache,Hibernate底層還需要Java Transaction API,所以您還需要jta.jar。 解開Hibernate Annotations 3.2的zip檔案后,您需要hibernate-annotations.jar、ejb3-persistence.jar這兩個檔案。 到這邊為止,總共需要以下的jar檔案: ![]() Hibernate可以運行于單機之上,也可以運行于Web應用程序之中,如果是運行于單機,則將所有用到的jar檔案(包括JDBC驅動程序)設定至CLASSPATH中,如果是運行于Web應用程序中,則將jar檔案置放于WEB-INF/lib中。 如果您還需要額外的Library,再依需求加入,例如JUnit、Proxool等等,接下來可以將etc目錄下的 log4j.properties復制至Hibernate項目的Classpath下,并修改一下當中的 log4j.logger.org.hibernate為error,也就是只在在錯誤發生時顯示必要的訊息。 接著設置基本的Hibernate配置文件,可以使用XML或Properties檔案,這邊先使用XML,檔名預設為hibernate.cfg.xml: <?xml version="1.0" encoding="utf-8"?> <!DOCTYPE hibernate-configuration PUBLIC ? "-//Hibernate/Hibernate Configuration DTD 3.0//EN" ? "http://hibernate.sourceforge.net/hibernate-configuration-3.0.dtd"> ? <hibernate-configuration> ??? <session-factory> ??????? <!-- 顯示實際操作數據庫時的SQL --> ??????? <property name="show_sql">true</property> ??????? <!-- SQL方言,這邊設定的是MySQL --> ??????? <property name="dialect">org.hibernate.dialect.MySQLDialect</property> ??????? <!-- JDBC驅動程序 --> ??????? <property name="connection.driver_class">com.mysql.jdbc.Driver</property> ??????? <!-- JDBC URL --> ??????? <property name="connection.url">jdbc:mysql://localhost/demo</property> ??????? <!-- 數據庫使用者 --> ??????? <property name="connection.username">root</property> ??????? <!-- 數據庫密碼 --> ??????? <property name="connection.password">123456</property> ? ??????? <!-- 以下設置對象與數據庫表格映像類別 --> ??????? <mapping class="onlyfun.caterpillar.User"/> ??? </session-factory> </hibernate-configuration> 這邊以一個簡單的單機程序來示范Hibernate的配置與功能,首先作數據庫的準備工作,在MySQL中新增一個demo數據庫,并建立user表格: CREATE TABLE user (對于這個表格,您有一個User類別與之對應,表格中的每一個字段將對應至User實例上的Field成員。 package onlyfun.caterpillar; ? import javax.persistence.*; ? @Entity @Table(name="user") // 非必要,在表格名稱與類別名稱不同時使用 public class User { ? @Id ? @GeneratedValue(strategy=GenerationType.AUTO) ??? private Integer id; ? ? @Column(name="name") // 非必要,在字段名稱與屬性名稱不同時使用 ??? private String name; ? ? @Column(name="age") ??? private Integer age; // 非必要,在字段名稱與屬性名稱不同時使用 ??? ??? // 必須要有一個預設的建構方法 ??? // 以使得Hibernate可以使用Constructor.newInstance()建立對象 ??? public User() { ??? } ? ??? public Integer getId() { ??????? return id; ??? } ? ??? public void setId(Integer id) { ??????? this.id = id; ??? } ? ??? public String getName() { ??????? return name; ??? } ? ??? public void setName(String name) { ??????? this.name = name; ??? } ??? ??? public Integer getAge() { ??????? return age; ??? } ? ??? public void setAge(Integer age) { ??????? this.age = age; ??? } } 其中id是個特殊的屬性,Hibernate會使用它來作為主鍵識別,您可以定義主鍵產生的方式,這邊設定為自動產生主鍵,可以看到,實體標識,主鍵生成,以及相關映像,都可以使用Annotation來完成。 接下來撰寫一個測試的程序,這個程序直接以Java程序設計人員熟悉的語法方式來操作對象,而實際上也直接完成對數據庫的操作,程序將會將一筆數據存入表格之中: package onlyfun.caterpillar; ? import org.hibernate.SessionFactory; import org.hibernate.Session; import org.hibernate.Transaction; import org.hibernate.cfg.AnnotationConfiguration; import org.hibernate.cfg.Configuration; ? public class HibernateAnnotationDemo { ? ??? public static void main(String[] args) { ??????? // 需要AnnotationConfiguration讀取Annotation訊息 ??????? Configuration config = new AnnotationConfiguration().configure(); ??????? // 根據 config 建立 SessionFactory ??????? // SessionFactory 將用于建立 Session ??????? SessionFactory sessionFactory = config.buildSessionFactory(); ? ??????? // 將持久化的物件 ??????? User user = new User(); ??????? user.setName("caterpillar"); ??????? user.setAge(new Integer(30));???? ? ??????? // 開啟Session,相當于開啟JDBC的Connection ??????? Session session = sessionFactory.openSession(); ??????? // Transaction表示一組會話操作 ??????? Transaction tx= session.beginTransaction(); ??????? // 將對象映像至數據庫表格中儲存 ??????? session.save(user); ??????? tx.commit(); ??????? session.close(); ??????? sessionFactory.close(); ?????? ??????? System.out.println("新增資料OK!請先用MySQL觀看結果!"); ??? } } 注意,使用Annotation時,需要的是AnnotationConfiguration類別。 如您所看到的,程序中只需要直接操作User對象,并進行Session與Transaction的相關操作,Hibernate就會自動完成對數據庫的操作,您看不到任何一行JDBC或SQL的陳述,撰寫好以上的各個檔案之后,各檔案的放置位置如下: ![]() 接著可以開始運行程序,結果如下: Hibernate: insert into user (name, age) values (?, ?) 新增資料OK!請先用MySQL觀看結果! 執行結果中顯示了Hibernate所實際使用的SQL,由于這個程序還沒有查詢功能,所以要進入MySQL中看看新增的數據,如下: mysql> select * from user;
+----+-----------------+------+ | id??? | name???????? | age? | +----+-----------------+------+ |? 1??? | caterpillar? | 30?? | +----+-----------------+------+ 1 row in set (0.03 sec) posted @ 2006-09-01 14:00 Binary 閱讀(305) | 評論 (0) | 編輯 收藏 Hibernate Annotations 實戰
摘要: 任何獲得Matrix授權的網站,轉載請保留以下作者信息和鏈接:
作者:icess(作者的blog:http://blog.matrix.org.cn/page/icess)關鍵字:Hibernate Validator
下面讓我們先看一個通常用 hbm.xml 映射文件的例子. 有3個類 .HibernateUtil.java 也就是 Hibernate文檔中推薦的工具類,Pers... 閱讀全文
posted @ 2006-09-01 13:59 Binary 閱讀(409) | 評論 (0) | 編輯 收藏 在filter中關閉session利用Thread-Specific Storage撰寫一個HibernateUtil
HibernateSessionUtil.java
import java.io.Serializable; filter中的程式碼如下
HibernateSessionCloser.java
public class HibernateSessionCloser implements Filter{ 然後在操作資料庫之前加上 HibernateSessionUtil.beginTransaction(); posted @ 2006-09-01 13:51 Binary 閱讀(471) | 評論 (0) | 編輯 收藏 acegi-security-sample-contacts-filter例子學習(二)功能實現分析 這個例子使用了HSQL做數據庫,spring的AOP作為基礎,使用Acegi做安全控制組件。 2. 并解析文件里的內容。 b) filter元素。 e) 密碼加密。這里定義了一個acegi的Md5算法加密對象Md5PasswordEncoder。 i) 定義接收來自DaoAuthenticationProvider的認證事件的listener――LoggerListener。 ii. InterceptorNames。攔截器名稱。可以有多個,iv. 這里包括:transactionInterceptor、contactManagerSecurity、contactManagerTarget。其中,v. transactionInterceptor是前面定義的事務攔截器。ContactManagerSecurity則是在 applicationContext-common-authorization.xml里定義的方法調用授權。 posted @ 2006-09-01 13:45 Binary 閱讀(892) | 評論 (0) | 編輯 收藏 acegi-security-sample-contacts-filter例子學習(一)
這是一個
Acegi
官方的例子。它以聯系人的管理為例子,說明如何使用
Acegi
作權限控制。這個例子包含在
acegi
的包里面。下載地址:
http://prdownloads.sourceforge.net/acegisecurity/acegi-security-0.8.3.zip?download。
聯系人管理說明了下列中心的Acegi安全控制能力:
聯系人管理的業務功能描述: 1.1. 每個用戶登錄后,可以看到一個聯系人列表。例如, marissa's Contacts
說明:用戶沒有權限訪問的聯系人信息,將不會顯示。 2.2. 用戶可以增加新的聯系人信息。 3.3. 如果有刪除權限,用戶可以看到在聯系人后面有一個“ Del ”鏈接。用戶可以點擊這個鏈接來刪除某個聯系人信息。 4.4. 如果有管理權限,用戶可以看到在聯系人后面有一個“ Admin Permission ”鏈接。用戶可以點擊這個鏈接來管理訪問這個聯系人的權限。例如, Administer Permissions
說明:每一行記錄包含有 3 列。
第一列表示權限,例如,“
第二列也表示權限,但它是以類似 unix 權限的數字表達。例如,“ [22] ” , 表示可讀、可寫、可刪除。 第三列是用戶名稱。 每一行記錄后面都有一個“ Del ”鏈接。點擊這個鏈接,可以刪除掉指定用戶對這個聯系人信息的權限。 5.5. 用戶可以為某個聯系人信息添加權限。例如, Add Permission
posted @ 2006-09-01 13:44 Binary 閱讀(636) | 評論 (0) | 編輯 收藏 WebWork教程-ServletDispatcher
摘要: ServletDispatcher
原理
ServletDispatcher
是默認的處理
Web Http
請求的調度器,它是一個
JavaServlet
,是
WebWork
框架的控制器。... 閱讀全文
posted @ 2006-09-01 13:41 Binary 閱讀(653) | 評論 (0) | 編輯 收藏 WebWork教程-validator
驗證框架
WebWork
提供了在
Action
執行之前,對輸入數據的驗證功能,它使用了其核心
XWork
的驗證框架。提供了如下功能:
1、??
可配置的驗證文件。它的驗證文件是一個獨立的
XML
配置文件,對驗證的添加、修改只需更改配置文件,無需編譯任何的
Class
。
2、??
驗證文件和被驗證的對象完全解藕。驗證對象是普通的
JavaBean
就可以了(可以是
FormBean
、域對象等),它們不需實現任何額外的方法或繼承額外的類。
3、??
多種不同的驗證方式。因為它驗證功能是可以繼承的,所以可以用多種不同的方式指定驗證文件,比如:通過父類的
Action
、通過
Action
、通過
Action
的方法、通過
Action
所使用的對象,等等。
4、??
強大的表達式驗證。它使用了
OGNL
的表達式語言,提供強大的表達式驗證功能。
5、??
同時支持服務器端和客戶端驗證。
下面我們來看看如何為用戶注冊添加驗證功能:
1、??
注冊我們的驗證類型
WebWork
為不同的驗證要求提供不同的驗證類型。一個驗證類型,一般是有一個類來提供。這個類必須實現接口:
com.opensymphony.xwork.validator.Validator
,但我們在寫自己的驗證類型時,無需直接實現
Validator
接口,它有抽象類可供直接使用如
ValidatorSupport
、
FieldValidatorSupport
等。
驗證類型在使用之前,必須要在
ValidatorFactory
(
com.opensymphony.xwork.validator
. ValidatorFactory
)中
注冊。可以有二種方法實現驗證類型的注冊。一、寫程序代碼進行注冊,它使用
ValidatorFactory
類的靜態方法:
registerValidator(String name, String className)
。
二、使用配置文件
validators.xml
進行注冊,要求把文件
validators.xml
放到
ClassPath
的跟目錄中(
/WEB-INF/classes
)。但在實際開發中,一般都使用第二中注冊方法。我們的驗證類型注冊如下:
<validators>
??? <validator name="required" class="com.opensymphony.xwork.validator.validators.RequiredFieldValidator"/>
?? ?<validator name="requiredstring" class="com.opensymphony.xwork.validator.validators.RequiredStringValidator"/>
??? <validator name="int" class="com.opensymphony.xwork.validator.validators.IntRangeFieldValidator"/>
??? <validator name="date" class="com.opensymphony.xwork.validator.validators.DateRangeFieldValidator"/>
??? <validator name="expression" class="com.opensymphony.xwork.validator.validators.ExpressionValidator"/>
??? <validator name="fieldexpression" class="com.opensymphony.xwork.validator.validators.FieldExpressionValidator"/>
??? <validator name="email" class="com.opensymphony.xwork.validator.validators.EmailValidator"/>
??? <validator name="url" class="com.opensymphony.xwork.validator.validators.URLValidator"/>
??? <validator name="visitor" class="com.opensymphony.xwork.validator.validators.VisitorFieldValidator"/>
??? <validator name="conversion" class="com.opensymphony.xwork.validator.validators.ConversionErrorFieldValidator"/>
??? <validator name="stringlength" class="com.opensymphony.xwork.validator.validators.StringLengthFieldValidator"/>
</validators>
注冊驗證類型的配置文件非常簡單。它使用標簽
<validator
>
提供名-值對的形式注冊。這樣我們的驗證文件就可以直接引用它的名字。
2、??
開啟
Action
的驗證功能
?
如果
Action
要使用驗證框架的驗證功能,它必須在配置文件中指定攔截器“
validation
”,它的定義如下:
<interceptor name="validation" class="com.opensymphony.xwork.validator.ValidationInterceptor"/>
。
我們的驗證文件必須以
ActionName-validation.xml
格式命名,它必須被放置到與這個
Action
相同的包中。你也可以為這個
Action
通過別名的方式指定驗證文件,它的命名格式為:
ActionName-aliasname-validation.xml
。“
ActionName
”是我們
Action
的類名;“
aliasname
”是我們在配置文件(
xwork.xml
)中定義這個
Action
所用到的名稱。這樣,同一個
Action
類,在配置文件中的不同定義就可以對應不同的驗證文件。驗證框架也會根據
Action
的繼承結構去查找
Action
的父類驗證文件,如果找到它會去執行這個父類的驗證。
?
3、??
實現我們的驗證文件:
RegisterActionSupport-validation.xml
<!DOCTYPE validators PUBLIC "-//OpenSymphony Group//XWork Validator 1.0//EN" "http://www.opensymphony.com/xwork/xwork-validator-1.0.dtd">
<validators>
??? <field name="user.username">
??? <field-validator type="requiredstring">
??????????? <message>You must enter a value for username.</message>
??????? </field-validator>
??? </field>
??? <field name="user.password">
??? <field-validator type="requiredstring">
??????????? <message>You must enter a value for password.</message>
??????? </field-validator>
??????? <field-validator type="fieldexpression">
??????????? <param name="expression">user.password == verifyPassword</param>
??????????? <message>Passwords don't match.</message>
??????? </field-validator>
??? </field>
??? <field name="user.email">
??? <field-validator type="email">
??????????? <message>You must enter a valid email.</message>
??????? </field-validator>
??? </field>
??? <field name="user.age">
??? <field-validator type="int">
??????????? <param name="min">6</param>
??????????? <param name="max">100</param>
??????????? <message>Age must be between ${min} and ${max}, current value is ${user.age}.</message>
?????? ?</field-validator>
??? </field>
</validators>
說明:
1
)、
<field
>
標簽代表一個字段,它的屬性“
name
”和頁面輸入框的“
name
”屬性必需完全一致,其實它也就是我們的表達式語言。
2
)、
<field-validator
>
標簽定義我們的驗證規則,
type
屬性的值就是就是我們前面定義的驗證類型。
3
)、驗證文件中,字段的數據是通過表達式語言從我們的值堆棧(
OgnlValueStack
)中取得,一般是
Action
或
Model
對象。例如:我們的字段“
user.age
”,它會通過
Action
的
getUser().getAge()
來取得用戶輸入的年齡,再來根據驗證的類型“
int
”和最大值最小值的參數來判斷輸入的數據是否能通過驗證。
4
)、不管驗證是否通過,我們的
Action
都會執行,但如果驗證沒有通過,它不會調用
Action
的
execute()
方法。
?
4、??
顯示
Action
的驗證錯誤信息
如果用戶輸入的數據驗證沒有通過,我們需重新返回輸入頁面,并給出錯誤信息提示。攔截器棧“
validationWorkflowStack
”為我們實現了這個功能。它首先驗證用戶輸入的數據,如果驗證沒有通過將不執行我們
Action
的
execute()
方法,而是將請求重新返回到輸入頁面。
我們的
xwork.xml
配置文件如下:
<action name="registerSupport" class="example.register.RegisterActionSupport">
??????????? <result name="success" type="dispatcher">
??????????????? <param name="location">/register-result.jsp</param>
??????????? </result>
??????????? <result name="input" type="dispatcher">
??????????????? <param name="location">/registerSupport.jsp</param>
??????????? </result>
??????????? <interceptor-ref name="validationWorkflowStack"/>
??????? </action>
?
通過接口
ValidationAware
,
我們可以獲得類級別或字段級別的驗證錯誤信息,這個錯誤信息也就是我們驗證文件中
<message>
標簽里的數據。
ActionSupport
類已實現了此接口,這樣在應用中我們的
Action
只要繼承
ActionSupport
類就可以了。
RegisterActionSupport
.java
代碼如下:
package
example.register;
?
import
com.opensymphony.xwork.ActionSupport;
?
?
??? private User user= new User();
??? private String verifyPassword;
???
??? public User getUser(){
??????? returnthis.user;
??? }
???
??? public String execute(){
??????? //
在這里調用用戶注冊的業務邏輯,比如:將注冊信息存儲到數據庫
??????? return SUCCESS;
??? }
?
??? public String getVerifyPassword(){
??????? returnthis.verifyPassword;
??? }
???
??? publicvoid setVerifyPassword(String verPassword){
??????? this.verifyPassword = verPassword;
??? }
}
我們
WebWork
的
UI
標簽庫直接提供了驗證錯誤信息顯示功能。如果字段級別的驗證沒有通過,它會在輸入框上方顯示驗證文件定義的錯誤提示信息。我們將用戶輸入的頁面更改如下:
registerSupport.jsp
<%@ taglib uri="webwork" prefix="ww" %>
<html>
<head><title>Register Example</title></head>
<body>
<table border=0 width=97%>
<tr><td align="left">
??? <ww:form name="'test'" action="'/example/registerSupport.action'" method="'POST'">
??????????? <ww:textfield label="'Username'" name="'user.username'" required="true"/>
??????????? <ww:textfield label="'Password'" name="'user.password'" required="true"/>
??????????? <ww:textfield label="'VerifyPassword'" name="'verifyPassword'" required="true"/>
?????????? ?<ww:textfield label="'Email'" name="'user.email'" required="true"/>
??????????? <ww:textfield label="'Age'" name="'user.age'" required="true"/>
??????????? <ww:submit value="'Submit'"/>
???????? </ww:form>
</td></tr>
</table>
</body>
</html>
我們上面的例子使用的是服務器端驗證。
WebWork
也為我們提供了方便的客戶端驗證。它將驗證自動生成
JavaScript
腳本。如果要使用客戶端驗證只需改變相應的驗證類型就可以了(輸入頁面的表單必需使用
<ww:form>
標簽,并設置屬性“
validate="true"
”)。具體的驗證類型可以在
WebWork
的包
com.opensymphony.webwork.validators
中找到。
posted @ 2006-09-01 13:40 Binary 閱讀(681) | 評論 (0) | 編輯 收藏 WebWork教程- Interceptor(攔截器)
摘要: Interceptor
(攔截器)將
Action
共用的行為獨立出來,在
Action
執行前后運行。這也就是我們所說的
AOP
(
Aspect Oriented Programming
,面向切面編程),它是分散關注的編程方法,它將通用需求功能從不相關類之中分離出來;同時,能夠使得很多類共享一個行為,一... 閱讀全文
posted @ 2006-09-01 13:39 Binary 閱讀(616) | 評論 (0) | 編輯 收藏 WebWork介紹-Action篇
摘要: Action
簡介
Action
在
MVC
模式中擔任控制部分的角色
,
在
WebWork
中使用的最多
,
用于接收頁面參數,起到對
HttpRequest
判斷處理作用。每個請求的動作都對應于一個相應的
... 閱讀全文
posted @ 2006-09-01 13:38 Binary 閱讀(230) | 評論 (0) | 編輯 收藏 Log4J學習筆記
posted @ 2006-09-01 13:25 Binary 閱讀(436) | 評論 (0) | 編輯 收藏 |
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||