天天看點

HTML5 離線緩存manifest淺析

最近公司項目開發app内嵌入H5應用,由于公司網絡不佳,導緻開發的H5應用首頁加載時快時慢,體驗效果不佳,和原生app相比感覺差別很大。以前學習了解H5的時候對H5的緩存有點印象,故就有了把首頁緩存在用戶端本地的想法,這樣可以保證首頁、js-lib、圖檔的快速加載。這才有了這篇基礎文章。

1、簡介

W3C官方對manifest的介紹是HTML5 引入了應用程式緩存,這意味着 web 應用可進行緩存,并可在沒有網際網路連接配接時進行通路。

應用程式緩存為應用帶來三個優勢:

  • 離線浏覽 - 使用者可在應用離線時使用它們
  • 速度 - 已緩存資源加載得更快
  • 減少伺服器負載 - 浏覽器将隻從伺服器下載下傳更新過或更改過的資源。

在使用過程中我總結了幾個缺點:

  • manifest中cache部分不能使用通配符,如果緩存頁引入大量JS,圖檔,寫起來比較麻煩,雖然可以使用grunt-manifest自動生成
  • 如果頁面是通過ajax請求拼接出來的頁面中含有圖檔,這些圖檔又是從web上傳的,這些圖檔也必須寫入緩存檔案,否則下次就讀不出來了。大大降低了實用性

2、mainifest執行個體

HTML5 離線緩存manifest淺析

html中寫法

<!doctype html>
<html manifest="index.manifest">
<head>
<meta charset="utf-8">
<title>應用中心</title>
           

注意: 每個指定了 manifest 的頁面在使用者對其通路時都會被緩存。如果未指定 manifest 屬性,則頁面不會被緩存(除非在 manifest 檔案中直接指定了該頁面)。

manifest 檔案可分為三個部分:

  • CACHE MANIFEST - 在此标題下列出的檔案将在首次下載下傳後進行緩存
  • NETWORK - 在此标題下列出的檔案需要與伺服器的連接配接,且不會被緩存
  • FALLBACK - 在此标題下列出的檔案規定當頁面無法通路時的回退頁面(比如 404 頁面)
HTML5 離線緩存manifest淺析

緩存是否成功加載可以用Chrome打開這個頁面就可以在控制台中找到這個manifest的工作資訊:

HTML5 離線緩存manifest淺析

再次請求此頁面的時候:

HTML5 離線緩存manifest淺析

如果有報錯的話,會有提示:

HTML5 離線緩存manifest淺析

3、緩存更新

一旦應用被緩存,它就會保持緩存直到發生下列情況:

  • 使用者清空浏覽器緩存
  • manifest 檔案被修改
  • 由程式來更新應用緩存

開發者也可以使用 window.applicationCache 的接口更新緩存

擷取緩存狀态:window.applicationCache.status 為了通過程式設計更新cache,首先調用 applicationCache.update()。這将會試圖更新使用者的 cache( 要求manifest檔案已經改變)。最後,當 applicationCache.status 處于 UPDATEREADY 狀态時, 調用applicationCache.swapCache(),舊的cache就會被置換成新的。

4、自動化工具

manifest中 cache部分不能使用通配符 ,如果緩存頁引入大量JS,圖檔,寫起來比較麻煩,這時候就可以使用自動化工具grunt-manifest。 grunt-manifest GitHub位址

grunt搭建檢視:【前端福利】用grunt搭建自動化的web前端開發環境-完整教程 安裝grunt-manifest

npm install grunt-manifest --save-dev 載入:

grunt.loadNpmTasks('grunt-manifest');
           

執行個體:

grunt.initConfig({
  pkg: grunt.file.readJSON('package.json'),
  manifest: {
    generate: {
      options: {
        basePath: '../',
        cache: ['js/app.js', 'css/style.css'],
        network: ['http://*', 'https://*'],
        fallback: ['/ /offline.html'],
        exclude: ['js/jquery.min.js'],
        preferOnline: true,
        headcomment: " <%= pkg.name %> v<%= pkg.version %>",
        verbose: true,
        timestamp: true,
        hash: true,
        master: ['index.html'],
        process: function(path) {
          return path.substring('build/'.length);
        }
      },
      src: [
      	'build/some_files/*.html',
    	  'build/js/*.min.js',
    	  'build/css/*.css'
      ],
      dest: 'manifest.appcache'
    }
  }
});
           

其中options定義生成manifest的一些自定義參數,src是要生成的檔案,dest是輸出檔案。

options下有很多參數,主要參數如下:

basePath 設定出入檔案的根目錄

cache 手動添加緩存檔案

network 手動添加網絡檔案

fallback 手動添加後備檔案

exclude 設定不添加到cache的檔案

verbose 是否添加版權資訊

timestamp是否添加時間戳

5、注意事項

  • 浏覽器對緩存資料的容量限制可能不太一樣(某些浏覽器設定的限制是每個站點 5MB)。
  • 如果manifest檔案,或者内部列舉的某一個檔案不能正常下載下傳,整個更新過程都将失敗,浏覽器繼續全部使用老的緩存。
  • 引用manifest的html必須與manifest檔案同源,在同一個域下。
  • FALLBACK中的資源必須和manifest檔案同源。
  • 當一個資源被緩存後,該浏覽器直接請求這個絕對路徑也會通路緩存中的資源。
  • 站點中的其他頁面即使沒有設定manifest屬性,請求的資源如果在緩存中也從緩存中通路。
  • 當manifest檔案發生改變時,資源請求本身也會觸發更新。
  • 系統會自動緩存引用清單檔案的 HTML 檔案
  • manifest檔案中CACHE則與NETWORK,FALLBACK的位置順序沒有關系,如果是隐式聲明需要在最前面

繼續閱讀