OLD | NEW |
1 <!DOCTYPE html> | 1 <!DOCTYPE html> |
2 <title>Service Worker: Registration</title> | 2 <title>Service Worker: Registration</title> |
3 <script src="../resources/testharness.js"></script> | 3 <script src="../resources/testharness.js"></script> |
4 <script src="../resources/testharness-helpers.js"></script> | 4 <script src="../resources/testharness-helpers.js"></script> |
5 <script src="../resources/testharnessreport.js"></script> | 5 <script src="../resources/testharnessreport.js"></script> |
6 <script src="resources/test-helpers.js"></script> | 6 <script src="resources/test-helpers.js"></script> |
| 7 <script src="resources/registration-tests.js"></script> |
7 <script> | 8 <script> |
8 | 9 registration_tests((script, options) => navigator.serviceWorker.register(script,
options), true); |
9 promise_test(function(t) { | |
10 var script = 'resources/registration-worker.js'; | |
11 var scope = 'resources/registration/normal'; | |
12 return navigator.serviceWorker.register(script, {scope: scope}) | |
13 .then(function(registration) { | |
14 assert_true(registration instanceof ServiceWorkerRegistration, | |
15 'Successfully registered.'); | |
16 service_worker_unregister_and_done(t, scope); | |
17 }) | |
18 }, 'Registering normal scope'); | |
19 | |
20 promise_test(function(t) { | |
21 var script = 'resources/registration-worker.js'; | |
22 var scope = 'resources/registration/scope-with-fragment#ref'; | |
23 return navigator.serviceWorker.register(script, {scope: scope}) | |
24 .then(function(registration) { | |
25 assert_true( | |
26 registration instanceof ServiceWorkerRegistration, | |
27 'Successfully registered.'); | |
28 assert_equals( | |
29 registration.scope, | |
30 normalizeURL('resources/registration/scope-with-fragment'), | |
31 'A fragment should be removed from scope') | |
32 service_worker_unregister_and_done(t, scope); | |
33 }) | |
34 }, 'Registering scope with fragment'); | |
35 | |
36 promise_test(function(t) { | |
37 var script = 'resources/registration-worker.js'; | |
38 var scope = 'resources/'; | |
39 return navigator.serviceWorker.register(script, {scope: scope}) | |
40 .then(function(registration) { | |
41 assert_true(registration instanceof ServiceWorkerRegistration, | |
42 'Successfully registered.'); | |
43 service_worker_unregister_and_done(t, scope); | |
44 }) | |
45 }, 'Registering same scope as the script directory'); | |
46 | |
47 promise_test(function(t) { | |
48 var script = 'resources/registration-worker.js'; | |
49 var scope = 'resources'; | |
50 return assert_promise_rejects( | |
51 navigator.serviceWorker.register(script, {scope: scope}), | |
52 'SecurityError', | |
53 'Registering same scope as the script directory without the last ' + | |
54 'slash should fail with SecurityError.'); | |
55 }, 'Registering same scope as the script directory without the last slash'); | |
56 | |
57 promise_test(function(t) { | |
58 var script = 'resources/registration-worker.js'; | |
59 var scope = 'different-directory/'; | |
60 return assert_promise_rejects( | |
61 navigator.serviceWorker.register(script, {scope: scope}), | |
62 'SecurityError', | |
63 'Registration scope outside the script directory should fail ' + | |
64 'with SecurityError.'); | |
65 }, 'Registration scope outside the script directory'); | |
66 | |
67 promise_test(function(t) { | |
68 var script = 'resources/registration-worker.js'; | |
69 var scope = 'http://example.com/'; | |
70 return assert_promise_rejects( | |
71 navigator.serviceWorker.register(script, {scope: scope}), | |
72 'SecurityError', | |
73 'Registration scope outside domain should fail with SecurityError.'); | |
74 }, 'Registering scope outside domain'); | |
75 | |
76 promise_test(function(t) { | |
77 var script = 'http://example.com/worker.js'; | |
78 var scope = 'http://example.com/scope/'; | |
79 return assert_promise_rejects( | |
80 navigator.serviceWorker.register(script, {scope: scope}), | |
81 'SecurityError', | |
82 'Registration script outside domain should fail with SecurityError.'); | |
83 }, 'Registering script outside domain'); | |
84 | |
85 promise_test(function(t) { | |
86 var script = 'resources/no-such-worker.js'; | |
87 var scope = 'resources/scope/no-such-worker'; | |
88 return assert_promise_rejects( | |
89 navigator.serviceWorker.register(script, {scope: scope}), | |
90 'NetworkError', | |
91 'Registration of non-existent script should fail.'); | |
92 }, 'Registering non-existent script'); | |
93 | |
94 promise_test(function(t) { | |
95 var script = 'resources/invalid-chunked-encoding.php'; | |
96 var scope = 'resources/scope/invalid-chunked-encoding/'; | |
97 return assert_promise_rejects( | |
98 navigator.serviceWorker.register(script, {scope: scope}), | |
99 'NetworkError', | |
100 'Registration of invalid chunked encoding script should fail.'); | |
101 }, 'Registering invalid chunked encoding script'); | |
102 | |
103 promise_test(function(t) { | |
104 var script = 'resources/invalid-chunked-encoding-with-flush.php'; | |
105 var scope = 'resources/scope/invalid-chunked-encoding-with-flush/'; | |
106 return assert_promise_rejects( | |
107 navigator.serviceWorker.register(script, {scope: scope}), | |
108 'NetworkError', | |
109 'Registration of invalid chunked encoding script should fail.'); | |
110 }, 'Registering invalid chunked encoding script with flush'); | |
111 | |
112 promise_test(function(t) { | |
113 var script = 'resources/mime-type-worker.php'; | |
114 var scope = 'resources/scope/no-mime-type-worker/'; | |
115 return assert_promise_rejects( | |
116 navigator.serviceWorker.register(script, {scope: scope}), | |
117 'SecurityError', | |
118 'Registration of no MIME type script should fail.'); | |
119 }, 'Registering script with no MIME type'); | |
120 | |
121 promise_test(function(t) { | |
122 var script = 'resources/mime-type-worker.php?mime=text/plain'; | |
123 var scope = 'resources/scope/bad-mime-type-worker/'; | |
124 return assert_promise_rejects( | |
125 navigator.serviceWorker.register(script, {scope: scope}), | |
126 'SecurityError', | |
127 'Registration of plain text script should fail.'); | |
128 }, 'Registering script with bad MIME type'); | |
129 | |
130 promise_test(function(t) { | |
131 var script = 'resources/redirect.php?Redirect=' + | |
132 encodeURIComponent('/resources/registration-worker.js'); | |
133 var scope = 'resources/scope/redirect/'; | |
134 return assert_promise_rejects( | |
135 navigator.serviceWorker.register(script, {scope: scope}), | |
136 'SecurityError', | |
137 'Registration of redirected script should fail.'); | |
138 }, 'Registering redirected script'); | |
139 | |
140 promise_test(function(t) { | |
141 var script = 'resources/malformed-worker.php?parse-error'; | |
142 var scope = 'resources/scope/parse-error'; | |
143 return assert_promise_rejects( | |
144 navigator.serviceWorker.register(script, {scope: scope}), | |
145 'AbortError', | |
146 'Registration of script including parse error should fail.'); | |
147 }, 'Registering script including parse error'); | |
148 | |
149 promise_test(function(t) { | |
150 var script = 'resources/malformed-worker.php?undefined-error'; | |
151 var scope = 'resources/scope/undefined-error'; | |
152 return assert_promise_rejects( | |
153 navigator.serviceWorker.register(script, {scope: scope}), | |
154 'AbortError', | |
155 'Registration of script including undefined error should fail.'); | |
156 }, 'Registering script including undefined error'); | |
157 | |
158 promise_test(function(t) { | |
159 var script = 'resources/malformed-worker.php?uncaught-exception'; | |
160 var scope = 'resources/scope/uncaught-exception'; | |
161 return assert_promise_rejects( | |
162 navigator.serviceWorker.register(script, {scope: scope}), | |
163 'AbortError', | |
164 'Registration of script including uncaught exception should fail.'); | |
165 }, 'Registering script including uncaught exception'); | |
166 | |
167 promise_test(function(t) { | |
168 var script = 'resources/malformed-worker.php?caught-exception'; | |
169 var scope = 'resources/scope/caught-exception'; | |
170 return navigator.serviceWorker.register(script, {scope: scope}) | |
171 .then(function(registration) { | |
172 assert_true(registration instanceof ServiceWorkerRegistration, | |
173 'Successfully registered.'); | |
174 service_worker_unregister_and_done(t, scope); | |
175 }) | |
176 }, 'Registering script including caught exception'); | |
177 | |
178 promise_test(function(t) { | |
179 var script = 'resources/malformed-worker.php?import-malformed-script'; | |
180 var scope = 'resources/scope/import-malformed-script'; | |
181 return assert_promise_rejects( | |
182 navigator.serviceWorker.register(script, {scope: scope}), | |
183 'AbortError', | |
184 'Registration of script importing malformed script should fail.'); | |
185 }, 'Registering script importing malformed script'); | |
186 | |
187 promise_test(function(t) { | |
188 var script = 'resources/malformed-worker.php?import-no-such-script'; | |
189 var scope = 'resources/scope/import-no-such-script'; | |
190 return assert_promise_rejects( | |
191 navigator.serviceWorker.register(script, {scope: scope}), | |
192 'AbortError', | |
193 'Registration of script importing non-existent script should fail.'); | |
194 }, 'Registering script importing non-existent script'); | |
195 | |
196 promise_test(function(t) { | |
197 // URL-encoded full-width 'scope'. | |
198 var name = '%ef%bd%93%ef%bd%83%ef%bd%8f%ef%bd%90%ef%bd%85'; | |
199 var script = 'resources/empty-worker.js'; | |
200 var scope = 'resources/' + name + '/escaped-multibyte-character-scope'; | |
201 return navigator.serviceWorker.register(script, {scope: scope}) | |
202 .then(function(registration) { | |
203 assert_equals( | |
204 registration.scope, | |
205 normalizeURL(scope), | |
206 'URL-encoded multibyte characters should be available.'); | |
207 service_worker_unregister_and_done(t, scope); | |
208 }); | |
209 }, 'Scope including URL-encoded multibyte characters'); | |
210 | |
211 promise_test(function(t) { | |
212 // Non-URL-encoded full-width "scope". | |
213 var name = String.fromCodePoint(0xff53, 0xff43, 0xff4f, 0xff50, 0xff45); | |
214 var script = 'resources/empty-worker.js'; | |
215 var scope = 'resources/' + name + '/non-escaped-multibyte-character-scope'; | |
216 return navigator.serviceWorker.register(script, {scope: scope}) | |
217 .then(function(registration) { | |
218 assert_equals( | |
219 registration.scope, | |
220 normalizeURL(scope), | |
221 'Non-URL-encoded multibyte characters should be available.'); | |
222 service_worker_unregister_and_done(t, scope); | |
223 }); | |
224 }, 'Scope including non-escaped multibyte characters'); | |
225 | |
226 promise_test(function(t) { | |
227 var script = 'resources%2fempty-worker.js'; | |
228 var scope = 'resources/scope/encoded-slash-in-script-url'; | |
229 return assert_promise_rejects( | |
230 navigator.serviceWorker.register(script, {scope: scope}), | |
231 new TypeError, | |
232 'URL-encoded slash in the script URL should be rejected.'); | |
233 }, 'Script URL including URL-encoded slash'); | |
234 | |
235 promise_test(function(t) { | |
236 var script = 'resources%2Fempty-worker.js'; | |
237 var scope = 'resources/scope/encoded-slash-in-script-url'; | |
238 return assert_promise_rejects( | |
239 navigator.serviceWorker.register(script, {scope: scope}), | |
240 new TypeError, | |
241 'URL-encoded slash in the script URL should be rejected.'); | |
242 }, 'Script URL including uppercase URL-encoded slash'); | |
243 | |
244 promise_test(function(t) { | |
245 var script = 'resources/empty-worker.js'; | |
246 var scope = 'resources/scope%2fencoded-slash-in-scope'; | |
247 return assert_promise_rejects( | |
248 navigator.serviceWorker.register(script, {scope: scope}), | |
249 new TypeError, | |
250 'URL-encoded slash in the scope should be rejected.'); | |
251 }, 'Scope including URL-encoded slash'); | |
252 | |
253 promise_test(function(t) { | |
254 var script = 'resources%5cempty-worker.js'; | |
255 var scope = 'resources/scope/encoded-slash-in-script-url'; | |
256 return assert_promise_rejects( | |
257 navigator.serviceWorker.register(script, {scope: scope}), | |
258 new TypeError, | |
259 'URL-encoded backslash in the script URL should be rejected.'); | |
260 }, 'Script URL including URL-encoded backslash'); | |
261 | |
262 promise_test(function(t) { | |
263 var script = 'resources%5Cempty-worker.js'; | |
264 var scope = 'resources/scope/encoded-slash-in-script-url'; | |
265 return assert_promise_rejects( | |
266 navigator.serviceWorker.register(script, {scope: scope}), | |
267 new TypeError, | |
268 'URL-encoded backslash in the script URL should be rejected.'); | |
269 }, 'Script URL including uppercase URL-encoded backslash'); | |
270 | |
271 promise_test(function(t) { | |
272 var script = 'resources/empty-worker.js'; | |
273 var scope = 'resources/scope%5cencoded-slash-in-scope'; | |
274 return assert_promise_rejects( | |
275 navigator.serviceWorker.register(script, {scope: scope}), | |
276 new TypeError, | |
277 'URL-encoded backslash in the scope should be rejected.'); | |
278 }, 'Scope including URL-encoded backslash'); | |
279 | |
280 promise_test(function(t) { | |
281 var script = 'resources/././empty-worker.js'; | |
282 var scope = 'resources/scope/parent-reference-in-script-url'; | |
283 return navigator.serviceWorker.register(script, {scope: scope}) | |
284 .then(function(registration) { | |
285 assert_equals( | |
286 registration.installing.scriptURL, | |
287 normalizeURL('resources/empty-worker.js'), | |
288 'Script URL including self-reference should be normalized.'); | |
289 service_worker_unregister_and_done(t, scope); | |
290 }); | |
291 }, 'Script URL including self-reference'); | |
292 | |
293 promise_test(function(t) { | |
294 var script = 'resources/empty-worker.js'; | |
295 var scope = 'resources/././scope/self-reference-in-scope'; | |
296 return navigator.serviceWorker.register(script, {scope: scope}) | |
297 .then(function(registration) { | |
298 assert_equals( | |
299 registration.scope, | |
300 normalizeURL('resources/scope/self-reference-in-scope'), | |
301 'Scope including self-reference should be normalized.'); | |
302 service_worker_unregister_and_done(t, scope); | |
303 }); | |
304 }, 'Scope including self-reference'); | |
305 | |
306 promise_test(function(t) { | |
307 var script = 'resources/../resources/empty-worker.js'; | |
308 var scope = 'resources/scope/parent-reference-in-script-url'; | |
309 return navigator.serviceWorker.register(script, {scope: scope}) | |
310 .then(function(registration) { | |
311 assert_equals( | |
312 registration.installing.scriptURL, | |
313 normalizeURL('resources/empty-worker.js'), | |
314 'Script URL including parent-reference should be normalized.'); | |
315 service_worker_unregister_and_done(t, scope); | |
316 }); | |
317 }, 'Script URL including parent-reference'); | |
318 | |
319 promise_test(function(t) { | |
320 var script = 'resources/empty-worker.js'; | |
321 var scope = 'resources/../resources/scope/parent-reference-in-scope'; | |
322 return navigator.serviceWorker.register(script, {scope: scope}) | |
323 .then(function(registration) { | |
324 assert_equals( | |
325 registration.scope, | |
326 normalizeURL('resources/scope/parent-reference-in-scope'), | |
327 'Scope including parent-reference should be normalized.'); | |
328 service_worker_unregister_and_done(t, scope); | |
329 }); | |
330 }, 'Scope including parent-reference'); | |
331 | |
332 promise_test(function(t) { | |
333 var script = 'resources/empty-worker.js'; | |
334 var scope = 'resources/../scope/parent-reference-in-scope'; | |
335 return assert_promise_rejects( | |
336 navigator.serviceWorker.register(script, {scope: scope}), | |
337 'SecurityError', | |
338 'Scope not under the script directory should be rejected.'); | |
339 }, 'Scope including parent-reference and not under the script directory'); | |
340 | |
341 promise_test(function(t) { | |
342 var script = 'resources////empty-worker.js'; | |
343 var scope = 'resources/scope/consecutive-slashes-in-script-url'; | |
344 return assert_promise_rejects( | |
345 navigator.serviceWorker.register(script, {scope: scope}), | |
346 'SecurityError', | |
347 'Consecutive slashes in the script url should not be unified.'); | |
348 }, 'Script URL including consecutive slashes'); | |
349 | |
350 promise_test(function(t) { | |
351 var script = 'resources/empty-worker.js'; | |
352 var scope = 'resources/scope////consecutive-slashes-in-scope'; | |
353 return navigator.serviceWorker.register(script, {scope: scope}) | |
354 .then(function(registration) { | |
355 // Although consecutive slashes in the scope are not unified, the | |
356 // scope is under the script directory and registration should | |
357 // succeed. | |
358 assert_equals( | |
359 registration.scope, | |
360 normalizeURL(scope), | |
361 'Should successfully be registered.'); | |
362 service_worker_unregister_and_done(t, scope); | |
363 }) | |
364 }, 'Scope including consecutive slashes'); | |
365 | |
366 promise_test(function(t) { | |
367 var script = 'filesystem:' + normalizeURL('resources/empty-worker.js'); | |
368 var scope = 'resources/scope/filesystem-script-url'; | |
369 return assert_promise_rejects( | |
370 navigator.serviceWorker.register(script, {scope: scope}), | |
371 'SecurityError', | |
372 'Registering a script which has same-origin filesystem: URL should ' + | |
373 'fail with SecurityError.'); | |
374 }, 'Script URL is same-origin filesystem: URL'); | |
375 | |
376 promise_test(function(t) { | |
377 var script = 'resources/empty-worker.js'; | |
378 var scope = 'filesystem:' + normalizeURL('resources/scope/filesystem-scope-u
rl'); | |
379 return assert_promise_rejects( | |
380 navigator.serviceWorker.register(script, {scope: scope}), | |
381 'SecurityError', | |
382 'Registering with the scope that has same-origin filesystem: URL ' + | |
383 'should fail with SecurityError.'); | |
384 }, 'Scope URL is same-origin filesystem: URL'); | |
385 | |
386 </script> | 10 </script> |
OLD | NEW |