在struts1.x中防止重复提交的实现
当我们在Struts中提交表单后,可以通过会退按钮返回到原来的表单页面,进行重复性提交。这在很多情况下是不允许的。比如当注册用户的表单中,当提交成功后,回退或者按刷新按钮可以再次提交表单,这样造成数据的不一致性,因为数据已经提交。
Struts中可以利用同步令牌机制来解决重复提交表单的问题。在Struts的Action中提供了和同步令牌相关的方法
protected boolean isTokenValid(HttpServletRequest request)
此方法用来判断当前用户会话中存储的令牌值和当前请求参数的令牌值是否一致,如果不一致返回false,一致则返回true。当我们利用Action进行相应调用处理时,就是利用此方法判断令牌值是否一致来决定是否进行处理
protected void saveToken(HttpServletRequest request)
此方法创建一个新的令牌值,将其保存在当前的会话(session)范围内。如果当前的会话对象不存在,则创建会话对象
protected void resetToken(HttpServletRequest request)
此方法对当前会话范围的令牌值进行复位操作,即删除当前会话范围的令牌值
了解了以上方法后,我们就可以在我们的应用中利用这些方法防止表单的重复性提交。例如在此我们实现一个简单的数据增加操作,首先需要显示给用户一个信息录入表单,显示此录入表单页面前,需要给当前的请求分配一个同步令牌值,并存储在当前的会话范围内。并在当前的录入页面中生成一个隐藏域,令牌值作为此隐藏域的内容,当用户提交时,控制器获取隐藏域的内容,利用isValidToken方法判断此参数内容是否和会话中存储的令牌值内容匹配,如果不匹配则进行适当的错误处理
由于要在页面显示前生成此次请求的令牌值,所以通过一个额外的Action生成令牌值,并转发到录入页面。
下面是我做的一个例子:
配置文件struts-config.xml
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE struts-config PUBLIC "-//Apache Software Foundation//DTD Struts Configuration 1.3//EN" "http://struts.apache.org/dtds/struts-config_1_3.dtd">
<struts-config>
<form-beans >
<form-bean name="registerForm" type="com.struts.token.form.RegisterForm" />
</form-beans>
<global-exceptions />
<global-forwards />
<action-mappings >
<action
attribute="registerForm"
input="/register.jsp"
name="registerForm"
path="/register"
scope="request"
parameter="action"
type="com.struts.token.action.RegisterAction"
cancellable="true">
<forward name="succ" path="/registerSucc.jsp" />
<forward name="fail" path="/registerFail.jsp" />
</action>
<action
path="/produce"
scope="request"
type="com.struts.token.action.ProduceToken">
<forward name="succ" path="/register.jsp" />
</action>
</action-mappings>
<message-resources parameter="com.struts.token.ApplicationResources" />
</struts-config>
自动生成令牌机制的action:
package com.struts.token.action;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.apache.struts.action.Action;
import org.apache.struts.action.ActionForm;
import org.apache.struts.action.ActionForward;
import org.apache.struts.action.ActionMapping;
import com.struts.token.form.RegisterForm;
//作者,朱湘鄂
//完成日期:10-05-21
//目的:在用户注册之前生成一个令牌值
public class ProduceToken extends Action {
public ActionForward execute(ActionMapping mapping, ActionForm form,
HttpServletRequest request, HttpServletResponse response) {
RegisterForm registerForm = (RegisterForm) form;// TODO Auto-generated method stub
//Save a new transaction token in the user's current session,
// creating a new session if necessary.
this.saveToken(request);//生成令牌值,并且存入到当前的会话中
return mapping.findForward("succ");//转入到注册页面
}
}
将令牌机制的值与请求的值相比较的action:
/*
* Generated by MyEclipse Struts
* Template path: templates/java/JavaClass.vtl
*/
package com.struts.token.action;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.apache.struts.action.ActionForm;
import org.apache.struts.action.ActionForward;
import org.apache.struts.action.ActionMapping;
import org.apache.struts.actions.DispatchAction;
import com.struts.token.form.RegisterForm;
/**
* MyEclipse Struts//作者:朱湘鄂
* Creation date: 05-21-2010
*
* XDoclet definition:这个主要是一个处理业务逻辑的action,
* 用来将当前会话中的令牌机制值和请求中的对比
* @struts.action path="/register" name="registerForm" input="/register.jsp" scope="request" validate="true"
* @struts.action-forward name="succ" path="/rigisterSucc"
* @struts.action-forward name="fail" path="/registerFail.jsp"
*/
public class RegisterAction extends DispatchAction {
public ActionForward add(ActionMapping mapping, ActionForm form,
HttpServletRequest request, HttpServletResponse response) {
//struts机制,将注册的信息封装到了一个formBean中了
RegisterForm registerForm = (RegisterForm) form;// TODO Auto-generated method stub
String username = registerForm.getUsername();//得到用户注册的姓名值
String password = registerForm.getPassword();//得到用户注册的密码值
//这里可以对数据进行一些操作,由于主要功能是进行令牌机制的验证,所以省了...、
/*
* 判断会话中的令牌机制值域与
如果不匹配则重新生成令牌值
转发到fail(即信息录入页面重新录入)。
如果匹配则删除当前会话中的令牌值(这样,
当点回退或者刷新按钮重复提交时,因为此时令牌值已经被删除,
显然不匹配,则不进行实际的业务操作,即防止了重复提交),
完成实际的业务操作。
*/
//这里是不匹配
if(!this.isTokenValid(request)){
//再创建一个,存入到会话中
this.saveToken(request);//生成令牌机制
return mapping.findForward("fail");
//这里是匹配
}else{
this.resetToken(request);//删除令牌机
//制值
return mapping.findForward("succ");
}
}
}
注册的页面:
<%@ page language="java" pageEncoding="UTF-8"%>
<%@ taglib uri="http://struts.apache.org/tags-bean" prefix="bean"%>
<%@ taglib uri="http://struts.apache.org/tags-html" prefix="html"%>
<html>
<head>
<title>JSP for RegisterForm form</title>
</head>
<body>
<html:form action="/register?action=add">
username : <html:text property="username"/><html:errors property="username"/><br/>
password : <html:password property="password"/><html:errors property="password"/><br/>
<html:submit/><html:cancel/>
</html:form>
</body>
</html>
直接访问那个生成令牌机制的action,然后,跳转到注册的页面,然后,根据跳转页面的action,来显示相应的页面!!!
over了!
分享到:
相关推荐
2. **Action类**:在Struts1.x中,控制器由Action类实现。每个Action对应一个用户请求,处理完成后返回一个结果转发到特定的视图。 3. **配置文件**:`struts-config.xml`是Struts1.x的核心配置文件,用于定义...
而Struts1.x的令牌机制(Token)则是防止重复提交、跨页请求攻击的重要手段。在此,我们将深入探讨Struts1.x令牌的使用方法及其背后的原理。 首先,理解为何需要令牌。在Web应用中,用户可能会意外或恶意地多次点击...
通过以上步骤,Struts1.x的Token机制就能有效地防止重复提交和CSRF攻击。在实际项目中,可以根据具体需求进行适当的调整,例如增加对Ajax请求的支持,或者自定义错误处理逻辑。记住,安全是Web开发中不可忽视的一...
Struts 1.x 是一个非常经典的Java Web框架,它在早期的Web开发中占据了重要的地位。这个框架的主要目的是为了提供一种MVC(Model-View-Controller)架构,以帮助开发者更好地组织和管理Web应用程序的逻辑。批量封装...
4. **防止重复提交**:为了增加安全性,可以设置验证码一次有效,即用户输入验证码后,无论是否正确,都会立即清除session中的验证码,防止恶意用户多次尝试。 5. **优化用户体验**:验证码的设计应考虑用户体验,...
Struts 2.X是Java Web开发中非常重要的一个框架,它基于MVC(Model-View-Controller)设计模式,提供了一种结构化的、灵活的、可扩展的方式来构建应用程序。在《Struts 2.X权威指南(第3版)》第二章中,作者深入...
Struts1.x_Tags是Apache Struts框架的一个重要组成部分,它是用于构建MVC(Model-View-Controller)架构Web应用程序的标签库。Struts1.x_Tags提供了丰富的JSP标签,使得开发者能够更加方便地创建动态用户界面,提高...
5. TokenInterceptor防止表单重复提交。 34 6.使用拦截器实现权限验证 35 7.拦截器中的注解 37 8.使用PreResultListener实现回调 39 六、使用标签 40 1.基础表单标签 40 2.单选按钮和复选框: 41 3.三种方式实现下拉...
- **Struts2概述**:Struts2是一个开源的MVC框架,它结合了Struts 1.x、WebWork和其他一些框架的优点。Struts2的主要目标是简化Web应用程序的开发过程。 - **Struts2的起源**:Struts2最初由WebWork和Struts1的核心...
ActionForm对象在请求之间可以进行回话持久化,以支持表单的重复提交。 3. **Action**:这是处理业务逻辑的类,它接收ActionForm对象并执行必要的操作。Action类通过调用服务层方法完成业务处理,然后返回一个表示...
在Struts 1中,标签库是实现视图层与控制器层交互的重要工具,使得开发者可以方便地在JSP页面中处理用户输入、展示数据和控制流程。 ### 一、STRUTS1.X 工作原理 Struts 1 的工作流程主要包括以下几个步骤: 1. ...
对于需要改变URL或者避免用户重复提交的情况,我们会选择重定向。在Action类中,可以使用`ActionRedirect`或`RedirectAction`类(Struts1.3.x后期版本)来实现: ```java ActionRedirect redirect = new ...
Validator框架则是Struts 1.x中的增强功能,允许更灵活的XML配置和可重用的验证规则。 4. **Validator框架** - **ValidatorConfig**:配置文件(如struts-validator.xml或struts-config.xml)定义了验证规则和错误...
在实际应用中,Struts还提供了一种防止重复提交的机制,这在`Struts令牌防止重复提交.docx`中有所阐述。通过在请求中添加令牌,服务器可以在接收到请求时检查该令牌,如果发现重复的令牌,则拒绝处理,从而避免了因...
需要注意的是,Struts 1.x虽然经典,但在现代开发中已被Struts 2或其他更现代的框架(如Spring MVC)所取代,学习时也应关注新技术的发展。不过,了解Struts 1的基础和原理对于理解其他框架的工作方式仍有帮助。
1. **下载Struts 2**:根据教程中的提示,建议下载Struts 2.1.x版本。 2. **安装Eclipse for Java EE**:这是一款强大的IDE,适合Java Web开发。教程中提到了需要下载Eclipse for Java EE,这是为了方便进行Struts 2...
5.5 避免重复提交功能 5.6 缩略加水印图像 5.7 小结 第6章 网络硬盘 6.1 网络硬盘功能原理 6.2 网络硬盘功能具体实现——浏览磁盘和显示文件信息 6.3 网络硬盘功能具体实现——操作文件夹和文件...
- **token防止表单重复提交**:使用`<s:token>`标签可以生成一个隐藏字段,防止用户多次提交同一个表单。 通过以上内容的学习,可以全面了解Struts2.1框架的核心特性和使用方法,这对于开发者来说是非常宝贵的资源...
- 在`resources/js/upload.js`文件中添加代码,禁用表单提交按钮,防止用户重复提交。 ```javascript function disableSubmit() { var allInputs = document.forms[0].getElementsByTagName('input'); for (var...