首页 > 其他分享 >Struts2之验证框架

Struts2之验证框架

时间:2022-11-16 17:31:26浏览次数:45  
标签:拦截器 框架 验证 18 chars bytes Struts2 user


1:Struts2提供了验证框架,功能强大而且简单易用,帮助用户做了很多事情,使得用户不必从头开发。那么一个好的验证框架需要考虑哪些因素呢?

   *验证功能的复用性

    比如都是对一个int数据类型的验证,验证的是它的数据范围,如果验证功能抽象的好,就可以复用同样的验证功能,省去重复开发的麻烦。

   *验证功能的可扩展性

      是不是可以自己扩展验证功能,并保证扩展功能和原有的框架功能一样使用。

    *验证与业务逻辑分离

      在业务开发时,可能需要在业务逻辑不变的情况下修改验证逻辑,比如某个网站要求大于18周岁的公民才能注册,随着业务的开展,要修改为大于15岁的公民才能注册,很显然,这个时候,注册逻辑本身没有改变,但是验证逻辑发生了变化,那么,分离的验证逻辑可以保证在修改验证逻辑的时候,不会为业务逻辑带来麻烦。

 

 2:验证框架入门

     验证需求:用户注册时只需要填写自己的账号、姓名、年龄,其中,账号和姓名必须填写,年龄要求必填而且在18岁以上。

     简单示例:

     页面:register.jsp

      

<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<%@ taglib prefix="s" uri="/struts-tags" %>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>Struts2验证框架</title>
</head>
<body>
<s:form action="register" method="post">
<s:textfield name="user.account" label="账号" />
<s:textfield name="user.name" label="姓名" />
<s:textfield name="user.age" label="年龄" />
<s:submit value="注册" />
</s:form>
</body>
</html>


Action的内容:

   

package com.capinfotech.action;

import com.capinfotech.model.UserModel;

public class RegisterAction extends BaseAction {

private UserModel user = new UserModel();

public UserModel getUser() {
return user;
}

public void setUser(UserModel user) {
this.user = user;
}

public String execute() {
System.out.println("传人的数据为:" + user.toString());
return SUCCESS;
}

}


struts.xml的内容:

 

<action name="register" class="com.capinfotech.action.RegisterAction">
<result name="success">/validation/success.jsp</result>
<result name="input">/validation/register.jsp</result>
</action>


验证框架的配置文件RegisterAction-validation.xml

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE validators PUBLIC
"-//OpenSymphony Group//XWork Validator 1.0.2//EN"
"http://www.opensymphony.com/xwork/xwork-validator-1.0.2.dtd">
<validators>
<field name="user.account">
<field-validator type="requiredstring">
<message>请输入账号</message>
</field-validator>
</field>

<field name="user.name">
<field-validator type="requiredstring">
<message>请输入姓名</message>
</field-validator>
</field>

<field name="user.age">
<field-validator type="int">
<param name="min">18</param>
<message>年龄必须在18岁以上</message>
</field-validator>
</field>
</validators>



输出结果:

   

   


验证执行时机:验证发生在execute方法运行之前,在Struts2的params拦截器已经把请求的参数反射的设置到Action的属性之后,所以,验证框架实际上验证的是值栈里面的内容。

验证的结果:如果用户输入的参数完全满足验证条件,则会继续执行execute方法,如果用户输入的参数不满足验证条件,注意:3个验证条件只要有一个验证通不过,就会跳转到这个Action所配置的名为input的Result,所以在struts.xml里最好配置一个名为input的result


3:验证框架的运行原理

   *首先看一下defaultStack包括的拦截器

    

