浏览器存储全解析:从Cookie到IndexedDB,前端必知的5大存储方案与面试指南

116 阅读8分钟

公众号:小博的前端笔记

核心浏览器存储方式:

  1. Cookie

    • 本质: 小型文本字符串(通常由服务器通过Set-Cookie HTTP响应头设置,也可由客户端JavaScript通过document.cookie读写)。

    • 容量: 非常小(通常每个域名下限制为4KB左右,且浏览器对单个域名下的Cookie总数也有限制,通常为20-50个)。

    • 生命周期:

      • 会话Cookie:ExpiresMax-Age属性,浏览器关闭即失效。
      • 持久Cookie:Expires(到期日期)或Max-Age(存活秒数)属性,到期后失效。
    • 作用域:

      • Domain: 指定哪些主机可以接收该Cookie(默认为设置Cookie时的域名,不包括子域名;可显式设置.example.com来包含所有子域名)。
      • Path: 指定URL路径前缀,只有匹配该路径的请求才会携带Cookie(默认为设置时的路径)。
    • 自动携带: 每次HTTP请求(包括页面、图片、API、CSS等)都会自动将匹配作用域的Cookie放在Cookie请求头中发送给服务器。 这是Cookie最显著的特点。

    • 主要用途:

      • 会话管理(Session ID):服务器用于识别用户会话状态的核心机制。
      • 用户个性化(主题、语言偏好等)。
      • 用户行为追踪(广告、分析)。
    • 安全相关属性:

      • Secure 仅通过HTTPS连接发送。

      • HttpOnly 无法通过JavaScript的document.cookie访问,防止XSS攻击窃取敏感Cookie(如Session ID)。强烈建议用于会话标识符。

      • SameSite 控制Cookie在跨站请求时是否发送。值有:

        • Strict: 仅在当前站点上下文(URL栏显示的站点)发送。
        • Lax: (现代浏览器默认)在安全的跨站请求(如导航到目标站点的GET请求)中发送,但如POST请求或<iframe>加载则不发送。平衡安全与功能。
        • None: 允许跨站发送(必须同时设置Secure)。
    • JavaScript访问: 通过document.cookie读写,操作相对繁琐(需要手动解析字符串)。

    • 面试要点:

      • 小容量,自动随请求发送。
      • HttpOnly对安全的重要性。
      • SameSite的作用(防止CSRF攻击,提升隐私)。
      • 与服务器端Session的关系(Cookie通常只存Session ID,用户状态数据在服务器)。
  2. Web Storage (Local Storage & Session Storage)

    • 本质: 浏览器提供的键值对(Key-Value)存储API(localStoragesessionStorage),操作简单。

    • 容量: 远大于Cookie,通常为5-10MB(不同浏览器不同) 。存储的是字符串。

    • 作用域: 基于协议、域名和端口(同源策略)。不同源(协议/域名/端口任一不同)完全隔离。

    • 生命周期:

      • localStorage 持久化存储。除非用户清除浏览器缓存或代码显式删除,否则数据一直存在,即使关闭浏览器或重启电脑。
      • sessionStorage 会话级存储。数据仅在当前浏览器标签页或窗口的生命周期内有效。关闭标签页/窗口即清除。刷新页面会保留,但新开标签页(即使是同源页面)或窗口会创建新的独立sessionStorage。
    • API: 非常简洁:

      // 存储
      localStorage.setItem('key', 'value'); // 或 localStorage.key = 'value';
      sessionStorage.setItem('key', 'value');
      // 读取
      const value = localStorage.getItem('key'); // 或 const value = localStorage.key;
      // 删除
      localStorage.removeItem('key');
      // 清空
      localStorage.clear();
      sessionStorage.clear();
      
    • 数据格式: 键和值都必须是字符串。存储对象需用JSON.stringify(),读取时用JSON.parse()

    • 不自动发送: 数据不会自动随HTTP请求发送到服务器。

    • 主要用途:

      • localStorage: 需要持久化的用户偏好设置(如深色模式、布局)、缓存非关键性应用状态、保存离线数据草稿。
      • sessionStorage: 存储当前标签页会话的临时数据(如表单分步骤填写时的中间状态、单页应用(SPA)的路由状态或组件间临时传递数据)。
    • 面试要点:

      • 区分localStorage(持久) 和 sessionStorage(会话/标签页级)。
      • 容量比Cookie大得多。
      • 同源策略隔离。
      • 纯客户端存储,不自动发送到服务器。
      • 只能存字符串,需手动处理对象序列化。
  3. IndexedDB

    • 本质: 浏览器内置的非关系型(NoSQL)数据库。功能强大,支持存储大量结构化数据(甚至是文件/Blob)。

    • 容量: 理论上是“无上限”的(通常占用户磁盘空间的很大一部分,如50%或更多),但浏览器会管理配额并可能提示用户。 具体限制因浏览器和存储设备而异。

    • 数据模型: 基于“对象存储”(Object Stores),类似于数据库表。数据以键值对形式存储,值可以是复杂JavaScript对象(无需序列化成字符串)、数组、文件、Blob等。支持索引进行高效查询。

    • 操作方式: 异步API(基于事件或Promise)。操作(打开数据库、创建存储、增删改查)不会阻塞主线程。

    • 事务支持: 提供事务机制保证数据操作的原子性和一致性(ACID特性)。

    • 查询能力: 支持基于键、索引的范围查询和游标遍历,功能比Web Storage强大得多。

    • 作用域: 同源策略。

    • 生命周期: 持久化存储。除非用户清除网站数据,否则数据会一直保留。

    • 主要用途:

      • 存储大量结构化客户端数据(如用户生成的文档、邮件、笔记)。
      • 离线Web应用的核心数据存储。
      • 缓存大型数据集(如图库、产品目录)以实现快速访问。
      • 存储文件或二进制数据(Blob)。
    • 面试要点:

      • 强大的客户端数据库,支持大量结构化数据和二进制数据。
      • 异步API,不阻塞主线程。
      • 支持事务和索引。
      • 持久化存储,容量大。
      • 适用于需要复杂查询或离线功能的场景。是替代已废弃的Web SQL Database的标准方案。

