It’s a well-known fact that Apple currently does not support service workers on iOS. There’s nothing much we can do about that when running our apps in the device browser on iOS, however, with Cordova/PhoneGap we have the ability to access native device features via plugins and essentially polyfill the service worker code natively.
There’s actually a plugin available now that adds service worker support to your Cordova iOS apps, called phonegap-plugin-service-worker. This plugin was originally built by the Mobile Chrome Apps team and subsequently forked by the PhoneGap team with some minor updates. It’s undergoing further change but there are some basic features available now, specifically the caching/fetching APIs.
Add the phonegap service worker plugin with the following command:
phonegap plugin add https://github.com/phonegap/phonegap-plugin-service-worker
If you’re using a recent version of the PhoneGap CLI, this plugin will automatically be saved to your config.xml. If you are running an older version you can add the
--save
to the command to ensure that it’s saved.
Open your config.xml and look to ensure you see the plugin tag added like below:
<plugin name="phonegap-plugin-service-worker" spec="https://github.com/phonegap/phonegap-plugin-service-worker" />
There are a couple of preferences that are used by the plugin and you will also need to add these into your config.xml file.
the ServiceWorker
preference - you need to set this to the filename of the Service Worker JS code to be used when the app is run on iOS
the CacheCordovaAssets
preference - a flag to tell the plugin if you want your Cordova app assets cached when it is first run. The default is true
. Set this to false
if you do not want your app assets cached.
Open config.xml and add these two preferences with your desired values (or leave off the 2nd if you do want the assets to be cached):
<preference name="ServiceWorker" value="service-worker.js" />
<preference name="CacheCordovaAssets" value="false" />
The value of the ServiceWorker preference should match the service worker file you created previously in the
www
folder. DO NOT include thewww
in the file path as it is assumed to be located there by the plugin.
If you chose to set CacheCordovaAssets
to true
above, you will need to add the CordovaAssets
cache name into your service worker code goodCaches
array or it will get deleted in our activate
event. Add the goodCaches.push('CordovaAssets')
as shown below to the top of the service-worker.js code from lesson 5.
var cacheName = 'todos_offline_cache:v1'
var goodCaches = [];
goodCaches.push(cacheName);
goodCaches.push('CordovaAssets);
Now run the PhoneGap CLI build
command on iOS so the platform is added:
phonegap build ios
Next open the <todos>.xcodeproject file created in the ~/pgday/todos-app-starter/platforms/ios/ folder in Xcode. For instance, if you named your project todos-app-starter then it will be named todos-app-starter.xcodeproject.
Run the app from Xcode and watch the console for the service worker generated statements which indicate if a file was fetched or retrieved from the cache.
Subsequent runs should show the files fetched from the cache.
If you don’t see your service worker code updating properly, you can try some of the following:
CacheCordovaAssets
set to true
this will force a new cache to be created).~/Library/CoreSimulator/Devices/.../Application/***
app bundle based on the service worker console statements and delete the folder for it. The folder bundle is typically a really long random number like shown in the screenshots.The phonegap-service-worker-plugin
writes to a SQLite data store on iOS and also actually logs the location in the Xcode console if you want to take a look at it:
You can download the DB Browser for SQLite tool to view the data cached by your app. Simply find the location of the cache data in the Xcode console and open the swcache.db
file:
Then browse the data with the DB Browser:
The cache name created by the config.xml preference when
CacheCordovaAssets
is true is calledCordovaAssets
. If you have another cache you’re managing you should see both when you open the database file.
Go ahead and try out that same service worker fetch code we tested in lesson 4 for network interception. You can uncomment the block in the service-worker.js file (don’t forget to comment out the other fetch handler. You’ll also need to uncomment the <img... logo.png>
tag from index.html
.
If you want to change the code directly in Xcode to test, make sure to update the code in the sStaging folder. If you edit your code in the root project you will just need to be sure to run
phonegap build
again to generate the new version for Xcode.