5.2.1 编写校验规则文件

Struts 2提供了基于校验框架的输入校验,在这种校验方式下,所有的输入校验只需要编写简单的配置文件,Struts 2的校验框架就会负责进行服务器端校验和客户端校验。

下面的应用将会示范如何利用Struts 2的校验框架进行输入校验,使用Struts 2的校验框架进行校验不必对程序代码进行任何改变,只需编写校验规则文件即可,校验规则文件指定每个表单域应该满足怎样的规则。

本应用所使用的表单代码如下。

程序清单:codes\05\5.2\BasicValidate\WEB-INF\content\regist.jsp

<form method="post" action="regist">
    用户名:<input type="text" name="name"><br />
    密&nbsp;&nbsp;码:<input type="text" name="pass"><br />
    年&nbsp;&nbsp;龄:<input type="text" name="age"><br />
    生&nbsp;&nbsp;日:<input type="text" name="birth"><br />
    <input type="submit" value="注册">
</form>

上面的粗体字代码定义了4个表单域,这4个表单域分别对应name、pass、age和birth 4个请求参数,假设本应用要求这4个请求参数满足如下规则。

name和pass只能是字母和数字,且长度必须在4到25之间。

年龄必须是1到150之间的整数。

生日必须在1900-01-01和2050-02-21之间。

本系统使用如下简单的Action处理类。

程序清单:codes\05\5.2\BasicValidate\WEB-INF\src\org\crazyit\struts2\action\RegistAction.java

public class RegistAction extends ActionSupport
{
    //该请求包含的4个请求参数
    private String name;
    private String pass;
    private int age;
    private Date birth;
    //此处省略了4个属性的setter和getter方法
    ...
}

在上面的Action中,仅提供了4个属性来封装用户请求参数,并为这4个属性提供了对应的setter和getter方法。初看起来,这个类是一个普通的JavaBean,不是Action,但由于它继承了ActionSupport类,因此它也包含了一个execute方法,且该方法直接返回success字符串。

采用Struts 2的校验框架时,只需要为该Action指定一个校验文件即可。校验文件是一个XML 配置文件,该文件指定了 Action 的属性必须满足怎样的规则。下面是该应用中 Action的校验文件代码。

程序清单:codes\05\5.2\BasicValidate\WEB-INF\src\org\crazyit\struts2\action\RegistAction-validation.xml

<?xml version="1.0" encoding="GBK"?>
<!-- 指定校验配置文件的DTD信息 -->
<!DOCTYPE validators PUBLIC
    "-//OpenSymphony Group//XWork Validator 1.0.3//EN"
    "http://www.opensymphony.com/xwork/xwork-validator-1.0.3.dtd">
<!-- 校验文件的根元素 -->
<validators>
    <!-- 校验Action的name属性 -->
    <field name="name">
          <!-- 指定name属性必须满足必填规则 -->
          <field-validator type="requiredstring">
                <param name="trim">true</param>
                <message>必须输入名字</message>
          </field-validator>
          <!-- 指定name属性必须匹配正则表达式 -->
          <field-validator type="regex">
                <param name="expression"><![CDATA[(\w{4,25})]]></param>
                <message>您输入的用户名只能是字母和数字
                    ,且长度必须在4到25之间</message>
          </field-validator>
    </field>
    <!-- 校验Action的pass属性 -->
    <field name="pass">
          <!-- 指定pass属性必须满足必填规则 -->
          <field-validator type="requiredstring">
                <param name="trim">true</param>
                <message>必须输入密码</message>
          </field-validator>
          <!-- 指定pass属性必须满足匹配指定的正则表达式 -->
          <field-validator type="regex">
                <param name="expression"><![CDATA[(\w{4,25})]]></param>
                <message>您输入的密码只能是字母和数字
                    ,且长度必须在4到25之间</message>
                </field-validator>
          </field>
          <!-- 指定age属性必须在指定范围内-->
          <field name="age">
                  <field-validator type="int">
                    <param name="min">1</param>
                    <param name="max">150</param>
                    <message>年龄必须在1到150之间</message>
                  </field-validator>
          </field>
          <!-- 指定birth属性必须在指定范围内-->
          <field name="birth">
                <field-validator type="date">
                  <!-- 下面指定日期字符串时,必须使用本Locale的日期格式 -->
                  <param name="min">1900-01-01</param>
                  <param name="max">2050-02-21</param>
                  <message>生日必须在${min}到${max}之间</message>
                </field-validator>
          </field>
     </validators>

Struts 2的校验文件规则与Struts 1的校验文件设计方式不同,Struts 2中的每个Action都有一个校验文件。从这种设计来看,Struts 2的校验框架可以更方便地进行模块化开发,Struts 2的Action与校验规则文件具有如下共性。

Action类与校验规则文件保存在同一路径下。

Action类的类名作为校验规则文件的文件名前缀。

通过上面这种设计,Struts 2应用的Action可以非常方便地与校验规则文件同步修改、同步升级,非常有利于模块化开发。

Struts 2的校验规则文件的文件名应该遵守如下命名规则。

<Action名字>-validation.xml

前面的Action名字是可以改变的,后面的-validation.xml部分总是固定的,且该文件应该被保存在与 Action class 文件相同的路径下。例如,本应用的 Action class 文件保存在WEB-INF/classes/lee路径下,故该校验规则文件也应该保存在该路径下。

注意

上面的校验规则文件的DTD升级到了1.0.3,与Struts 2.0所使用的1.0.2相比,1.0.3的DTD允许<message.../>元素使用<param.../>子元素;而1.0.2的DTD是不允许的。

增加了该校验文件后,系统会自动加载该文件。当用户提交请求时,Struts 2的校验框架会根据该文件对用户请求进行校验。

当输入校验失败后,Struts 2 将会自动返回名为 input 的逻辑视图,因此我们还应该为该Action配置增加一个<result.../>子元素——为input逻辑视图指定实际的物理视图资源。下面是本应用中的Action配置片段。

程序清单:codes\05\5.2\BasicValidate\WEB-INF\src\struts.xml

<!-- 下面配置本系统的Action -->
<action name="regist" class="org.crazyit.struts2.action.RegistAction">
    <!-- 指定输入校验失败后返回registForm.jsp页面 -->
    <result name="input">/WEB-INF/content/registForm.jsp</result>
    <result>/WEB-INF/content/show.jsp</result>
</action>

为了在input视图对应的JSP页面中输出错误提示,应该在该页面中增加如下代码:

<!-- 输出类型转换失败提示和校验失败提示 -->
<s:fielderror/>

上面的<s:fielderror/>标签专门负责输出系统的FieldError信息,也就是输出系统的类型转换失败提示,以及输入校验失败提示。

提示:

如果我们在regist.jsp页面中使用Struts 2的表单标签来生成表单,则无须在该页面中使用<s:fielderror/>标签即可输出校验失败的错误提示,因为Struts 2的表单标签默认就能输出校验失败的错误提示。本书后面章节会详细介绍Struts 2的标签库。

如果浏览者的输入不满足校验规则,将可以看到如图5.4所示的界面。

图5.4 使用校验框架的效果

从图5.4中可以看出,这种基于Struts 2的校验框架的校验方式完全可以替代手动校验,而且这种校验方式的可重用性非常高,只需要在配置文件中配置校验规则,即可完成数据校验,无须用户书写任何数据校验代码。