其他相关存储机制(了解即可):

  1. Cache API (Service Worker Cache)

    • 本质: 属于Service Worker API的一部分,主要用于缓存网络请求(Request)及其响应(Response)。
    • 用途: 实现离线应用(Progressive Web App, PWA) 、资源预加载、提升加载速度(从缓存读取而非网络)。
    • 存储内容: HTTP请求/响应对(包括HTML, CSS, JS, 图片,API响应等)。
    • 控制权: 由Service Worker脚本完全控制缓存策略(何时存、存什么、何时用、何时更新)。
    • 生命周期: 持久化存储,但可由Service Worker或用户清除缓存。
    • 容量: 浏览器管理配额(通常与其他存储如IndexedDB共享一个较大配额)。
    • 面试要点: PWA离线能力的核心,缓存网络资源。区别于存储应用数据的IndexedDB/Web Storage。
  2. Web SQL Database (已废弃 - Deprecated)

    • 本质: 曾试图提供一个基于SQL的客户端数据库(类似SQLite)。
    • 状态: W3C已废弃该规范。不再建议用于新项目。
    • 替代方案: IndexedDB 是官方推荐的标准替代方案。
    • 面试要点: 知道它存在过但已被废弃,IndexedDB是现在的主流选择。

总结对比表:

特性CookielocalStoragesessionStorageIndexedDBCache API
容量~4KB (很小)~5-10MB (较大)~5-10MB (较大)非常大 (GB级, 有配额)较大 (有配额)
生命周期会话或设置过期时间永久 (直到清除)当前标签页/窗口 (关闭即清除)永久 (直到清除)永久 (直到清除或失效策略触发)
作用域Domain/Path同源同源 + 当前标签页/窗口同源同源 (可跨Service Worker作用域)
数据格式文本字符串字符串 (需序列化对象)字符串 (需序列化对象)结构化数据、对象、文件/BlobRequest/Response 对象
访问方式文档 document.cookie / 自动HTTP头同步 API同步 API异步 API (事件/Promise)异步 API (Promise)
自动发送到服务器 (每次HTTP请求)
主要用途会话管理、小量用户设置、追踪持久化用户设置、离线数据缓存当前会话/标签页临时数据大量结构化数据、离线应用核心数据、文件缓存网络资源缓存 (PWA离线、加速)
关键特性HttpOnly, Secure, SameSite 安全属性简单键值存储标签页/窗口隔离事务、索引、查询、大容量、二进制支持Service Worker 控制缓存策略
面试强调点小、自动带、安全属性、Session ID载体持久、同源、字符串、容量适中会话级、标签页隔离、临时数据强大DB、异步、事务、大存储、离线核心PWA离线能力核心、缓存网络资源

回答建议:

  1. 结构化清晰: 按顺序介绍Cookie、Web Storage (区分local/session)、IndexedDB、再提一下Cache API和废弃的Web SQL。
  2. 突出关键区别: 重点对比容量、生命周期、作用域、是否自动发送、主要用途。
  3. 结合实际场景: 举例说明每种存储最适合什么情况(如Session ID用Cookie,用户设置用localStorage,购物车复杂数据用IndexedDB)。
  4. 强调安全性: 提到Cookie的HttpOnlySecureSameSite属性对于安全的重要性。
  5. 提及现代趋势: 说明IndexedDB是复杂客户端存储和PWA的基石,Cache API是实现离线应用的关键。
  6. 简洁准确: 使用上表中的关键词(如同源、持久化、会话级、异步、事务、配额等)。