晓晓的个人博客Logo
晓晓的个人博客
chrome.storage.session的数据清除时机是否包括休眠后重启?
AI提炼icon
提炼
本文围绕 Chrome 扩展中 chrome.storage.session 数据清除时机展开探讨。在 Chrome 扩展里,chrome.storage.session 数据会在插件被禁用、重启、更新及浏览器重启时清除,这一特性本适用于减少网络请求场景,即获取更新时效不敏感数据以降低云服务商成本。但在 Chrome 扩展 V3 版本中,因扩展后台 Service Worker 有 “休眠” 概念,作者对 “reloaded” 是否包含休眠后重启存疑,若包含则 chrome.storage.session 不适用于该场景。通过实践,作者设计了涉及 Chrome 扩展 Content 与 Service Worker 层的通信及用户操作交互流程进行验证。最终得出 chrome.storage.session 数据清除时机 “reloaded” 不包括 “休眠后的重启时机”,并展示了部分相关代码及测试交互分步解说。虽为 Chrome Extension 学习小知识点,但作者强调细节重要性。
本文于 2025-05-20 15:40 首次发布,最后修改于 2025-08-25 13:33

问题背景

The storage is cleared if the extension is disabled, reloaded or updated and when the browser restarts.

---引用自Chrome Extension开发者手册

在 Chrome Extension(下称Chrome扩展)中,不同于 chrome.storage.local 的持久性存储方式,chrome.storage.session 会在插件被禁用、重启、更新和浏览器重启时清除数据,也就是说,每次插件在回到初始状态时,chrome.storage.session 里面的数据就会被清除。

从使用场景出发,chrome.storage.session 这一清除数据的时机特性 为减少网络请求提供了便利

比如,有这样一种场景:

当用户开始使用 Chrome扩展 时,有一些对更新时效并不敏感、但需要从服务端或其他存储系统通过网络请求获得的数据,一般会在获取后被存储在 Chrome扩展侧 以供用户在使用扩展期间使用,而这些数据的更新时机只需放在这个扩展下一次启动时就可以了。

这个需求场景一般产生于:需减少网络请求来减少云服务商侧的一些带宽、请求次数的成本,即,对于一些时效不高的数据没必要多花钱。所以从理论的整体来看,chrome.storage.session 的数据清除时机特性与该场景应该是十分契合的。

而,本文命题来源于:Chrome扩展 的V3版本中,扩展后台 Service Worker 有 休眠 的概念,所以当我在 Chrome 开发者手册中看到 reloaded 字样时,我的心里就一直在打鼓:这个 reloaded 是否包括了休眠后重启时的那个 reload 呢?

如果包括的话,那么 chrome.storage.session 存储并不适用于减少成本的需求场景。

因为,一般我们的技术方案会这样设计:当用户开始使用 Chrome扩展 时,在 Service Worker 层检测xxx数据是否存在于缓存介质中,如果不存在则通过网络请求获取并存储于缓存介质中。然而,在用户使用过程中,绝大部分用户都能命中“ Chrome 扩展30秒休眠”的时机,毕竟我们不会频繁的打开 TAB 页(一般情况下,浏览一个页面需要点时间,这点时间再快也得超过30秒)。也就是说,如果这数据只能被存储30秒,以及,在下一次休眠唤醒时又需要重新请求网络的话,那么这样的缓存就失去了意义。(如果真这样,我们就要另择方案:比如使用长效缓存+编写代码自行判断缓存时间策略就行,就是麻烦点&这个方案也不在本次的讨论范围内)

所以,如果 Chrome 开发者手册中说的 “reloaded” 包括了休眠后再重启的时机,那么 “减少网络请求的这一需求在 chrome.storage.session 的使用场景中”这一逻辑就不成立

问题答案

经过实践,chrome.storage.session 的数据清除时机 reloaded”不包括“休眠后的重启时机

实践出真知

自古“实践出真知”,于是我设计了以下流程来消除我的困惑。(本文忽略 Content 与 Service Worker 的通信、休眠后自动重建长链接的代码)

设计方案说明

1. Extension底层设计

Chrome Etension通信流程图
Chrome Etension通信流程图

本次课题点涉及到 Chrome扩展 的 Content 与 Service Worker 层,通信流程说明如下:

  1. Content 层首次向 Service Worker 请求时,理论上无法获取到数据,所以走向 获取数据&缓存数据 分支;

  2. 在 Service Worker 休眠&由 Content 自动发起长链接重建后,再次向 Service Worker 请求数据时,是否能从 chrome.storage.session 中获取到数据 ”是我们本次需要验证的课题;