<interceptor-stack name="defaultStack">
<interceptor-ref name="exception"/>
<interceptor-ref name="alias"/>
<interceptor-ref name="servletConfig"/>
<interceptor-ref name="i18n"/>
<interceptor-ref name="prepare"/>
<interceptor-ref name="chain"/>
<interceptor-ref name="debugging"/>
<interceptor-ref name="scopedModelDriven"/>
<interceptor-ref name="modelDriven"/>
<interceptor-ref name="fileUpload"/>
<interceptor-ref name="checkbox"/>
<interceptor-ref name="multiselect"/>
<interceptor-ref name="staticParams"/>
<interceptor-ref name="actionMappingParams"/>
<interceptor-ref name="params">
<param name="excludeParams">dojo\..*,^struts\..*</param>
</interceptor-ref>
<interceptor-ref name="conversionError"/>
<interceptor-ref name="validation">
<param name="excludeMethods">input,back,cancel,browse</param>
</interceptor-ref>
<interceptor-ref name="workflow">
<param name="excludeMethods">input,back,cancel,browse</param>
</interceptor-ref>
</interceptor-stack>


params拦截器和conversionError拦截器在validation拦截器的前面。

params拦截器将请求的参数反射的设置到Action的属性,当然,这时候有可能出错。

conversionError拦截器验证Action的属性是否符合条件。

validation会根据配置文件的配置进行验证,其实,validation验证的是值栈中的内容,而值栈中的内容则来源于请求的参数部分。


验证框架运行流程如下图所示:



4:验证器类型

    *验证谁

    *使用什么条件进行验证

    *不满足条件显示什么结果

    *不满足验证条件时,显示的结果出现在页面的什么位置


    *字段验证器:用来验证提交的表单内的单个字段

    

<field name="user.age">
<field-validator type="int">
<param name="min">18</param>
<message>年龄必须在18岁以上,您输入的年龄为${user.age}</message>
</field-validator>
</field>

   *field表示是字段验证器,name指示验证哪个字段,每一个field-validator元素是这个字段的一种验证条件,type指示的是验证器,验证错误时,message表示的消息会返回,message元素存在key属性,可以用来引用国际化信息


另一种写法:

  

<validator type="int">
<param name="filedName">user.age</param>
<param name="min">18</param>
<message>年龄必须在18岁以上,您输入的是${user.age}</message>
</validator>


    *动作验证器

    动作验证器应用于整个动作(Action),一般用于验证提交的表单内的多个字段之间的关系,当然也可以验证单个字段

   假定要求输入的账号也为数字,并要求输入的age的值要大于账号的值,那么在验证文件里,可以按照如下写法:

   

<validator type="expression">
<param name="expression">
<![CDATA[user.name.length() < user.account.length()]]>
</param>
<message>姓名的长度要比账号的长度小</message>
</validator>
<validators>
<validator name="required" class="com.opensymphony.xwork2.validator.validators.RequiredFieldValidator"/>
<validator name="requiredstring" class="com.opensymphony.xwork2.validator.validators.RequiredStringValidator"/>
<validator name="int" class="com.opensymphony.xwork2.validator.validators.IntRangeFieldValidator"/>
<validator name="long" class="com.opensymphony.xwork2.validator.validators.LongRangeFieldValidator"/>
<validator name="short" class="com.opensymphony.xwork2.validator.validators.ShortRangeFieldValidator"/>
<validator name="double" class="com.opensymphony.xwork2.validator.validators.DoubleRangeFieldValidator"/>
<validator name="date" class="com.opensymphony.xwork2.validator.validators.DateRangeFieldValidator"/>
<validator name="expression" class="com.opensymphony.xwork2.validator.validators.ExpressionValidator"/>
<validator name="fieldexpression" class="com.opensymphony.xwork2.validator.validators.FieldExpressionValidator"/>
<validator name="email" class="com.opensymphony.xwork2.validator.validators.EmailValidator"/>
<validator name="url" class="com.opensymphony.xwork2.validator.validators.URLValidator"/>
<validator name="visitor" class="com.opensymphony.xwork2.validator.validators.VisitorFieldValidator"/>
<validator name="conversion" class="com.opensymphony.xwork2.validator.validators.ConversionErrorFieldValidator"/>
<validator name="stringlength" class="com.opensymphony.xwork2.validator.validators.StringLengthFieldValidator"/>
<validator name="regex" class="com.opensymphony.xwork2.validator.validators.RegexFieldValidator"/>
<validator name="conditionalvisitor" class="com.opensymphony.xwork2.validator.validators.ConditionalVisitorFieldValidator"/>
</validators>
package com.capinfotech.validator;

