最新下载
热门教程
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
如何利用 Page Lifecycle API 的 discarded 状态还原被浏览器主动回收的页面现场
时间:2026-07-18 10:55:49 编辑:袖梨 来源:一聚教程网
discarded 状态无法被 JavaScript 捕获,唯一线索是 pageshow 事件中 persisted === false 且为全新加载;可靠保存时机仅 freeze 事件和 pagehide 且 persisted === true;还原需区分冷启动与热恢复,并清除旧快照。
discarded 状态无法被 JavaScript 捕获或响应
页面进入 discarded 阶段时,浏览器已彻底终止 JS 执行环境,所有监听器、定时器、fetch 请求、甚至 beforeunload 都不会触发。这不是一个可监听的生命周期事件,而是一个「事后状态」——你只能在用户**重新打开该 Tab** 时,通过判断加载上下文来推测它曾被丢弃。
pageshow 事件里的 persisted 属性是唯一线索
当用户从任务管理器或后台切回一个被丢弃后重建的 Tab,浏览器会重新加载整个页面(即发起新 navigation),此时 pageshow 事件会触发,且 event.persisted === false —— 注意:这和 Frozen 后恢复的 persisted === true 正好相反。
关键点在于:persisted === false 不代表“没被丢弃”,而是代表“这次不是从缓存恢复”,即一次全新加载。你需要结合其他信号交叉判断:
- 检查 URL 参数是否含
?_reloaded=1或类似标记(需你主动在上一次页面卸载前写入 localStorage) - 读取
localStorage中保存的最后状态时间戳,若距当前时间 > 5 分钟,大概率已被 discard(Frozen 通常撑不过 2–3 分钟) - 检测
performance.navigation.type已废弃,改用performance.getEntriesByType('navigation')[0]?.type,值为'reload'或'navigate'均可能对应 discard 后重建
真正能保存现场的只有 freeze + pagehide(persisted=true)
想保住用户现场,不能等 discarded——它不可逆。必须在进入 frozen 前完成持久化。可靠时机只有两个:
-
freeze事件:页面即将冻结,JS 还能执行,是最后安全的保存窗口 -
pagehide事件且event.persisted === true:说明页面将被放入 bfcache,后续可能直接 resume,此时也应保存关键状态
这两个事件中,你可以安全调用 localStorage.setItem()、indexedDB 写入、或发送带 keepalive: true 的 navigator.sendBeacon() 上报快照。但注意:sendBeacon() 在 freeze 中不一定发出,优先用存储类方案。
还原逻辑必须区分「冷启动」和「热恢复」
用户回到页面时,你要立刻判断这次加载是:
- 冷启动(discard 后重建):无有效缓存、
pageshow.persisted === false、document.hasFocus() === true且无残留 DOM 状态 → 从localStorage或服务端拉取最近快照,再手动 restore 表单、滚动位置、选中项等 - 热恢复(bfcache resume):
pageshow.persisted === true→ 不要重置 DOM,只需校验并补全异步数据(如 token 过期、列表陈旧)
最容易被忽略的是:冷启动还原后,必须清除旧的 localStorage 快照,否则下次再进还会误还原;同时滚动位置恢复要用 history.scrollRestoration = 'manual' 配合 scrollTo(),避免浏览器默认行为覆盖你的逻辑。
相关文章
- 哔咔漫画免费入口网页下载-哔咔漫画免费网页下载地址 07-31
- 逆战未来狙击技巧是什么 07-31
- 风暴怕死队炸弹流玩法搭配推荐分享 07-31
- 《龙之剑觉醒》暴击和攻击力机制讲解 暴击和攻击力如何选 07-31
- 背包闯江湖北冥阴气流搭配推荐分享 07-31
- 《天天拼词王》第435关九寨沟找出23个常用字通关攻略 07-31