mvc 防止客服端多次提交

但凡web开发中都会有户多次点击了提交按钮导致多次提交的情况,一般的集中做法

1、通过js在用户点击的时候将按钮disabled掉,但是这样并不是很可靠(我就可以跳过这个,用一个for循环 我直接自己post数据过去)

2、在生成客服端html的时候存放一个隐藏的input,input里面存放一个随机生成的值(一般为guid),服务器端会将此值保存,等用户提交的时候 判断提交过来的guid是否匹配(这种方法相对第一种安全性更高,但是如果是全静态的页面的话就不满足了,于是自己琢磨了第3中解决方案)

3、通过自定义ActionFilter来实现,代码如下

public class PreventMutipleSubmitAttribute:ActionFilterAttribute
    {
        private int delaySecond =5;
        /// <summary>
        /// 重复提交的时间秒(两次间隔不大于改值时视为重复提交),默认为5s
        /// </summary>
        public int DelaySecond 
        {
            get { return delaySecond; }
            set { delaySecond = value; }
        }

        public override void OnActionExecuting(ActionExecutingContext filterContext)
        {
            var request=filterContext.RequestContext.HttpContext.Request;
            var cache = filterContext.RequestContext.HttpContext.Cache;

            var paramModel = filterContext.ActionParameters;
            paramModel.Add("userID", ApplicationPrincipal.CurrentPrincipal.UserID);
            paramModel.Add("userIP", request.UserHostAddress);
            var clientPostModel = JsonConvert.SerializeObject(paramModel);

            var md5Model = MD5.Create().ComputeHash(Encoding.ASCII.GetBytes(clientPostModel)).Select(s => s.ToString("x2"));
            var hashValue = string.Join("", md5Model);
            if (cache[hashValue] == null)
            {
                cache.Add(hashValue, "", null, DateTime.Now.AddSeconds(delaySecond), Cache.NoSlidingExpiration, CacheItemPriority.Default, null);
                base.OnActionExecuting(filterContext);
            }
            else {
                filterContext.Result = new MutipleSubmitException();
            }
        }
    }

 跟权限过滤器一样,在需要防止多次提交的地方打上这个标签就ok啦。

解释下实现的思路:主要是将用户提交过来的参数+用户IP+用户主键ID 然后得到这些值的md5,将得到的md5值存放在缓存中(只存了5秒,根据实际情况可以适当增加),当用户提交过来的时候判断缓存中是否与这个键,如果有就是重复提交的,在else里面做相应的处理就可以了,我这里的MutipleSubmitException是自定义的一个异常状态码,你也可以自己定义返回json什么的都可以,配合前端的处理就跟完美了。ok 到此,服务器端防止多次提交完毕!如有bug谢谢网友反馈...

 

郑重声明:本站内容如果来自互联网及其他传播媒体,其版权均属原媒体及文章作者所有。转载目的在于传递更多信息及用于网络分享,并不代表本站赞同其观点和对其真实性负责,也不构成任何其他建议。