import com.opensymphony.xwork2.validator.ValidationException;
import com.opensymphony.xwork2.validator.validators.FieldValidatorSupport;

public class ChineseValidator extends FieldValidatorSupport {

/**
* 表示是否包含有中文,有3中模式
* none:没有中文
* some:含有中文字符,取默认值
* all:全是中文字符
*/
private String mode = "some";

public void setMode(String mode) {
this.mode = mode;
}

@Override
public void validate(Object object) throws ValidationException {

//获得字段名
final String fieldName = this.getFieldName();
//获得字段值
final String fieldValue = (String)this.getFieldValue(fieldName, object);
//获得字节数
final int bytes = fieldValue.getBytes().length;
//获得字符数
final int chars = fieldValue.length();

System.out.println("bytes:" + bytes);
System.out.println("chars:" + chars);

if(mode.equals("none")) {
//要求全是非中文字符
//所以字节数和字符数,两个数字必须相等,不相等则出错
if(chars != bytes) {
this.addFieldError(fieldName, object);
}
} else if(mode.equals("some")) {
//现在要求包含有中文字符
if(chars == bytes || chars * 2 == bytes) {
this.addFieldError(fieldName, object);
}
} else if(mode.equals("all")) {
if(chars * 2 != bytes) {
this.addFieldError(fieldName, object);
}
}
}
}

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE validators PUBLIC
"-//OpenSymphony Group//XWork Validator Config 1.0//EN"
"http://www.opensymphony.com/xwork/xwork-validator-config-1.0.dtd">

<!-- START SNIPPET: validators-default -->
<validators>
<validator name="required" class="com.opensymphony.xwork2.validator.validators.RequiredFieldValidator"/>
<validator name="requiredstring" class="com.opensymphony.xwork2.validator.validators.RequiredStringValidator"/>
<validator name="int" class="com.opensymphony.xwork2.validator.validators.IntRangeFieldValidator"/>
<validator name="long" class="com.opensymphony.xwork2.validator.validators.LongRangeFieldValidator"/>
<validator name="short" class="com.opensymphony.xwork2.validator.validators.ShortRangeFieldValidator"/>
<validator name="double" class="com.opensymphony.xwork2.validator.validators.DoubleRangeFieldValidator"/>
<validator name="date" class="com.opensymphony.xwork2.validator.validators.DateRangeFieldValidator"/>
<validator name="expression" class="com.opensymphony.xwork2.validator.validators.ExpressionValidator"/>
<validator name="fieldexpression" class="com.opensymphony.xwork2.validator.validators.FieldExpressionValidator"/>
<validator name="email" class="com.opensymphony.xwork2.validator.validators.EmailValidator"/>
<validator name="url" class="com.opensymphony.xwork2.validator.validators.URLValidator"/>
<validator name="visitor" class="com.opensymphony.xwork2.validator.validators.VisitorFieldValidator"/>
<validator name="conversion" class="com.opensymphony.xwork2.validator.validators.ConversionErrorFieldValidator"/>
<validator name="stringlength" class="com.opensymphony.xwork2.validator.validators.StringLengthFieldValidator"/>
<validator name="regex" class="com.opensymphony.xwork2.validator.validators.RegexFieldValidator"/>
<validator name="conditionalvisitor" class="com.opensymphony.xwork2.validator.validators.ConditionalVisitorFieldValidator"/>
<validator name="chinese" class="com.capinfotech.validator.ChineseValidator"/>
</validators>
<!-- END SNIPPET: validators-default -->

<field name="user.name">
<field-validator type="requiredstring">
<message>请输入姓名</message>
</field-validator>

<field-validator type="chinese">
<param name="mode">none</param>
<message>用户账号,只能输入非中文的字符</message>
</field-validator>
</field>

标签:拦截器,框架,验证,18,chars,bytes,Struts2,user
From: https://blog.51cto.com/woshisap/5856871

相关文章