某个请求对应的是一个数据库的插入操作。从服务端角度来看,如何防止因为页面连续点击造成的重复提交。
1
leriou 2018-11-25 10:35:32 +08:00 1
csrf , 或者自己用事件 id 去重
|
2
utoyuri 2018-11-25 10:35:41 +08:00 5
根据 request 内容生成一个 unique key 塞到 redis,结束后删掉。接到新 request 后在 redis 里面找一下,存在就丢弃这个 request。
|
3
lihongjie0209 2018-11-25 10:37:58 +08:00
@leriou 跨站请求伪造 和 服务端有什么关系?
|
4
t6attack 2018-11-25 10:41:19 +08:00
参考眼前的页面。
<input type="hidden" value="xxxxx" name="once"> |
7
Sharuru 2018-11-25 11:02:40 +08:00 via Android
PRG
|
8
allanzhuo 2018-11-25 11:08:38 +08:00 via Android
token
|
9
jugelizi 2018-11-25 11:08:39 +08:00
就是表单 token 啊 如果不是前后端分离的话
|
10
leriou 2018-11-25 11:11:30 +08:00 1
@wleexi 其实就是你需要能识别出来相同的请求, 做幂等处理, csrf 的原理是你每次前端的表单页面生成时候提供一个唯一的 csrf_id, 发起请求的时候这个 id 会跟着一起到达后端,标记本次请求, 如果后端发现这个 id 已经处理过一次了, 就说这次请求就是没有刷新页面情况下的重复的提交
|
11
wleexi OP |
13
lihongjie0209 2018-11-25 11:21:14 +08:00
@leriou 前端保持不变的情况下 这个办法不可行, 你要改表单的逻辑
|
14
allanzhuo 2018-11-25 11:25:16 +08:00 via Android
@wleexi 我之前瞎写的,你可以参考下 https://www.cnblogs.com/laoyeye/p/9557269.html
|
20
iyangyuan 2018-11-25 12:53:12 +08:00 via iPhone
直接把 token 放 cookie 里不就行了?
|
21
checgg 2018-11-25 13:06:28 +08:00 1
这个问题的实际需求是什么?
1 防止提交两次? 这只能客户端去解决。 2 防止数据入库两次? 那么重复提交的定义是什么? 两个客户端,提交同一份数据,算重复提交吗? 如果算,设置数据库唯一索引就好,写入相同数据会失败。 如果不算,服务端没法验证。因为客户端请求都可以伪造。 |
22
dagger 2018-11-25 13:42:08 +08:00
你都说了是为了防止页面连续点击,那不去改前端的话,后端真的只能靠意念来感知了,就像前阵子那个要感知手机壳颜色一样
|
24
reself 2018-11-25 14:07:48 +08:00 via Android
@wleexi 可以把 csrf ——这个场景也可以称为 token ——放到 header 里,就不用改表单了
|
25
TangMonk 2018-11-25 14:10:50 +08:00 via Android
|
26
reself 2018-11-25 14:11:23 +08:00 via Android
@lihongjie0209 本质是 token,只是顺带具有 csrf 的功能,表单只是实现方式,放表单,放 session,放 header,放 meta 都可以
|
27
TangMonk 2018-11-25 14:11:54 +08:00 via Android
可以用类似 csrf 的 token,并且在表单在提交了后 disable 掉
|
28
TangMonk 2018-11-25 14:12:32 +08:00 via Android
可以用类似 csrf 的 token,并且在表单在提交了后把体检按钮 disable 掉
|
29
TangMonk 2018-11-25 14:13:09 +08:00 via Android
体检按钮☞提交按钮
|
30
Vegetable 2018-11-25 14:22:00 +08:00 via Android
总之就是需要一个事务 id。csrf 的 token 功能和这个需求有一定的交叉,可以使用但是不完全匹配。
重复提交你说是连续点击,那么做个限速就好了,后几秒的请求丢弃就完了,用到缓存或者 session。这种需求前端配合禁用提交按钮好一点。 |
31
paicha 2018-11-25 14:33:33 +08:00
这是业务问题。
|
32
showecho 2018-11-25 19:38:17 +08:00
通常我是改前端,点击之后马上变为 disabled,这样就无法再次提交了,后端通常也有判断的逻辑,比如评论的话看时间间隔,注册的话比如邮箱唯一等;
这应该就可以解决了吧? |
36
yc8332 2018-11-26 09:16:03 +08:00
表单 token 或者是 session 控制,还有同一个用户的提交数据 sha1 一下,缓存个几秒(这个相当于加锁)。。。
|
37
Raymon111111 2018-11-26 11:46:38 +08:00
前端让按钮只能点一下是最好的
后端防恶意请求可以用 锁+数据库查询 的方法搞定幂等 |