最近PWAという技術ワードに注目が集まっています。PWAとはProgressive Web Appの略で、スマートフォンやタブレット向けのWebアプリケーションをより、ネイティブアプリのようにしていくためのベストプラクティスを呼びます。大きく分けて以下の技術要素になります。
- Service Worker
- 通知
- ストレージ
- HTTPS
これらの技術要素の詳細については様々なブログやメディアで語られていますので、そちらに譲りたいと思います。今回は、そのPWAにMonacaが対応したことと、PWAをどうmBaaSで活かすかについて紹介します。
PWAテンプレートではじめてみる
まずはMonacaのPWAテンプレートでプロジェクトを作成します。これはほぼ素のHTML5ですが、Service Workerがあらかじめ登録されていること、manifest.jsonが用意されていることが特徴です。
Service Workerのインストール
デフォルトの www/index.html を見ると、次のようなJavaScriptが用意されています。これがService Workerの登録処理になります。見ての通りですが、service-worker.jsを読み込んでいます。
if ('serviceWorker' in navigator) { navigator.serviceWorker.register('/service-worker.js').then(function (registration) { console.log('ServiceWorker registration successful with scope: ', registration.scope); }).catch(function (err) { console.log('ServiceWorker registration failed: ', err); }); }
Service Workerがインストールされた時に実行されるのが install イベントです。これは urlsToCache で定義されているURLのリストをキャッシュに登録する処理を行っています。
self.addEventListener('install', function (event) { event.waitUntil( caches.open(CACHE_NAME) .then(function (cache) { console.log('Opened cache'); return cache.addAll(urlsToCache); }) ); });
有効になったタイミングでは activate イベントが実行されますが、こちらは不要なキャッシュを削除しています。
self.addEventListener('activate', function (event) { var cacheWhitelist = [CACHE_NAME]; event.waitUntil( caches.keys().then(function (cacheNames) { return Promise.all( cacheNames.map(function (cacheName) { if (cacheWhitelist.indexOf(cacheName) === -1) { return caches.delete(cacheName); } }) ); }) ); });
キャッシュからの読み込み
一度目に表示した時点ではキャッシュの登録、二回目以降のアクセスではキャッシュから返却することで表示を高速化します。その際に呼ばれるのが fetch イベントになります。キャッシュにあれば、それを返却し、なければネットワークアクセスを行って結果を返却しています。
self.addEventListener('fetch', function (event) { event.respondWith( caches.match(event.request) .then(function (response) { if (response) { return response; } var fetchRequest = event.request.clone(); return fetch(fetchRequest).then( function (response) { if (!response || response.status !== 200 || response.type !== 'basic') { return response; } var responseToCache = response.clone(); caches.open(CACHE_NAME) .then(function (cache) { cache.put(event.request, responseToCache); }); return response; } ); }) ); });
これはオンライン、オフラインに関係なく行われるので、オフライン時でもコンテンツを表示できるようにしたり、オンライン時にはキャッシュを使うことで表示が高速化します。
Firebaseにデプロイする
そしてMonacaではMonaca IDEからFirebaseのホスティングサービスにデプロイができます。利用するためにはまずFirebaseへのプロジェクト登録が必要です。
また、Firebase CLI をインストールする必要があります。
npm install -g firebase-tools
インストールされたらFirebaseにログインします。
firebase login
ログインしたら適当なディレクトリで初期化します。そうするとFirebaseプロジェクトを選択しますので、デプロイ先のプロジェクトを選んでください。
firebase init
最後にAPIトークンを取得します。
firebase login:ci
認証が終わると最後にトークンが表示されます。
$ firebase login:ci Visit this URL on any device to log in: https://accounts.google.com/o/oauth2/auth?client_id=56...05 Waiting for authentication... ✔ Success! Use this token to login on a CI server: 1/RPf-FI2...GU
この 1/
ではじまる文字列をMonaca IDEのデプロイサービスとしてFirebaseを選択して、出てきたモーダルに設定します。プロジェクト名などは分かりやすいものを入力してください。
デプロイする
後はMonaca IDE上でPWA開発を行って、Firebaseでデプロイするだけです。PWAとしてビルドを行った後、Firebaseへのデプロイが可能です。もちろんZipでダウンロードして任意のサービスにデプロイもできます。
注意点
PWAはWebアプリケーションなので、幾つかの制約があります。
- Cordovaプラグインは使えません
- mBaaSのプッシュ通知は(今のところ)使えません
- MonacaアプリではService Workerは使えません
Service WorkerはHTTPSでないと使えないという制約があります。そのため、Monaca IDEのプレビューサーバではService Workerは動きますが、MonacaデバッガーやMonacaアプリとしては利用できません。また、Cordovaアプリはネイティブ(SwiftやJava、Kotlinなど)を使いますので、PWAでは利用できません。
mBaaSと組み合わせる場合にはクライアントキーの取り扱いが問題になります。ACLを正しく設定すれば問題はないのですが、それでも安全のために隠蔽しておいた方が良いでしょう。そこでお勧めなのはWebAssembly版を利用することになります。
まとめ
PWAは今後のWebアプリケーションを語る上で欠かせないキーワードになっていくと考えられます。Monacaが対応したことで、スマートフォンアプリとともにPWAにも対応したいというニーズが出てくることでしょう。mBaaSも同様で、スマートフォンアプリだけでなくPWAでもぜひ活用してください!
次はこちら
mBaaSを使ったPWAを作る