用sessionstorage防重复提交的核心是:请求前存url+方法+参数摘要的哈希值为'pending',完成后在finally中清除;仅用url会导致不同参数请求误判,且仅限单页标签页生效。

用 sessionStorage 防重复提交,核心是:在发起请求前存一个唯一标识(如接口路径+参数摘要),请求完成后立即清除;若检测到该标识已存在,就阻止二次提交。
生成并校验请求唯一标识
不能只用接口 URL,否则带不同参数的请求会被误判为重复。推荐组合:URL + 请求方法 + 序列化后的请求体(或关键参数)。例如:
- POST /api/order 创建订单 → 取
JSON.stringify({userId: 123, amount: 99.9})的哈希(如简单用hashCode函数) - GET /api/user?id=1001 → 可直接用
/api/user?id=1001(含完整查询参数) - 避免直接存原始数据(可能超 5MB 限制),用短哈希值更安全
提交前检查并写入 sessionStorage
在调用 fetch 或 axios 前执行判断:
- 计算当前请求的 key(如
key = 'submit_' + hash(url + method + bodyStr)) - 若
sessionStorage.getItem(key)存在且为'pending',直接 return 或提示“请求处理中” - 否则,
sessionStorage.setItem(key, 'pending'),再发请求
请求完成(无论成功/失败)后及时清理
必须在 finally 块里清除标识,否则会永久锁定:
- fetch 写法:
.finally(() => sessionStorage.removeItem(key)) - axios 写法:
.finally(() => sessionStorage.removeItem(key)) - 不要只放在
.then或.catch中——网络超时、服务端异常等场景下仍需释放锁
注意 sessionStorage 的作用域限制
它只对当前标签页生效,适合单页应用内的防重;但不跨标签页、不跨域名:
- 用户新开一个 tab 提交同一接口 → 不受拦截(这是合理行为,非 bug)
- 页面刷新后 sessionStorage 清空 → 自动解除锁定,符合“单次会话”预期
- 若需更强控制(如全站级防重),需配合后端幂等 token 或服务端状态记录
Java免费学习笔记:立即使用
解锁 Java 大师之旅:从入门到精通的终极指南











