1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
|
---
title: ExtendableEvent
slug: Web/API/ExtendableEvent
tags:
- API
- Experimental
- ExtendableEvent
- Interface
- NeedsTranslation
- Offline
- Reference
- Service Workers
- ServiceWorker
- TopicStub
- Workers
translation_of: Web/API/ExtendableEvent
---
<div>{{APIRef("Service Workers API")}}</div>
<p>The <strong><code>ExtendableEvent</code></strong> interface extends the lifetime of the <code><a href="/en-US/docs/Web/API/ServiceWorkerGlobalScope/install">install</a></code> and <code><a href="/en-US/docs/Web/API/ServiceWorkerGlobalScope/activate">activate</a></code> events dispatched on the global scope as part of the service worker lifecycle. This ensures that any functional events (like {{domxref("FetchEvent")}}) are not dispatched until it upgrades database schemas and deletes the outdated cache entries.</p>
<p>If {{domxref("ExtendableEvent.waitUntil","waitUntil()")}} is called outside of the <code>ExtendableEvent</code> handler, the browser should throw an <code>InvalidStateError</code>; note also that multiple calls will stack up, and the resulting promises will be added to the list of <a href="https://w3c.github.io/ServiceWorker/#extendableevent-extend-lifetime-promises">extend lifetime promises</a>.</p>
<div class="note">
<p><strong>Note</strong>: The behaviour described in the above paragraph was fixed in Firefox 43 (see {{bug(1180274)}}.)</p>
</div>
<p>This interface inherits from the {{domxref("Event")}} interface.</p>
<p>{{InheritanceDiagram(700, 60, 20)}}</p>
<div class="note">
<p><strong>Note</strong>: This interface is only available when the global scope is a {{domxref("ServiceWorkerGlobalScope")}}. It is not available when it is a {{domxref("Window")}}, or the scope of another kind of worker.</p>
</div>
<h2 id="Constructor">Constructor</h2>
<dl>
<dt>{{domxref("ExtendableEvent.ExtendableEvent()", "ExtendableEvent()")}}</dt>
<dd>Creates a new <code>ExtendableEvent</code> object.</dd>
</dl>
<h2 id="Properties">Properties</h2>
<p><em>Doesn't implement any specific properties, but inherits properties from its parent, {{domxref("Event")}}.</em></p>
<h2 id="Methods">Methods</h2>
<p><em>Inherits methods from its parent, </em><em>{{domxref("Event")}}</em>.</p>
<dl>
<dt>{{domxref("ExtendableEvent.waitUntil", "ExtendableEvent.waitUntil()")}}</dt>
<dd>
<p>Extends the lifetime of the event. It is intended to be called in the <code><a href="/en-US/docs/Web/API/ServiceWorkerGlobalScope/install">install</a></code> {{event("Event_handlers", "event handler")}} for the {{domxref("ServiceWorkerRegistration.installing", "installing")}} worker and on the <code><a href="/en-US/docs/Web/API/ServiceWorkerGlobalScope/activate">activate</a></code> {{event("Event_handlers", "event handler")}} for the {{domxref("ServiceWorkerRegistration.active", "active")}} worker.</p>
</dd>
</dl>
<h2 id="Examples">Examples</h2>
<p>This code snippet is from the <a href="https://github.com/GoogleChrome/samples/blob/gh-pages/service-worker/prefetch/service-worker.js">service worker prefetch sample</a> (see <a href="https://googlechrome.github.io/samples/service-worker/prefetch/">prefetch example live</a>.) The code calls {{domxref("ExtendableEvent.waitUntil()")}} in {{domxref("ServiceWorkerGlobalScope.oninstall")}}, delaying treating the {{domxref("ServiceWorkerRegistration.installing")}} worker as installed until the passed promise resolves successfully. The promise resolves when all resources have been fetched and cached, or else when any exception occurs.</p>
<p>The code snippet also shows a best practice for versioning caches used by the service worker. Though there's only one cache in this example, the same approach can be used for multiple caches. It maps a shorthand identifier for a cache to a specific, versioned cache name.</p>
<div class="note">
<p><strong>Note</strong>: In Chrome, logging statements are visible via the "Inspect" interface for the relevant service worker accessed via chrome://serviceworker-internals.</p>
</div>
<pre class="brush: js notranslate">var CACHE_VERSION = 1;
var CURRENT_CACHES = {
prefetch: 'prefetch-cache-v' + CACHE_VERSION
};
self.addEventListener('install', function(event) {
var urlsToPrefetch = [
'./static/pre_fetched.txt',
'./static/pre_fetched.html',
'https://www.chromium.org/_/rsrc/1302286216006/config/customLogo.gif'
];
console.log('Handling install event. Resources to pre-fetch:', urlsToPrefetch);
event.waitUntil(
caches.open(CURRENT_CACHES['prefetch']).then(function(cache) {
return cache.addAll(urlsToPrefetch.map(function(urlToPrefetch) {
return new Request(urlToPrefetch, {mode: 'no-cors'});
})).then(function() {
console.log('All resources have been fetched and cached.');
});
}).catch(function(error) {
console.error('Pre-fetching failed:', error);
})
);
});</pre>
<div class="note"><strong>Important</strong>: When fetching resources, it's very important to use <code>{mode: 'no-cors'}</code> if there is any chance that the resources are served off of a server that doesn't support {{glossary("CORS")}}. In this example, <a href="http://www.chromium.org">www.chromium.org</a> doesn't support CORS.</div>
<h2 id="Specifications">Specifications</h2>
<table class="standard-table">
<tbody>
<tr>
<th scope="col">Specification</th>
<th scope="col">Status</th>
<th scope="col">Comment</th>
</tr>
<tr>
<td>{{SpecName('Service Workers', '#extendableevent', 'ExtendableEvent')}}</td>
<td>{{Spec2('Service Workers')}}</td>
<td>Initial definition.</td>
</tr>
</tbody>
</table>
<h2 id="Browser_compatibility">Browser compatibility</h2>
<div>
<p>{{Compat("api.ExtendableEvent")}}</p>
</div>
<h2 id="See_also">See also</h2>
<ul>
<li><a href="/en-US/docs/Web/API/Service_Worker_API/Using_Service_Workers">Using Service Workers</a></li>
<li><a class="external external-icon" href="https://github.com/mdn/sw-test">Service workers basic code example</a></li>
<li><a class="external external-icon" href="https://jakearchibald.github.io/isserviceworkerready/">Is ServiceWorker ready?</a></li>
<li>{{jsxref("Promise")}}</li>
<li><a href="/en-US/docs/Web/API/Web_Workers_API/Using_web_workers">Using web workers</a></li>
</ul>
|