客户端存储
现代 web 浏览器提供了很多在用户电脑 web 客户端存放数据的方法 — 只要用户的允许 — 可以在它需要的时候被重新获得。这样能让你存留的数据长时间保存,保存站点和文档在离线情况下使用,保留你对其站点的个性化配置等等。本篇文章只解释它们工作的一些很基础的部分。
客户端存储?
在其他的 MDN 学习中我们已经讨论过 静态网站(static sites)和动态网站( dynamic sites)的区别。大多数现代的 web 站点是动态的— 它们在服务端使用各种类型的数据库来存储数据 (服务端存储), 之后通过运行服务端( server-side)代码来重新获取需要的数据,把其数据插入到静态页面的模板中,并且生成出 HTML 渲染到用户浏览上。
客户端存储以相同的原理工作,但是在使用上有一些不同。它是由 JavaScript APIs 组成的因此允许你在客户端存储数据 (比如在用户的机器上),而且可以在需要的时候重新取得需要的数据。这有很多明显的用处,比如:
- 个性化网站偏好(比如显示一个用户选择的窗口小部件,颜色主题,或者字体)。
- 保存之前的站点行为 (比如从先前的 session 中获取购物车中的内容,记住用户是否之前已经登陆过)。
- 本地化保存数据和静态资源可以使一个站点更快(至少让资源变少)的下载,甚至可以在网络失去链接的时候变得暂时可用。
- 保存 web 已经生产的文档可以在离线状态下访问。
通常客户端和服务端存储是结合在一起使用的。例如,你可以从数据库中下载一个由网络游戏或音乐播放器应用程序使用的音乐文件,将它们存储在客户端数据库中,并按需要播放它们。用户只需下载音乐文件一次——在随后的访问中,它们将从数据库中检索。
传统方法:cookies
客户端存储的概念已经存在很长一段时间了。从早期的网络时代开始,网站就使用 cookies 来存储信息,以在网站上提供个性化的用户体验。它们是网络上最早最常用的客户端存储形式。 因为在那个年代,有许多问题——无论是从技术上的还是用户体验的角度——都是困扰着 cookies 的问题。这些问题非常重要,以至于当第一次访问一个网站时,欧洲居民会收到消息,告诉他们是否会使用 cookies 来存储关于他们的数据,而这是由一项被称为欧盟 Cookie 条例的欧盟法律导致的。
由于这些原因,我们不会在本文中教你如何使用 cookie。毕竟它过时、存在各种安全问题,而且无法存储复杂数据,而且有更好的、更现代的方法可以在用户的计算机上存储种类更广泛的数据。 cookie 的唯一优势是它们得到了非常旧的浏览器的支持,所以如果您的项目需要支持已经过时的浏览器(比如 Internet Explorer 8 或更早的浏览器),cookie 可能仍然有用,但是对于大多数项目(很明显不包括本站)来说,您不需要再使用它们了。其实 cookie 也没什么好说的,document.cookie 一把梭就完事了。
新流派:Web Storage 和 IndexedDB
现代浏览器有比使用 cookies 更简单、更有效的存储客户端数据的 API。
Web Storage API 提供了一种非常简单的语法,用于存储和检索较小的、由名称和相应值组成的数据项。当您只需要存储一些简单的数据时,比如用户的名字,用户是否登录,屏幕背景使用了什么颜色等等,这是非常有用的。
IndexedDB API 为浏览器提供了一个完整的数据库系统来存储复杂的数据。这可以用于存储从完整的用户记录到甚至是复杂的数据类型,如音频或视频文件。
您将在下面了解更多关于这些 API 的信息。
未来:Cache API
一些现代浏览器支持新的 Cache API。这个 API 是为存储特定 HTTP 请求的响应文件而设计的,它对于像存储离线网站文件这样的事情非常有用,这样网站就可以在没有网络连接的情况下使用。缓存通常与 Service Worker API 组合使用,尽管不一定非要这么做。 Cache 和 Service Workers 的使用是一个高级主题,我们不会在本文中详细讨论它,尽管我们将在下面的 离线文件存储 一节中展示一个简单的例子。
存储简单数据 — web storage
Web Storage API 非常容易使用 — 你只需存储简单的 键名/键值 对数据 (限制为字符串、数字等类型) 并在需要的时候检索其值。
为每个域名分离储存
每个域都有一个单独的数据存储区 (每个单独的网址都在浏览器中加载). 你 会看到,如果你加载两个网站(例如 google.com 和 amazon.com)并尝试将某个项目存储在一个网站上,该数据项将无法从另一个网站获取。
存储复杂数据 — IndexedDB
IndexedDB API(有时简称 IDB)是可以在浏览器中访问的一个完整的数据库系统,在这里,你可以存储复杂的关系数据。其种类不限于像字符串和数字这样的简单值。你可以在一个 IndexedDB 中存储视频,图像和许多其他的内容。
但是,这确实是有代价的:使用 IndexedDB 要比 Web Storage API 复杂得多。在本节中,我们仅仅只能浅尝辄止地一提它的能力,不过我们会给你足够基础知识以帮助你开始。
离线文件存储
上面的示例已经说明了如何创建一个将大型资产存储在 IndexedDB 数据库中的应用程序,从而无需多次下载它们。这已经是对用户体验的一个很大的改进,但仍然有一件事 - 每次访问网站时仍然需要下载主要的 HTML,CSS 和 JavaScript 文件,这意味着当没有网络连接时,它将无法工作。
这就是服务工作者和密切相关的 Cache API 的用武之地。
服务工作者是一个 JavaScript 文件,简单地说,它是在浏览器访问时针对特定来源(网站或某个域的网站的一部分)进行注册的。注册后,它可以控制该来源的可用页面。它通过坐在加载的页面和网络之间以及拦截针对该来源的网络请求来实现这一点。
当它拦截一个请求时,它可以做任何你想做的事情(参见用例思路),但经典的例子是离线保存网络响应,然后提供响应请求而不是来自网络的响应。实际上,它允许您使网站完全脱机工作。
Cache API 是另一种客户端存储机制,略有不同 - 它旨在保存 HTTP 响应,因此与服务工作者一起工作得非常好。
一个 service worker 例子‘
让我们看一个例子,让你对这可能是什么样子有所了解。我们已经创建了另一个版本的视频存储示例,我们在上一节中看到了 - 这个功能完全相同,只是它还通过服务工作者将 Cache,CSS 和 JavaScript 保存在 Cache API 中,允许示例脱机运行!
注册服务工作者
首先要注意的是,在主 JavaScript 文件中放置了一些额外的代码(请参阅 index.js)。首先,我们进行特征检测测试,以查看 serviceWorker 该 Navigator 对象中是否有该成员。如果返回 true,那么我们知道至少支持服务工作者的基础知识。在这里,我们使用该 ServiceWorkerContainer.register() 方法将 sw.js 文件中包含的服务工作者注册到它所驻留的源,因此它可以控制与它或子目录相同的目录中的页面。当其承诺履行时,服务人员被视为已注册。
安装 service worker
下次访问服务工作者控制下的任何页面时(例如,重新加载示例时),将针对该页面安装服务工作者,这意味着它将开始控制它。发生这种情况时,install 会向服务工作人员发起一个事件; 您可以在服务工作者本身内编写代码来响应安装。
让我们看一下 sw.js 文件(服务工作者)中的一个例子。您将看到安装侦听器已注册 self。此 self 关键字是一种从服务工作文件内部引用服务工作者的全局范围的方法。
在 install 处理程序内部,我们使用 ExtendableEvent.waitUntil() 事件对象上可用的方法来表示浏览器不应该完成服务工作者的安装,直到其中的 promise 成功完成。
这是我们在运行中看到 Cache API 的地方。我们使用该 CacheStorage.open() 方法打开一个可以存储响应的新缓存对象(类似于 IndexedDB 对象存储)。此承诺通过 Cache 表示 video-store 缓存的对象来实现。然后,我们使用该 Cache.addAll() 方法获取一系列资产并将其响应添加到缓存中。
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论