详解HTML5应用程序缓存Application Cache

2015年03月17日 08:43 0 点赞 0 评论 更新于 2025-11-21 17:22

什么是Application Cache

HTML5引入了应用程序缓存技术,这使得Web应用可以进行缓存,并在没有网络的情况下使用。通过创建cache manifest文件,就能轻松创建离线应用。

Application Cache的优势

  1. 离线浏览:用户在没有网络连接时仍可访问已缓存的Web应用。
  2. 提升页面载入速度:由于部分资源已被缓存,再次访问时无需重新下载,从而加快页面加载。
  3. 降低服务器压力:减少了对服务器资源的请求,降低了服务器的负载。

此外,主流浏览器均已支持Application Cache,即使浏览器不支持,也不会对程序造成影响。

离线存储技术

HTML5提出了两大离线存储技术:localStorageApplication Cache,它们各有不同的应用场景。传统的离线存储技术还有Cookie

  • localStorage:经过实践,localStorage适合存储一些非关键性的Ajax数据,起到锦上添花的作用。
  • Application Cache:主要用于存储静态资源,同样是辅助性的存储方式。
  • Cookie:只能保存一小段文本(最大4096字节),因此不能用于存储大数据。由于HTTP是无状态的,服务器为了区分请求是否来自同一客户端,需要一个标识字符串,这个任务由Cookie完成。每次请求时,这段文本都会在服务器与浏览器之间传递,以验证用户的权限。

由此可见,Application Cache的应用场景与其他缓存技术不同,其使用方式也有所差异。

Application Cache简介

使用Application Cache需要在两个方面进行操作:

  1. 服务器端:需要维护一个manifest清单。
  2. 浏览器端:只需进行简单的设置。

以下是一个示例:

<html manifest="demo.appcache">

manifest文件示例

CACHE MANIFEST
# 需要缓存的列表
CACHE:
style1.css
1.jpg
01.js
http://localhost/applicationcache/02.js
http://localhost/applicationcache/zepto.js

# 不需要缓存的
NETWORK:
4.jpg

# 访问缓存失败后,备用访问的资源,第一个是访问源,第二个是替换文件*.html /offline.html
FALLBACK:
2.jpg/3.jpg

错误处理

在使用过程中,可能会遇到如下错误:

Application Cache Error event: Manifest fetch failed (404)

该错误的原因是manifest文件需要配置正确的MIME - type,即 “text/cache - manifest”,且必须在Web服务器上进行配置,不同的服务器配置方式不同。

离线应用示例

\APPLICATIONCACHE
01.js
02.js
1.jpg
2.jpg
3.jpg
4.jpg
demo.appcache
index.html
style1.css
style2.css
web.config
zepto.js

配置好上述内容后,就可以实现离线应用。此时,即使断网,这些文件依然可以访问。

需要注意的是,如果manifest文件中不包含/index.html,浏览器会将 “applicationcache/” 进行缓存,实际上这就相当于缓存了index.html

manifest文件的结构

manifest文件可分为三个部分:

  • CACHE MANIFEST:在此标题下列出的文件将在首次下载后进行缓存。
  • NETWORK:在此标题下列出的文件需要与服务器保持连接,不会被缓存。
  • FALLBACK:在此标题下列出的文件规定了当页面无法访问时的回退页面(例如404页面)。

事件处理

HTML5定义了几个事件点,但在大多数情况下,我们无需主动使用JavaScript进行操作,完全可以依赖浏览器的默认处理机制。

尺寸限制

Application Cache的尺寸限制统一为5M。以下是一个测试示例:

Document was loaded from Application Cache with manifest http://localhost/applicationcache/demo.appcache
index.html:1 Application Cache Checking event
index.html:6 GET http://localhost/applicationcache/style2.css net::ERR_FAILED
index.html:1 Application Cache NoUpdate event
index.html:11 GET http://localhost/applicationcache/2.jpg net::ERR_FAILED
index.html:12 GET http://localhost/applicationcache/3.jpg net::ERR_FAILED

从上述示例可以看出,当两个CSS文件的大小超过5M时,style2.css就无法被缓存。这可能会导致一些问题,例如,如果A频道和B频道都维护了自己的Application Cache,当A频道的缓存使用达到峰值时,可能会导致B频道的所有缓存失效。因此,建议Application Cache用于存储公共资源,而不要存储业务资源。

一些问题

更新机制问题

首次更新manifest文件时,由于页面加载已经开始甚至完成,而缓存更新尚未完成,浏览器仍然会使用过期的资源。当Application Cache有更新时,浏览器在本次访问中不会使用新资源,而是在第二次访问时才会使用。可以在update事件中执行window.reload事件来解决这个问题:

window.applicationCache.addEventListener("updateready", function(){
window.location.reload();
});

缓存更新问题

缓存不仅仅会存储显式定义的文件,例如在上述示例中,缓存 “applicationcache/” 时会默认保存index.html作为映射数据,并且会包含demo.appcache文件。很多时候,线上文件更新后,缓存却没有更新,此时只需在manifest配置文件中进行一点修改即可触发更新。

例如,将代码从:

<html manifest="demo.appcache">

修改为:

<html manifest="demo1.appcache">

如果不更新demo.appcache,缓存将不会更新,因为index.html被缓存了,浏览器检测的仍然是原manifest清单。

页面管理问题

各个页面如果统一管理自己的manifest清单,例如a页面和b页面都配置了common.js,当a页面更新后,如果b页面的manifest不更改,b页面依旧会读取老版本的文件。这种方式有一定的合理性,但也存在资源浪费的问题,需要对公共页面进行特殊处理。

总结

从可用性和易用性来看,Application Cache是值得使用的,但它更适合用于静态资源的缓存。要真正实现离线应用,还需要付出更多的努力。

作者信息

boke

boke

共发布了 3994 篇文章