通过王涛完成的项目练习,发现了struts中的表单校验失败后重显的一个问题:假设ActionForm Bean中有一个整数类型的属性,如果将其类型定义为int,这个属性的默认值是0;在表单页面中用一个文本框来输入这个属性的值,当文本框中没有填写任何内容时,发送到WEB服务器的参数值为一空字符串"";当ActionForm Bean中的其它属性校验失败时,回到表单页面重新显示,这时,与整数字段对应的文本框中显示的内容为0,而不是最初的那样(没有任何内容)。
为此,我们想到了在Spring MVC中所采用的办法:将整数类型的属性定义为Integer类型,这样,该属性的默认值为null,借助<html:property>可将null显示为空字符串,但是,实际运行发现,ActionForm Bean中的其它属性校验失败回到表单页面重新显示时,与Integer类型的属性对应的文本框中显示的内容仍然为0。这说明struts在将请求参数组装进ActionForm Bean对象中时、它也会将内容为空字符串""的请求参数(文本框中不填写任何内容时即会出现这种情况)装配到ActionForm Bean中,并且将空字符串""转变成0值的Integer数据。对于这种情况,我们想到了将原本属于整数的属性设计成String类型的妥协解决办法,但觉得不是很理想,想知道各位有经验的朋友对这种情况是如何处理的?特向各位朋友请教。
下面是问题的完整描述:
假设有一个注册课程的表单,其中包含有“课程名”、“学分”等字段信息,显然“课程名”是String类型,“学分”是整数类型,与这个表单对应的ActionForm可以设计成如下形式:
public class RegisterCourseForm extends ActionForm
{
private String name;
public String getName()
{ return name;
}
public void setName(String name) {
this.name = name;
}
private Integer score;
public Integer getScore()
{
return score;
}
public void setScore(Integer score)
{
this.score = score;
}
public ActionErrors validate(ActionMapping mapping,HttpServletRequest request)
{
if("".equals(name))
{
ActionErrors errors = new ActionErrors();
errors.add("name",new ActionMessage("required.name"));
return errors;
}
return null;
}
}
注册课程的表单页面的主要内容如下:
<%@ taglib uri="http://jakarta.apache.org/struts/tags-bean" prefix="bean"%>
<%@ taglib uri="http://jakarta.apache.org/struts/tags-html" prefix="html"%>
<html:form action="/registerCourse">
name : <html:text property="name"/><html:errors property="name"/><br/>
score : <html:text property="score"/><html:errors property="score"/><br/>
<html:submit/>
</html:form>
为了让这个用例能够运行,同时又简化整个程序的代码,我们直接使用Struts提供的ForwardAction,大家也可以使用MyEclipse自动为我们创建的没有任何业务逻辑的Action。在struts-config.xml文件中的配置片段如下:
<form-bean name="registerCourseForm" type="cn.itcast.form.RegisterCourseForm" />
......
<action parameter="/WEB-INF/jsp/registerCourse.jsp"
path="/index" type="org.apache.struts.actions.ForwardAction"/>
<action
input="/WEB-INF/jsp/registerCourse.jsp"
name="registerCourseForm"
path="/registerCourse"
scope="request"
type="org.apache.struts.actions.ForwardAction"
parameter="/WEB-INF/jsp/registerCourse.jsp"
/>
(1)首先在浏览器地址栏中输入http://localhost:8080/CourseManager/index.do,请求交给第一个Action处理,浏览器中显示出registerCourse.jsp页面;
(2)在注册课程的表单页面不填写任何内容,直接提交表单,这时候表单校验失败(即RegisterCourseForm.validate方法返回ActionErrors对象),浏览器重新显示registerCourse.jsp页面。registerCourse.jsp页面除了显示出错误描述信息之外,还在表单中显示出上次输入的内容,现在遇到的问题是:我们上次提交表单时,并没有在学分(score)文本框中输入任何内容,但这次重显表单时,在学分(score)文本框中添入了一个0。
我猜想这是因为struts在将请求参数组装进RegisterCourseForm对象中时、将空字符串""的请求参数(文本框中不填写任何内容时即会出现这种情况)转变成了0值的Integer数据。查看struts的源代码,了解到请求参数组装到FormBean中的方法调用过程如下:
ActionServlet.doGet/doPost-->ActionServlet.process-->RequestProcessor.process-->
RequestProcessor.processActionForm,RequestProcessor.processPopulate-->RequestUtils.populate-->
BeanUtils.populate-->BeanUtilsBean.setProperty(Object bean, String name, Object value)
可见,将请求参数组装成FormBean的属性时,最终调用的是BeanUtilsBean.setProperty方法,可能的原因就是BeanUtilsBean.setProperty方法在为JavaBean的整数类型的属性进行赋值时,会将空字符串""转换成0。BeanUtilsBean类位于apache的commons-beanutils包中,大家从struts安装包的lib目录中能够找到commons-beanutils.jar包及相关的依赖包。我安排王涛写了一个程序,来验证这种效果:
package com.tony;
public class TestInteger {
public static void main(String[] args) {
Student student = new Student();
try {
BeanUtilsBean.getInstance().setProperty(student,"name","Tony");
BeanUtilsBean.getInstance().setProperty(student,"age","");
System.out.print(student);
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
package com.tony;
public class Student {
private String name;
private Integer age;
public Integer getAge() {
return age;
}
public void setAge(Integer age) {
this.age = age;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String toString()
{
return this.name + ":" + this.age;
}
}
程序最后打印出来的结果为Tony:0,这说明BeanUtilsBean.setProperty方法确实将空字符串""转换成了整数类型的0。
分享到:
相关推荐
如果验证失败,Struts会将错误信息添加到ActionContext,然后在JSP页面中显示给用户。 文件列表中的`.classpath`和`.project`是Eclipse项目的配置文件,它们与Struts的具体实现无关,但表明这个项目可能是在...
总结来说,Struts2的表单校验机制提供了多种灵活的方式,开发者可以根据实际需求选择适合的校验策略,确保用户输入的数据准确无误,从而提高应用的安全性和稳定性。无论是使用XML配置文件、注解还是自定义校验方法,...
5. **处理验证失败**:当验证失败时,Struts2会自动将错误信息放入ValueStack,然后跳转到`input`属性指定的页面。但由于ValueStack中的值可能会丢失,你可以选择实现`Preparable`接口并在`prepare()`方法中重新初始...
3. **IntRangeFieldValidator** (`int`):用于验证整数范围。可以设定最小值和最大值,以确保输入的整数值落在指定范围内。 4. **LongRangeFieldValidator** (`long`):验证长整型数值范围。 5. **...
Struts2的校验框架基于Apache Commons Validator,提供了多种预定义的验证器类型以及自定义验证器的功能。这些验证器可以在配置文件中或代码中定义,用于检查表单字段的有效性。 #### 三、示例分析 ##### 1. 配置...
Struts1.x内置了多种验证器类型,如`requiredstring`(检查是否为空)、`int`(检查是否为整数)、`long`、`email`(检查是否符合电子邮件格式)等。你可以根据需要选择合适的验证器类型。 5. **验证流程** 当...
总结来说,Struts2提供了灵活的输入校验机制,允许开发者通过Action的`validate()`方法或者XML配置文件来定义验证规则。无论选择哪种方式,都能有效地确保从客户端接收的数据符合预期,从而提高了应用的安全性和用户...
- **错误处理**:如果转换失败或验证不通过,Struts2会自动添加相应的错误信息到`ActionContext`中,并可以通过`addFieldError()`方法获取这些错误。 ### 验证配置与国际化资源 #### 配置验证规则 Struts2允许...
当用户在Web表单中填写信息并提交后,Struts会自动调用Form Bean的validate()方法进行验证。以下是一些重要的Form验证知识点: 1. **创建Form Bean**:首先,你需要定义一个Form Bean类,它通常对应于HTML表单。这...
Struts的验证框架支持多种验证类型,如`required`(必填),`int`(整数),`double`(浮点数),`email`(电子邮件地址)等。每种验证类型都有相应的验证逻辑。 5. **自定义验证器** 如果内置的验证器不能满足...
默认情况下,Struts的验证是按照顺序进行的,但如果设置了短路验证,则会在第一个验证失败后停止后续的验证步骤。 ```xml ... ``` #### 六、自定义验证器 除了内置的验证器之外,Struts还允许开发人员创建...
3. **IntRangeFieldValidator**: 验证整数类型的字段,确保数值在指定的范围内。 4. **DoubleRangeFieldValidator**: 对于浮点数或双精度数,验证其是否在给定的最小值和最大值之间。 5. **...
客户端验证可以在用户提交表单前通过JavaScript进行,而服务器端验证则是在请求到达服务器后进行,这是为了防止恶意用户绕过客户端验证。 Struts的验证框架主要由以下组件组成: 1. 验证配置文件(Validation.xml...
Struts2是一款基于MVC设计模式的开源Java框架,它为Web应用开发提供了丰富的功能,包括请求处理、视图渲染以及表单验证等。在Struts2中,表单验证是一项重要的功能,它确保了用户输入的数据符合预期的格式和范围,...
**Struts Validator** 是一个强大的框架,用于简化Web应用程序中的表单验证过程。它首次出现在Struts 0.5版本中,并逐渐发展成为Struts 1.1版本的重要组成部分之一。在Struts 1.1中,验证器的功能得到了显著增强,...
Struts的Validator-rules是Apache Struts框架的一个关键组件,主要用于处理Web应用中的表单验证。这个组件使得开发者能够方便地定义和实现客户端与服务器端的数据验证规则,从而确保用户输入的数据符合业务逻辑的...
当表单提交后,Struts2会自动执行这些验证规则,如果输入不符合规则,会抛出错误信息并返回到表单页面,提示用户修正。 压缩包中的"struts2"文件可能包含了以下内容: 1. `struts2.xml` - Struts2的核心配置文件,...
1. **默认校验**:Struts2框架提供了内置的校验机制,这些机制可以自动对表单字段进行基本的校验。例如,检查是否为空、长度限制等。 2. **添加错误消息**:当校验失败时,可以通过调用`addFieldError`方法向特定...
- `type`属性用于指定表单属性的Java类型,例如:整数类型(`java.lang.Byte`等),浮点类型(`java.lang.Float`等),字符类型(`java.lang.Character`),布尔类型(`java.lang.Boolean`),日期类型(`java.lang...