2. 用户操作交互设计

测试流程交互成品动图
测试流程交互成品动图

本次课题点涉及的交互有 TAB 页面与 Service Worker 后台,交互流程设计如下:

  1. 重启测试扩展后,打开或刷新一网页并打开开发者工具;

    1. 重启测试扩展是为了清除 chrome.storage.session 中的数据,以便排除以往数据的干扰;

    2. 打开或刷新网页时,扩展的 content.js 代码会被注入到网页中并执行。执行时,首先向 Service Worker 发送“初始化数据”消息,而后在当前页面插入一个可点击按钮;

    3. Service Worker 接收到消息之后,检测数据是否存在,如果不存在,则向 session 中存储数据;

  2. 在插件中打开 Service Worker 后台,看到数据存储成功后,关闭后台;

    1. 当 Service Worker 的后台被打开时,Service Worker 进入休眠期所需要的时间远远大于不打开后台时的时间此条信息没有开发者手册可以参考,完全由日常观察得出

  3. 关闭 Service Worker 后台后回到网页,静静等待插件休眠后自动重启;

    1. 本文中,自动重启的代码本文并未提供,可以自动使用 port.onDisconnect.addListener 监听函数来进行长链接重建;

    2. 长链接重建成功后输出日志,以让用户看到该重建消息后,手动点击按钮;

  4. 当网页的开发者工具中,输出了“长链接重建”消息后,点击按钮 & 向 Service Worker 请求获取数据;

    1. Service Worker 休眠时会自动断开与 Content 层的长链接,断开时,Content 层的 port 会收到 disconnect 监听消息,而我们需要做的就是在收到“断开连接”消息时又重建一次长链接;

  5. 基于4.1,当我们看到“长链接重建”消息时,不仅代表 Service Worker 曾经进入过休眠,也能让当前页面在不刷新的情况下向 Service Worker 发送长链接消息了;

  6. 此时打开 Service Worker 的后台,就可以看到“此次,数据是从获取-缓存分支中获取到的,还是直接从缓存中获取到的”的结果;

部分代码展示

本次课题点的代码主要涉及 Service Worker 读取数据Content 层二次触发获取数据 两块代码。

首先,是在 Service Worker 中编写缓存&数据获取代码:

其次,是 Content 层中的两块内容:

1. 页面初加载时,由 Content 主动向 Service Worker 请求获取数据。此时,理论上,走向的是“请求数据并向 chrome.storage.session 中塞入数据”分支;

2. 在 Content 层注入可点击的按钮,以用于扩展休眠重启后被点击&向 Service Worker 获取数据;

测试交互分步解说

看过代码后,应该对扩展中各个部分所负责的内容有了一点印象,接下来我们就着交互的分步截图与截图说明再加深一些印象。

扩展初始化时,从Service Worker获取数据结果展示
扩展初始化时,从Service Worker获取数据结果展示

上图展示了“Chrome 扩展初始化时,从 Service Worker 获取缓存数据是无法获取到的,转而走向了设置数据分支”。(该图出现在交互流程中的“刷新测试扩展后、刷新一个网页”时

等待扩展休眠、自动重建长链接后
等待扩展休眠、自动重建长链接后

上图展示的时机是:不操作浏览器的情况下,预计等待30秒左右,在开发者工具中显示“Content 层与 Service Worker 层之间的长链接被重建”的情况。

长链接之所以被重建是因为:

  • Service Worker 在进入休眠期时,会自动断开所有与 Content 层的长链接,长链接断开时,Content 层会收到监听端口被断开的消息;

  • 而我在 Content 层的执行代码中监听了断开消息,当断开时,重新建立了 Content 层与 Service Worker 层的之间的长链接。

Service Worker休眠后,能从缓存中获取到数据
Service Worker休眠后,能从缓存中获取到数据

上图展示的是:当 Content 层与 Service Worker 层之间的长链接被重建后,即 Service Worker 休眠后,再次从 Service Worker 的 chrome.storage.session 中获取到了数据;

由此,实践说明:Service Worker 休眠并重启后,chrome.storage.session 的数据并未被清除

写在最后

至此,本课题点验证过程结束。

虽然这是 Chrome Extension 学习旅途中一个极小的点,但我始终相信“细节决定成败”。

与君共勉

又或许,读到这里的你并不知道这个课题点有什么用,没事的,现在的你只需记住这个标题、记住这个网址,有需要的时候再来细细研究就好。

124个赞
喜欢就点个赞吧