Skip to content

Commit

Permalink
Revamp runtimeCaching.options to account for new plugins usage. (#1095)
Browse files Browse the repository at this point in the history
  • Loading branch information
jeffposnick authored Dec 1, 2017
1 parent 5dc606d commit 0342601
Show file tree
Hide file tree
Showing 6 changed files with 118 additions and 43 deletions.
10 changes: 10 additions & 0 deletions infra/testing/validator/service-worker-runtime.js
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,15 @@ const vm = require('vm');
function setupSpiesAndContext() {
const importScripts = sinon.spy();
const workbox = {
// To make testing easier, return the name of the plugin.
cacheableResponse: {
Plugin: sinon.stub().returns('workbox.cacheableResponse.Plugin'),
},
clientsClaim: sinon.spy(),
// To make testing easier, return the name of the plugin.
expiration: {
Plugin: sinon.stub().returns('workbox.expiration.Plugin'),
},
precaching: {
precacheAndRoute: sinon.spy(),
suppressWarnings: sinon.spy(),
Expand All @@ -35,6 +43,8 @@ function setupSpiesAndContext() {

const methodsToSpies = {
importScripts,
cacheableResponsePlugin: workbox.cacheableResponse.Plugin,
cacheExpirationPlugin: workbox.expiration.Plugin,
cacheFirst: workbox.strategies.cacheFirst,
clientsClaim: workbox.clientsClaim,
precacheAndRoute: workbox.precaching.precacheAndRoute,
Expand Down
2 changes: 2 additions & 0 deletions packages/workbox-build/src/lib/errors.js
Original file line number Diff line number Diff line change
Expand Up @@ -103,4 +103,6 @@ module.exports = {
'only-regexp-routes-supported': ol`Please use a regular expression object as
the urlPattern parameter. (Express-style routes are not currently
supported.)`,
'bad-runtime-caching-config': ol`An unknown configuration option was used
with runtimeCaching:`,
};
79 changes: 56 additions & 23 deletions packages/workbox-build/src/lib/runtime-caching-converter.js
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,8 @@
limitations under the License.
*/

const ol = require('common-tags').oneLine;

const errors = require('./errors');

/**
Expand All @@ -26,32 +28,63 @@ const errors = require('./errors');
*
* @private
*/
function getOptionsString(options) {
const cacheOptions = options.cache || {};
// Start with a base of a few properties that need to be renamed, as well
// as copying over all the other source properties as-is.
const effectiveOptions = Object.assign({
cacheName: cacheOptions.name,
}, options);

// Only create the cacheExpiration object if either maxEntries or
// maxAgeSeconds is set.
if (cacheOptions.maxEntries || cacheOptions.maxAgeSeconds) {
effectiveOptions.cacheExpiration =
Object.assign(effectiveOptions.cacheExpiration || {}, {
maxEntries: cacheOptions.maxEntries,
maxAgeSeconds: cacheOptions.maxAgeSeconds,
});
function getOptionsString(options = {}) {
let plugins = [];
if (options.plugins) {
plugins = options.plugins.map((plugin) => JSON.stringify(plugin));
delete options.plugins;
}

let cacheName;
if (options.cache && options.cache.name) {
cacheName = options.cache.name;
delete options.cache.name;
}

// Allow a top-level cacheName value to override the cache.name value.
if (options.cacheName) {
cacheName = options.cacheName;
delete options.cacheName;
}

let networkTimeoutSeconds;
if (options.networkTimeoutSeconds) {
networkTimeoutSeconds = options.networkTimeoutSeconds;
delete options.networkTimeoutSeconds;
}

// Everything should be copied to the corresponding new option names at this
// point, so set the old-style `cache` property to undefined so that it
// doesn't show up in the JSON output.
effectiveOptions.cache = undefined;
const pluginsMapping = {
backgroundSync: 'workbox.backgroundSync.Plugin',
broadcastCacheUpdate: 'workbox.broadcastCacheUpdate.Plugin',
cache: 'workbox.expiration.Plugin',
cacheExpiration: 'workbox.expiration.Plugin',
cacheableResponse: 'workbox.cacheableResponse.Plugin',
};

// JSON.stringify() will automatically omit any properties that are set to
// undefined values.
return JSON.stringify(effectiveOptions, null, 2);
for (const [pluginName, pluginConfig] of Object.entries(options)) {
// Ensure that we have some valid configuration to pass to Plugin().
if (Object.keys(pluginConfig).length === 0) {
continue;
}

const pluginString = pluginsMapping[pluginName];
if (!pluginString) {
throw new Error(`${errors['bad-runtime-caching-config']} ${pluginName}`);
}

plugins.push(`${pluginString}(${JSON.stringify(pluginConfig)})`);
}

if (networkTimeoutSeconds || cacheName || plugins.length > 0) {
return ol`{
${networkTimeoutSeconds ? ('networkTimeoutSeconds: ' +
JSON.stringify(networkTimeoutSeconds)) + ',' : ''}
${cacheName ? ('cacheName: ' + JSON.stringify(cacheName)) + ',' : ''}
plugins: [${plugins.join(', ')}]
}`;
} else {
return '';
}
}

module.exports = (runtimeCaching) => {
Expand Down
26 changes: 21 additions & 5 deletions test/workbox-build/node/entry-points/generate-sw-string.js
Original file line number Diff line number Diff line change
Expand Up @@ -294,7 +294,7 @@ describe(`[workbox-build] entry-points/generate-sw-string.js (End to End)`, func

const swCode = await generateSWString(options);
await validateServiceWorkerRuntime({swCode, expectedMethodCalls: {
[STRING_HANDLER]: [[{}]],
[STRING_HANDLER]: [[]],
importScripts: [[...DEFAULT_IMPORT_SCRIPTS]],
suppressWarnings: [[]],
precacheAndRoute: [[[], {}]],
Expand All @@ -312,7 +312,7 @@ describe(`[workbox-build] entry-points/generate-sw-string.js (End to End)`, func
const swCode = await generateSWString(options);

await validateServiceWorkerRuntime({swCode, expectedMethodCalls: {
[STRING_HANDLER]: [[{}]],
[STRING_HANDLER]: [[]],
importScripts: [[...DEFAULT_IMPORT_SCRIPTS]],
suppressWarnings: [[]],
precacheAndRoute: [[[], {}]],
Expand All @@ -333,7 +333,7 @@ describe(`[workbox-build] entry-points/generate-sw-string.js (End to End)`, func
const swCode = await generateSWString(options);

await validateServiceWorkerRuntime({swCode, expectedMethodCalls: {
[STRING_HANDLER]: [[{}], [{}]],
[STRING_HANDLER]: [[], []],
importScripts: [[...DEFAULT_IMPORT_SCRIPTS]],
suppressWarnings: [[]],
precacheAndRoute: [[[], {}]],
Expand Down Expand Up @@ -386,7 +386,15 @@ describe(`[workbox-build] entry-points/generate-sw-string.js (End to End)`, func
const swCode = await generateSWString(options);

await validateServiceWorkerRuntime({swCode, expectedMethodCalls: {
[STRING_HANDLER]: [[runtimeCachingOptions]],
[STRING_HANDLER]: [[{
cacheName: runtimeCachingOptions.cacheName,
plugins: runtimeCachingOptions.plugins.concat([
'workbox.expiration.Plugin',
'workbox.cacheableResponse.Plugin',
]),
}]],
cacheableResponsePlugin: [[runtimeCachingOptions.cacheableResponse]],
cacheExpirationPlugin: [[runtimeCachingOptions.cacheExpiration]],
importScripts: [[...DEFAULT_IMPORT_SCRIPTS]],
suppressWarnings: [[]],
precacheAndRoute: [[[], {}]],
Expand Down Expand Up @@ -425,7 +433,15 @@ describe(`[workbox-build] entry-points/generate-sw-string.js (End to End)`, func
const swCode = await generateSWString(options);

await validateServiceWorkerRuntime({swCode, expectedMethodCalls: {
[STRING_HANDLER]: [[firstRuntimeCachingOptions], [secondRuntimeCachingOptions]],
[STRING_HANDLER]: [[{
cacheName: firstRuntimeCachingOptions.cacheName,
plugins: ['workbox.expiration.Plugin'],
}], [{
cacheName: secondRuntimeCachingOptions.cacheName,
plugins: ['workbox.cacheableResponse.Plugin'],
}]],
cacheableResponsePlugin: [[secondRuntimeCachingOptions.cacheableResponse]],
cacheExpirationPlugin: [[firstRuntimeCachingOptions.cacheExpiration]],
importScripts: [[...DEFAULT_IMPORT_SCRIPTS]],
suppressWarnings: [[]],
precacheAndRoute: [[[], {}]],
Expand Down
12 changes: 10 additions & 2 deletions test/workbox-build/node/entry-points/generate-sw.js
Original file line number Diff line number Diff line change
Expand Up @@ -444,7 +444,7 @@ describe(`[workbox-build] entry-points/generate-sw.js (End to End)`, function()
expect(count).to.eql(6);
expect(size).to.eql(2421);
await validateServiceWorkerRuntime({swFile: swDest, expectedMethodCalls: {
[STRING_HANDLER]: [[{}]],
[STRING_HANDLER]: [[]],
importScripts: [[WORKBOX_SW_CDN_URL]],
suppressWarnings: [[]],
precacheAndRoute: [[[{
Expand Down Expand Up @@ -507,7 +507,15 @@ describe(`[workbox-build] entry-points/generate-sw.js (End to End)`, function()
expect(count).to.eql(6);
expect(size).to.eql(2421);
await validateServiceWorkerRuntime({swFile: swDest, expectedMethodCalls: {
[STRING_HANDLER]: [[firstRuntimeCachingOptions], [secondRuntimeCachingOptions]],
[STRING_HANDLER]: [[{
cacheName: firstRuntimeCachingOptions.cacheName,
plugins: ['workbox.expiration.Plugin'],
}], [{
cacheName: secondRuntimeCachingOptions.cacheName,
plugins: ['workbox.cacheableResponse.Plugin'],
}]],
cacheableResponsePlugin: [[secondRuntimeCachingOptions.cacheableResponse]],
cacheExpirationPlugin: [[firstRuntimeCachingOptions.cacheExpiration]],
importScripts: [[WORKBOX_SW_CDN_URL]],
suppressWarnings: [[]],
precacheAndRoute: [[[{
Expand Down
32 changes: 19 additions & 13 deletions test/workbox-build/node/lib/runtime-caching-converter.js
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,12 @@ function validate(runtimeCachingOptions, convertedOptions) {

const globalScope = {
workbox: {
cacheableResponse: {
Plugin: sinon.spy(),
},
expiration: {
Plugin: sinon.spy(),
},
routing: {
registerRoute: sinon.spy(),
},
Expand Down Expand Up @@ -52,28 +58,28 @@ function validate(runtimeCachingOptions, convertedOptions) {
const strategiesCall = globalScope.workbox.strategies[runtimeCachingOption.handler].firstCall;
const strategiesOptions = strategiesCall.args[0];

const expectedOptions = {};
if (runtimeCachingOption.options) {
if (runtimeCachingOption.options.networkTimeoutSeconds) {
expectedOptions.networkTimeoutSeconds = runtimeCachingOption.options.networkTimeoutSeconds;
const options = runtimeCachingOption.options;
if (options.networkTimeoutSeconds) {
expect(options.networkTimeoutSeconds)
.to.eql(strategiesOptions.networkTimeoutSeconds);
}

if (runtimeCachingOption.options.cache) {
if (runtimeCachingOption.options.cache.name) {
expectedOptions.cacheName = runtimeCachingOption.options.cache.name;
if (options.cache) {
if (options.cache.name) {
expect(strategiesOptions.cacheName).to.eql(options.cache.name);
delete options.cache.name;
}
if (runtimeCachingOption.options.cache.maxEntries || runtimeCachingOption.options.cache.maxAgeSeconds) {
expectedOptions.cacheExpiration = Object.assign({}, runtimeCachingOption.options.cache);
delete expectedOptions.cacheExpiration.name;

if (Object.keys(options.cache).length > 0) {
expect(globalScope.workbox.expiration.Plugin.calledWith(options.cache)).to.be.true;
}
}

if (runtimeCachingOption.options.cacheableResponse) {
expectedOptions.cacheableResponse = runtimeCachingOption.options.cacheableResponse;
if (options.cacheableResponse) {
expect(globalScope.workbox.cacheableResponse.Plugin.calledWith(options.cacheableResponse)).to.be.true;
}
}

expect(strategiesOptions).to.eql(expectedOptions);
});
}

Expand Down

0 comments on commit 0342601

Please sign in to comment.