struts2框架(五) 数据校验,数据回显,模型驱动,防止表单重复提交

1.数据校验

Struts数据效验, 通过拦截器完成

1.1 Struts2进行表单验证(手工方式)

a.配置表单

       
用户名:
密码:
邮箱:
生日:

b.UserAction.java

//b.1 代码方式验证Action中所有的方法
//注意:如果要想用struts的数据效验功能,必须继承ActionSupport或实现相关接口
public class UserAction extends ActionSupport {
    
    // 封装请求数据
    private User user = new User();
    public void setUser(User user) {
        this.user = user;
    }
    public User getUser() {
        return user;
    }

    // 重写数据验证的方法
    @Override
    public void validate() {
        // 用户名非空
        if (user.getUserName() == null || "".equals(user.getUserName())) {
            // 保存错误信息
            super.addFieldError("userName", "用户名必须填写!");
        }
        // 密码
        if (user.getPwd() == null || "".equals(user.getPwd())) {
            super.addFieldError("pwd", "密码必填");
        }
    }
}
b.2 代码方式验证Action中指定的方法
写验证方法命名规则:
    validate + 要验证的方法名
如:
    public void validateRegister() {}
    只会验证当前action的register方法!

总结代码方式验证:
繁琐,设计很多重复的验证逻辑!例如:非空验证、数值验证、email、日期等。

1.2 XML方式验证Action中所有的方法

Struts对于常用的验证,进行了封装,即提供了验证器, 验证指定的常用业务逻辑!

Struts提供的所有验证器
路径:xwork-core-2.3.4.1.jar/com.opensymphony.xwork2.validator.validators/default.xml






    
    
    
    
    
    
    
    
    
    
    
    
    
    
    
    


如果写xml,从而定义验证规则:
1)XML文件名称语法: ActionClassName-validation.xml
注意:此xml需要与当期要验证的action在同一个目录:
举例:UserAction-validation.xml
2) 写XML




    
    
    
        
        
            
            用户名不能为空!
        
    
    
    
    
        
        
        
            密码不能为空!
        
        
        
        
            6
            8
            密码必须为6-8位!
        
        
    
    
        
            日期格式不对!
        
        
    
    
        
            邮箱格式错误!
        
        
   

如果验证Action中指定的方法:
与上面xml验证方式大致相同: 验证xml文件内容不变;

   文件命名:
    语法:ActionClassName-ActionName-validation.xml
    举例:UserAction-user_register-validation.xml
          验证UserAction中的register方法

2.数据回显

数据回显,必须要用struts标签!

Action中:

// 进入修改页面
    public String viewUpdate() {
        // 模拟一个对象(先获取一个id,再根据id调用service查询,把查到的结果保存到域)
        User userInfo = new User();
        userInfo.setUserName("Jack");
        userInfo.setEmail("[email protected]");
        
        ActionContext ac = ActionContext.getContext();
//      Map request = (Map) ac.get("request");
//      request.put("userInfo", userInfo);
        
        /************* 数据回显***************/
        // 获取值栈
        ValueStack vs = ac.getValueStack();
        vs.pop();// 移除栈顶元素
        vs.push(userInfo);  // 入栈       
        
        // 进入修改页面
        return "viewUpdate";
    }

JSP页面:


    <%@taglib uri="/struts-tags" prefix="s" %>      
    
用户名:
邮箱:

3. 模型驱动

Struts运行时候,会执行默认的拦截器栈,其中有一个拦截器,模型驱动拦截器,可以把请求数据自动填充的action的属性中

实例:
JSP

   
   

Action

  1. 实现ModelDriver接口
  2. 实现接口方法: 接口方法返回的就是要封装的对象
  3. 对象一定要实例化。
public class UserAction extends ActionSupport implements ModelDriven {
    
    // 封装请求数据
    private User user = new User();
    public void setUser(User user) {
        this.user = user;
    }
    public User getUser() {
        return user;
    }
    
    // 实现模型驱动接口方法
    @Override
    public User getModel() {
        return user;
    }
    
    
    public String add() {
        // 测试: 使用了模型驱动,是否数据正常? Ok
        System.out.println(user);
        return "success";
    }
}

4.防止表单重复提交

Struts提供了防止表单重复提交拦截器:

