- 浏览: 93168 次
- 性别:
- 来自: 湖南
文章分类
最新评论
-
凡尘不了De:
大哥能否发一份源码,不甚感激,研究一下组卷的算法。。邮箱 lw ...
一个有点像样的考试系统 -
15959912925:
找到原因没?现在是14jar报这个错误,很无语,网上找了一堆也 ...
连接oracle数据库的一个报错 -
Mr_lee_2012:
来过。马克。
Java继承,深度理解。不上机运行你能正确写出运行结果吗? -
konnin:
打个能否给我一份源代码啊,我邮箱是pkonnin@gmail. ...
一个有点像样的考试系统 -
fy616508150:
楼主辛苦了``
Java继承,深度理解。不上机运行你能正确写出运行结果吗?
Struts2讲义34(转载)
第8 章 Struts2 输入校验
前 1 章记述的类型转换异常处理情况其实就笔者认为也可以算是 Struts2 的输入校验中的 1 种方式。在记述 Struts2 的核心技术时候,笔者也简单介绍过一些输入校验的 Struts2 的自带类和方法。现在在本章重新整理一下,将 Struts2 中的所有输入校验的使用做个完整而又详细的介绍。
8.1 validate 输入校验方式再谈
在 Web 系统项目中有大量的视图页面需要用户自行输入很多数据。这些数据的类型有很多种。为了防止某些客户的恶意输入以及对 Web 项目的恶意破坏。必须引入输入校验像 Windows 操作系统中的防火墙一样把一些“垃圾”数据过滤,挡在 Web 系统之外。
Struts2 的输入校验是以上一章的类型转换为基础。而且输入校验一般和 Web 系统的业务逻辑息息相关。所以在阅读本章前,笔者建议读者能仔细参看类型转换章节。有了坚实的基础再来阅读本章。
在前面的章节中笔者也对 Struts2 输入校验中最基本的使用 validate 方式做过简单介绍,本小节再次就这一话题进行讨论。
8.1.1 复习 validate 方法进行输入校验
技术要点
本节代码就 1 个简单的用户注册功能具体介绍利用 validate 方法对数字、字符串、日期等类型数据进行输入校验方式介绍。
几种基本 Java 数据类型输入校验。
针对具体业务逻辑进行输入校验。
演示代码
使用的 Action 文件:
- <!------------ 文件名: RegisterAction.java---------------->
- public class RegisterAction extends ActionSupport {
- // Action 类公用私有变量,用来做页面导航标志
- private static String FORWARD = null ;
- // 用户名属性
- private String username;
- ………
- // 年龄属性
- private int age;
- // 取得用户名值
- public String getUsername() {
- return username;
- }
- // 设置用户名值
- public void setUsername(String username) {
- this .username = username;
- }
- …………………
- // 取得年龄值
- public int getAge() {
- return age;
- }
- // 设置年龄值
- public void setAge(int age) {
- this .age = age;
- }
- // 执行注册方法
- public String execute() throws Exception {
- FORWARD = "success";
- return FORWARD ;
- }
- // 校验方法,用来输入校验
- public void validate() {
- // 校验是否输入用户名
- if (getUsername() == null || getUsername().trim().equals("")) {
- addFieldError("username", " 请输入用户名 ");
- }
- // 校验是否输入生日
- if (getBirthday()==null ){
- addFieldError("birthday", " 请输入生日日期 ");
- }else
- // 校验是否输入正确的生日日期
- if (getBirthday().after(new Date())){
- addFieldError("birthday", " 请不要输入未来日期 ");
- }
- // 校验是否输入密码
- if (getPassword() == null || getPassword().trim().equals("")) {
- addFieldError("password", " 请输入密码 ");
- }
- // 校验是否输入确认密码
- if (getRepassword() == null || getRepassword().trim().equals("")) {
- addFieldError("repassword", " 请输入确认密码 ");
- }
- // 校验输入的密码和确认密码是否一致
- if (!getPassword().equals(getRepassword())) {
- addFieldError("repassword", " 确认密码和密码输入不一致 ");
- }
- // 校验输入的手机号码长度是否正确
- if (getMobile().length()!=11) {
- addFieldError("mobile", " 请输入正确的手机号码 ");
- }
- // 校验输入的年龄是否正确
- if (getAge()<1||getAge()>99) {
- addFieldError("age", " 请输入您的真实年龄 ");
- }
- }
- }
<!------------ 文件名: RegisterAction.java----------------> public class RegisterAction extends ActionSupport { // Action 类公用私有变量,用来做页面导航标志 private static String FORWARD = null ; // 用户名属性 private String username; ……… // 年龄属性 private int age; // 取得用户名值 public String getUsername() { return username; } // 设置用户名值 public void setUsername(String username) { this .username = username; } ………………… // 取得年龄值 public int getAge() { return age; } // 设置年龄值 public void setAge(int age) { this .age = age; } // 执行注册方法 public String execute() throws Exception { FORWARD = "success"; return FORWARD ; } // 校验方法,用来输入校验 public void validate() { // 校验是否输入用户名 if (getUsername() == null || getUsername().trim().equals("")) { addFieldError("username", " 请输入用户名 "); } // 校验是否输入生日 if (getBirthday()==null ){ addFieldError("birthday", " 请输入生日日期 "); }else // 校验是否输入正确的生日日期 if (getBirthday().after(new Date())){ addFieldError("birthday", " 请不要输入未来日期 "); } // 校验是否输入密码 if (getPassword() == null || getPassword().trim().equals("")) { addFieldError("password", " 请输入密码 "); } // 校验是否输入确认密码 if (getRepassword() == null || getRepassword().trim().equals("")) { addFieldError("repassword", " 请输入确认密码 "); } // 校验输入的密码和确认密码是否一致 if (!getPassword().equals(getRepassword())) { addFieldError("repassword", " 确认密码和密码输入不一致 "); } // 校验输入的手机号码长度是否正确 if (getMobile().length()!=11) { addFieldError("mobile", " 请输入正确的手机号码 "); } // 校验输入的年龄是否正确 if (getAge()<1||getAge()>99) { addFieldError("age", " 请输入您的真实年龄 "); } } }
配置文件中的导航定义:
- <!-------------- 文件名: struts.xml---------------->
- <struts>
- <!-- Action 所在包定义 -->
- <package name="C08.1.1" extends="struts-default">
- <!-- Action 名字,类以及导航页面定义 -->
- <!-- 通过 Action 类处理才导航的的 Action 定义 -->
- <action name="Register"
- class="action.RegisterAction">
- <result name="input">/jsp/register.jsp</result>
- <result name="success">/jsp/success.jsp</result>
- </action>
- <!-- 直接导航的的 Action 定义 -->
- <action name="index" >
- <result >/jsp/register.jsp</result>
- </action>
- </package>
- </struts>
<!-------------- 文件名: struts.xml----------------> <struts> <!-- Action 所在包定义 --> <package name="C08.1.1" extends="struts-default"> <!-- Action 名字,类以及导航页面定义 --> <!-- 通过 Action 类处理才导航的的 Action 定义 --> <action name="Register" class="action.RegisterAction"> <result name="input">/jsp/register.jsp</result> <result name="success">/jsp/success.jsp</result> </action> <!-- 直接导航的的 Action 定义 --> <action name="index" > <result >/jsp/register.jsp</result> </action> </package> </struts>
输入校验的数据输入 JSP 文件:
- <!------------------- 文件名: register.jsp--------------------->
- …………
- <!-- 用户信息注册 form 表单 -->
- <s:form action="Register">
- <table width="60%" height="76" border="0">
- <!-- 各标签定义 -->
- <s:textfield name="username" label=" 用户名 "/>
- <s:password name="password" label=" 密 码 " />
- <s:password name="repassword" label=" 密 码确认 " />
- <s:textfield name="birthday" label=" 生日 "/>
- <s:textfield name="mobile" label=" 手机号码 "/>
- <s:textfield name="age" label=" 年龄 "/>
- <s:submit value=" 注册 " align="center"/>
- </table>
- </s:form>
<!------------------- 文件名: register.jsp---------------------> ………… <!-- 用户信息注册 form 表单 --> <s:form action="Register"> <table width="60%" height="76" border="0"> <!-- 各标签定义 --> <s:textfield name="username" label=" 用户名 "/> <s:password name="password" label=" 密 码 " /> <s:password name="repassword" label=" 密 码确认 " /> <s:textfield name="birthday" label=" 生日 "/> <s:textfield name="mobile" label=" 手机号码 "/> <s:textfield name="age" label=" 年龄 "/> <s:submit value=" 注册 " align="center"/> </table> </s:form>
数据不进行任何输入显示出错信息如图 8.1 。
图 8.1 输入校验发现数据没有进行任何输入
输入密码不一致时的出错信息显示如图 8.2 。
图 8.2 密码输入不一致时出错信息显示
代码解释
( 1 ) Struts2 对输入校验这方面采用的最基本方法是在每个 Action 里继承 ActionSupport 类,并且重写它的输入校验方法 validate() 。本示例中的 RegisterAction 代码中也显示,根据页面上输入的各种校验将所有不符合输入校验规则的错误信息都由 ActionSupport 类中另一个方法 addFieldError 方法将错误信息加入到表单错误信息,并且在输入数据的页面显示,而不会再由 Action 导航到注册成功页面。 struts.xml 也定义了 1 个名字为“ input ”的 result ,它表明将所有输入失败的错误信息导航到一个特定页面。本示例中笔者还是将这个特定页面定义为数据输入的页面。
( 2 )再次阅读 RegisterAction 代码,可以发现在 validate 方法里笔者编写了很多 if 语句。每一个 if 语句中都针对表单中某一字段进行输入校验。如果发现不符合输入校验规则则都调用 addFieldError 方法。该方法中有两个参数,第 1 个参数都是表单中字段名,这里所有的名字都和输入数据的页面中每一个字段的 name 属性中内容相同。否则 Struts2 是找不到具体错误信息是针对哪一个字段。第 2 个参数则是错误信息的内容。这些内容就是在输入校验失败时候显示在之前所说的特定页面中的。由图 7.1 和图 7.2 可以看到这些内容在页面上是如何显示的。
( 3 ) validate 方法中的各个 if 语句判断了表单中各个字段的输入数据是否符合输入校验的规则,这些规则也是开发人员根据特定业务逻辑定义的。比如其中数据是否输入,输入的生日信息是否在当前日期之前等等。这里细心读者又可以发现并没有对这些字段进行类型转换,但在 Action 中某些字段类型都已经变成 Java 的一些基本类型。比如生日字段,页面上输入时候是字符串,在 Action 中已经变成 Java 中的 Date 类型。因为之前在类型转换章节也已说明:页面上输入的数据已经都由字符串类型转换成 Action 中指定的 Java 类型。因此从这一点更加说明类型转换是输入校验的基础,也可以说是 1 种特定的输入校验。
8.1.2 validateXXX 方法进行输入校验
技术要点
本节代码也就 1 个简单的用户注册功能具体介绍利用 validateXXX 方法对 Action 中某一特定的方法进行校验。
Action 具体方法的 validateXXX 方法介绍。
演示代码
使用的 Action 文件:
- <!----------- 文件名: RegisterAction.java------------------>
- public class RegisterAction extends ActionSupport {
- // Action 类公用私有变量,用来做页面导航标志
- private static String FORWARD = null ;
- // 用户名属性
- private String username;
- ………
- // 年龄属性
- private int age;
- // 取得用户名值
- public String getUsername() {
- return username;
- }
- // 设置用户名值
- public void setUsername(String username) {
- this .username = username;
- }
- …………………
- // 取得年龄值
- public int getAge() {
- return age;
- }
- // 设置年龄值
- public void setAge(int age) {
- this .age = age;
- }
- // 执行注册方法
- public String Register() throws Exception {
- FORWARD = "success";
- return FORWARD ;
- }
- // 校验方法,用来输入校验
- public void validateRegister() {
- // 校验是否输入用户名
- if (getUsername() == null || getUsername().trim().equals("")) {
- addFieldError("username", " 请输入用户名 ");
- }
- // 校验是否输入生日
- if (getBirthday()==null ){
- addFieldError("birthday", " 请输入生日日期 ");
- }else
- // 校验是否输入正确的生日日期
- if (getBirthday().after(new Date())){
- addFieldError("birthday", " 请不要输入未来日期 ");
- }
- // 校验是否输入密码
- if (getPassword() == null || getPassword().trim().equals("")) {
- addFieldError("password", " 请输入密码 ");
- }
- // 校验是否输入确认密码
- if (getRepassword() == null || getRepassword().trim().equals("")) {
- addFieldError("repassword", " 请输入确认密码 ");
- }
- // 校验输入的密码和确认密码是否一致
- if (!getPassword().equals(getRepassword())) {
- addFieldError("repassword", " 确认密码和密码输入不一致 ");
- }
- // 校验输入的手机号码长度是否正确
- if (getMobile().length()!=11) {
- addFieldError("mobile", " 请输入正确的手机号码 ");
- }
- // 校验输入的年龄是否正确
- if (getAge()<1||getAge()>99) {
- addFieldError("age", " 请输入您的真实年龄 ");
- }
- }
- }
<!----------- 文件名: RegisterAction.java------------------> public class RegisterAction extends ActionSupport { // Action 类公用私有变量,用来做页面导航标志 private static String FORWARD = null ; // 用户名属性 private String username; ……… // 年龄属性 private int age; // 取得用户名值 public String getUsername() { return username; } // 设置用户名值 public void setUsername(String username) { this .username = username; } ………………… // 取得年龄值 public int getAge() { return age; } // 设置年龄值 public void setAge(int age) { this .age = age; } // 执行注册方法 public String Register() throws Exception { FORWARD = "success"; return FORWARD ; } // 校验方法,用来输入校验 public void validateRegister() { // 校验是否输入用户名 if (getUsername() == null || getUsername().trim().equals("")) { addFieldError("username", " 请输入用户名 "); } // 校验是否输入生日 if (getBirthday()==null ){ addFieldError("birthday", " 请输入生日日期 "); }else // 校验是否输入正确的生日日期 if (getBirthday().after(new Date())){ addFieldError("birthday", " 请不要输入未来日期 "); } // 校验是否输入密码 if (getPassword() == null || getPassword().trim().equals("")) { addFieldError("password", " 请输入密码 "); } // 校验是否输入确认密码 if (getRepassword() == null || getRepassword().trim().equals("")) { addFieldError("repassword", " 请输入确认密码 "); } // 校验输入的密码和确认密码是否一致 if (!getPassword().equals(getRepassword())) { addFieldError("repassword", " 确认密码和密码输入不一致 "); } // 校验输入的手机号码长度是否正确 if (getMobile().length()!=11) { addFieldError("mobile", " 请输入正确的手机号码 "); } // 校验输入的年龄是否正确 if (getAge()<1||getAge()>99) { addFieldError("age", " 请输入您的真实年龄 "); } } }
配置文件中的导航定义同 8.1.1 。输入校验的数据输入 JSP 文件同 8.1.1 有一点不同,具体代码如下:
- <!------------ 文件名: register.jsp---------------->
- …………
- <!-- fielderror 标签显示所有校验错误信息 -->
- <s:fielderror></s:fielderror>
- <!-- 用户信息注册 form 表单 -->
- <s:form action="Register!Register.action ">
- <table width="60%" height="76" border="0">
- <!-- 各标签定义 -->
- <s:textfield name="username" label=" 用户名 "/>
- <s:password name="password" label=" 密 码 " />
- <s:password name="repassword" label=" 密 码确认 " />
- <s:textfield name="birthday" label=" 生日 "/>
- <s:textfield name="mobile" label=" 手机号码 "/>
- <s:textfield name="age" label=" 年龄 "/>
- <s:submit value=" 注册 " align="center"/>
- </table>
- </s:form>
<!------------ 文件名: register.jsp----------------> ………… <!-- fielderror 标签显示所有校验错误信息 --> <s:fielderror></s:fielderror> <!-- 用户信息注册 form 表单 --> <s:form action="Register!Register.action "> <table width="60%" height="76" border="0"> <!-- 各标签定义 --> <s:textfield name="username" label=" 用户名 "/> <s:password name="password" label=" 密 码 " /> <s:password name="repassword" label=" 密 码确认 " /> <s:textfield name="birthday" label=" 生日 "/> <s:textfield name="mobile" label=" 手机号码 "/> <s:textfield name="age" label=" 年龄 "/> <s:submit value=" 注册 " align="center"/> </table> </s:form>
数据不进行任何输入显示出错信息如图 8.3 。
图 8.3 输入校验发现数据没有进行任何输入
输入密码不一致时的出错信息显示如图 8.4 。
图 8.4 密码输入不一致时出错信息显示
代码解释
( 1 ) Struts2 中除了 validate 方法之外它还有 1 种 validateXXX 方法针对 Action 中某一特定方法进行该方法的各种字段的输入校验。其中 XXX 就是该特定方法名。在本示例中笔者定义了一个 Register 方法,该方法和上一小节中的 execute 方法类似只是一个简单的导航。但是在该 RegisterAction 中就没有了 validate 方法,取而代之的是 validateRegister 方法。
注意:如果读者使用 validateRegister 方法,那最好不要再使用 validate 方法。虽然和上一小节示例代码比较这两个方法里的内容是完全一摸一样的,但是 validate 方法是对所有 Action 中方法的输入校验都进行校验, validateRegister 方法只对 Register 方法进行校验。因此两者不能重复使用,都使用会造成两个方法都进行了校验的结果。执行顺序是先 validateRegister 后 validate 。如果 validateRegister 方法有特殊的输入校验则就会被 validate 方法“覆盖”,因此达不到预期的输入校验目的。推荐读者自己进行试验,在这两个方法里设置断点运行一下就知道了。
( 2 )请读者阅读数据输入的页面代码,在代码中笔者用黑体标注的是 1 个特殊的运行 Action 的示例。这里笔者故意把名字都写为“ Register ”来让读者加深理解。首先第 1 个“ Register ”是 RegisterAction 中的方法名,一定要和方法名写成一样。而在“!”后的“ Register ”则是在 struts.xml 配置文件中定义的 RegisterAction 的映射里的“ name ”内容。黑体的内容表明该表单的 Action 是执行 RegisterAction 中的 Register 方法。如果在页面中直接写“!”后面的内容则表示执行的是 RegisterAction 中的 execute 方法。在图 8.3 浏览器中的 URL 笔者也有红框圈中,表明该表单数据输入完成后提交时候执行的是 Register 方法。这是 Struts2 中一个特殊的使用方式。如果开发者以后在使用 Struts2 的开发工作中根据特定业务逻辑不想执行 execute 方法而是执行另外一个开发完成的方法。则在视图页面(包括 velocity 和 freemarker )中可以以这种方式让表单提交后执行该开发完成的方法。
( 3 ) validateRegister 方法中各个if语句定义和上一小节的validate方法内容相同。这里笔者只是作为示例所以两个方法中的内容相同,其实可以和上一小节中的validate方法的内容不相同,用来进行Register方法中特定的表单字段输入校验。
(4)在数据输入的视图界面笔者又增加了Struts2的标签fielderror。图8.3和图8.4也可以看出在具体字段输入校验出错信息显示之外。在表单头部也有出错信息显示。这其实和Struts2的校验顺序有关。
在之前说明validateRegister方法和validate方法时候也记述了两者的执行校验顺序是先validateRegister后validate。其实在视图界面进行表单提交后。输入校验顺序是以如下的顺序:
l 查找Action中是否有validateXXX方法。如果有则执行该方法。将校验产生的错误信息放置到ActionContext对象中。
l 查找Action中是否有validate方法。如果有则执行该方法。将校验产生的错误信息放置到ActionContext对象中。
l 查找视图界面是否有fielderror标签定义。如果有则返回到result为“input”的视图。同时ActionContext对象中有关的输入校验的错误信息也显示在该视图中。
Struts2的输入校验顺序就是按照如上说明来先后执行的,这也更好的说明了validateRegister方法和validate方法并存在Action时候输入校验是如何进行的。这也是图8.3和图8.4会产生错误信息显示两遍现象的原因。
相关推荐
### Struts2讲义知识点概览 #### 一、Struts2的历史与发展 - **Struts框架的发展历程**: - Struts最初版本发布于2000年,是Java Web开发领域的一个重要里程碑。 - 随着时间的发展和技术的进步,Struts逐渐暴露...
### Struts2框架入门知识点详解 #### 一、Struts2框架概述 ##### 1.1 Struts2简介 Struts2是一个基于MVC(Model-View-Controller)设计模式的Web应用框架,用于简化Java Web应用程序的开发过程。与传统的Java Web...
struts2讲义struts2讲义struts2讲义struts2讲义struts2讲义struts2讲义struts2讲义struts2讲义struts2讲义struts2讲义struts2讲义
本讲义将详细介绍Struts2的核心概念、工作原理以及如何在实际项目中应用。 一、Struts2简介 Struts2是Apache软件基金会的开源项目,它是Struts1的升级版,旨在解决Struts1在可扩展性和灵活性上的不足。Struts2提供...
在本讲义中,我们将深入探讨Struts2的基本概念、依赖的库、启动配置以及配置文件。 首先,开发Struts2应用需要依赖一些核心的JAR文件。这些文件包括: 1. `struts2-core-2.x.x.jar`:这是Struts2框架的核心库,...
### Struts2框架详解 #### 一、Struts2框架介绍与概述 ##### 1.1 Struts2框架概述 Struts2是一个基于MVC(Model-View-Controller)模式的开源Java Web应用框架,它提供了强大的功能来帮助开发者构建灵活、可扩展...
第2章 Web基础技术简介第3章 Struts2核心技术第4章 另一Struts2核心技术:拦截器第5章 Struts2标签库第6章 Struts2非JSP视图技术第7章 Struts2类型转换技术第8章 Struts2输入校验第9章 Struts2国际化第10章 Struts2...
本讲义详细介绍了Struts2框架的各个方面,帮助开发者从基础到进阶全面掌握其用法。 1. **Struts2概述** Struts2是Apache软件基金会的开源项目,它继承了Struts1的优点并解决了其局限性,提供了更优秀的行动控制器...
### Struts2讲义知识点概览 #### 一、Struts2的历史与发展 - **Struts框架的演变**:从Struts1到Struts2,框架经历了从MVC(Model-View-Controller)架构的经典实践到更为灵活、强大的迭代升级。 - **Struts2的...
本教程讲义深入浅出地介绍了Struts2的核心概念和技术,旨在帮助开发者快速掌握这个框架的使用。 在Struts2中,主要知识点包括: 1. **MVC设计模式**:MVC模式是软件工程中的经典设计模式,它将应用程序分为模型...
这个“struts2讲义”显然提供了一个全面的教程,旨在帮助学习者理解和掌握Struts2的核心概念和技术。以下是Struts2的一些关键知识点: 1. **MVC模式**:Struts2基于Model-View-Controller(MVC)设计模式,它将应用...
Struts2讲义1 Struts2是一款基于MVC(Model-View-Controller)设计模式的Java Web开发框架,由Apache软件基金会维护。它继承了Struts1的优点,并结合了WebWork框架的功能,提供了更强大的控制层解决方案。Struts2的...
Struts2讲义 作者:吴峻申 目录 第1章 Struts过时了吗? 10 1.1 Struts历史发展过程 10 1.2 Struts2的“简历” 13 1.2.1 标签库介绍 13 1.2.2 拦截器应用目的 14 1.2.3 FilterDispatcher和Action概述 14 1.2.4 ...
西安野马计算机培训学校的STRUTS2讲义,可能涵盖了这一框架的基础知识和高级特性,帮助学员理解和掌握Struts2的核心概念。 首先,Struts2的基础部分可能包括以下几个方面: 1. **架构原理**:讲解Struts2的MVC设计...
Struts2是Apache软件基金会...总的来说,黑暗浪子的这本Struts2讲义涵盖了Struts2的各个方面,无论对于初学者还是有经验的开发者,都是一个宝贵的参考资料,能帮助读者深入理解和熟练运用Struts2框架,提高开发效率。