HTML5不提供加密机制,状态安全取决于传输方式与服务端验证;敏感数据禁放URL或history.state;前端加密仅防偶然查看,真正安全需后端签发JWT令牌并HTTPS传输。

HTML5 本身不提供页面间状态传递的“加密”机制,状态传递的安全性取决于你用什么方式传、传到哪、以及是否在服务端验证。所谓“加密”,其实是对敏感数据做保护处理,而非 HTML5 自带功能。关键不是“怎么加密”,而是“哪些状态不该明文传、怎么传更安全”。
别把敏感数据塞进 URL 或 history.state
很多人用 history.pushState() 或直接拼接 URL 参数(如 ?token=xxx)传用户 ID、权限、会话标识等——这等于把钥匙贴在快递单上。
URL 会被浏览器历史记录、服务器日志、代理缓存、Referer 头泄露,state 对象虽不暴露在地址栏,但仍在内存中可被 JS 读取,且刷新即丢失,无法替代服务端会话。
- ✅ 正确做法:只传轻量、非敏感的 UI 状态,比如
{ tab: "settings", scrollTop: 1200 } - ❌ 避免传:
{ userId: "123", authKey: "abc...", role: "admin" }
用 sessionStorage / localStorage 做临时中转?先加密再存
如果必须前端暂存某些需跨页使用的数据(如表单草稿、筛选条件),且不能走后端 API,可结合 Web Crypto API 加密后再存:
- 生成一个仅当前会话有效的密钥(如用
crypto.subtle.generateKey()) - 用 AES-GCM 加密数据,连同 IV 一起存入
sessionStorage - 下个页面读取后解密(注意:密钥不可硬编码,也不该存在 localStorage)
⚠️ 注意:前端加密≠安全。只要代码可见,密钥或算法就可能被逆向。它防的是“偶然查看本地存储”,不是主动攻击者。
立即学习“前端免费学习笔记(深入)”;
真正靠谱的方式:状态交给后端管,前端只持 Token
页面跳转时,不要传状态,而是传一个短期有效的、签名过的令牌(如 JWT),由后端验证并还原真实状态:
- 从 A 页面跳 B 时,请求后端接口生成一个带过期时间、绑定用户和上下文的 JWT
- 重定向到 B 页面时带上该 token(如
/b?st=eyJhbGciOi...) - B 页面用 fetch 向后端校验 token,获取真实状态数据(服务端完成鉴权与解密)
这样既避免前端暴露逻辑,又防止篡改,还支持吊销和审计。
补充提醒:HTTPS 是一切的前提
无论用哪种方式,所有跨页状态传递都必须在 HTTPS 下进行。HTTP 明文传输 URL、Header、甚至 fetch 请求体,加密也白搭。浏览器也会对非 HTTPS 环境下的 crypto.subtle 等 API 施加限制。










