SessionStorage本身不加密且不跨页共享,仅限当前标签页生命周期;若需多页面间中转密文,须由开发者主动存取并配合Web Crypto API实现AES-GCM加密解密,密钥不得硬编码或存入localStorage。

SessionStorage 本身不加密,也不能跨页面直接共享——它只在当前标签页内有效,关闭即销毁。所以“多页面间用 sessionStorage 传递密文”这个说法需要明确前提:不是靠 sessionStorage 自动同步,而是由开发者主动在跳转前存、跳转后取,并配合前端加密逻辑完成临时密文的中转。
加密前先确认数据是否真该走前端暂存
SessionStorage 适合存**单次会话内、非敏感、临时性**的数据,比如筛选条件、表单草稿、页面滚动位置。如果涉及密码、令牌、用户身份凭证等,哪怕加密了也不建议存在前端。优先考虑后端下发短期 token 或用服务端 session 管理状态。
若确需前端暂存且必须加密,核心是:加密动作在存之前做,解密动作在取之后做,密钥绝不硬编码、不存 localStorage。
用 Web Crypto API 实现 AES-GCM 加密 + sessionStorage 中转
这是目前浏览器原生支持、安全性相对合理的做法(比 base64 或简单异或强得多):
- 在源页面生成一次性的 AES 密钥(仅当前会话有效):
crypto.subtle.generateKey("AES-GCM", true, ["encrypt", "decrypt"]) - 用该密钥 + 随机 IV 对业务数据(如 JSON 字符串)加密,得到密文和 IV
- 把密文、IV、算法标识(如
"aes-gcm")一起序列化为对象,再用JSON.stringify()转成字符串,存入sessionStorage.setItem("tempPayload", ...) - 跳转到目标页面后,从 sessionStorage 读出字符串,
JSON.parse()还原,再用相同密钥和 IV 调用crypto.subtle.decrypt()解密 - 密钥本身不存 sessionStorage,而是在内存中保持;若需跨多个子页面复用,可考虑用
crypto.subtle.exportKey()导出为 JWK 后用sessionStorage短期缓存(但要确保页面跳转链可控,且不泄露到控制台)
关键细节不能漏
很多实现失败是因为忽略了这些点:
- IV 必须每次加密都新生成,不能固定。AES-GCM 要求 IV 唯一,重复使用会严重削弱安全性
- 加密前务必将原始数据转为
Uint8Array(可用new TextEncoder().encode(str)),解密后用new TextDecoder().decode()还原字符串 - 不要用
window.btoa / atob处理中文或二进制数据——它只支持 ASCII,会导致乱码或截断。Web Crypto 返回的是 ArrayBuffer,应转为 base64url(非 base64)或 hex 存储 - sessionStorage 是同源隔离的,确保两个页面协议、域名、端口完全一致,否则读不到
- 目标页面加载时,先检查
sessionStorage.getItem("tempPayload")是否存在且非空,再执行解密,避免报错中断流程
替代思路:用 BroadcastChannel + sessionStorage 协同
如果多个标签页需要“感知”同一份临时密文(比如主页面生成密文后通知其他已打开的页面刷新状态),可以这样组合:
- 主页面加密后,把密文+IV 存 sessionStorage,同时用
BroadcastChannel广播一个轻量事件(如{type: "payload-ready", timestamp: Date.now()}) - 其他页面监听该 channel,收到后从自己的 sessionStorage 读取(前提是它们也共享同一份密钥派生逻辑,比如基于登录态 hash 派生)
- 这样避免了密文在多个标签页重复存储,又实现了轻量同步
注意 BroadcastChannel 不支持 IE,且所有页面必须同源。
前端入门到VUE实战笔记:立即使用
在学习笔记中,你将探索 前端 的入门与实战技巧!