用户重复提交表单在某些场合将会造成非常严重的后果。例如,在使用信用卡进行在线支付的时候,如果服务器的响应速度太慢,用户有可能会多次点击提交按钮,而这可能导致那张信用卡上的金额被消费了多次。因此,重复提交表单会对你的系统带来逻辑影响,必须采取一些措施防止这类情况的发生。
用户重复提交同一个HTML表单的原因有:
一、快速多次点击了提交按钮;
二、提交表单后按下浏览器的刷新按钮。
Struts 2已经内置了能够防止用户重复提交同一个HTML表单的功能。它的工作原理:让服务器生成一个唯一标记,并在服务器和表单里各保存一份这个标记的副本。此后,在用户提交表单的时候,表单里的标记将随着其他请求参数一起发送到服务器,服务器将对他收到的标记和它留存的标记进行比较。如果两者匹配,这次提交的表单被认为是有效的,服务器将对之做出必要的处理并重新设置一个新标记。随后,提交相同的表单就会失败,因为服务器上的标记已经重置。
  Struts 2标签中的token标签,可以用来生成一个独一无二的标记。这个标记必须嵌套在form标签中使用,它会在表单里插入一个隐藏字段并把标记保存到HttpSession对象里。toke标签必须与Token或Token Session拦截器配合使用,两个拦截器都能对token标签进行处理。Token拦截器遇到重复提交表单的情况,会返回一个"invalid.token"结果并加上一个动作级别的错误。Token Session拦截器扩展了Token拦截器并提供了一种更复杂的服务,它采取的做法与Token拦截器不同,它只是阻断了后续的提交,这样用户不提交多少次,就好像只是提交了一次。

示例:使用Token拦截器预防表单重复提交

4.1 配置struts.xml文件,声明动作




    
        
            
            
        
            /error.jsp
            /input.jsp
            /output.jsp
        
    

此时,需要在动作的声明中,为动作添加token拦截器,因为token拦截器不在defaultStack拦截器栈中,注意,需要将拦截器放在拦截器栈的第一位,这是因为判断表单是否被重复提交的逻辑应该在表单处理前。

4.2 创建动作类

public class AvoidAction extends ActionSupport {
    private static final long serialVersionUID = 2676453800249807631L;
    
    private String username;
    private Date birthday;
    
    public String getUsername() {
        return username;
    }
    public void setUsername(String username) {
        this.username = username;
    }
    public Date getBirthday() {
        return birthday;
    }
    public void setBirthday(Date birthday) {
        this.birthday = birthday;
    }
    
    @Override
    public String execute()
    {
        try {
            Thread.sleep(4000);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
        
        return SUCCESS;
    }

}

这个动作逻辑处理为挂起4秒钟,让我们有机会多次点击提交按钮,测试效果。

4.4 创建页面:

input.jsp


    
    
    
    

要使用Struts 2的防止表单重复提交功能,需要在form标签中使用token标签,他会产生一个唯一的标识符,与其他参数一起提交到服务器,服务器会根据token标签所产生的标识符判断表单是否为重复提交的表单,这个功能是由Token拦截器完成的。

error.jsp


    do not duplicate submissions form!

当表单重复提交,Token拦截器会返回一个"invalid.token"结果,结果将页面转到这个页面,提示用户错误信息。

output.jsp


    Your Name : 
    
Your Birthday :

4.5 测试

在浏览器中输入:http://localhost:8080/struts04/input.jsp,输入信息得到如下界面

struts2框架(五) 数据校验,数据回显,模型驱动,防止表单重复提交_第1张图片

连续多次点击"submit"按钮,查看效果

struts2框架(五) 数据校验,数据回显,模型驱动,防止表单重复提交_第2张图片

可以看到,token拦截器的设置生效了,他阻止了表单的重复提交,并给出了错误提示
这次我们只点击一次提交(请重新输入URL,或后退到输入页面后刷新一下,这是因为token的标示在提交一次后已被修改,不刷新标示符是不可能与服务器存留的标示符一致的)

struts2框架(五) 数据校验,数据回显,模型驱动,防止表单重复提交_第3张图片

可以看到,表单被正确的处理了。

你可能感兴趣的:(struts2框架(五) 数据校验,数据回显,模型驱动,防止表单重复提交)