worker-in-sandboxed-iframe-by-csp-fetch-event.https.html (4746B)
1 <!DOCTYPE html> 2 <title>ServiceWorker FetchEvent issued from workers in an iframe sandboxed via CSP HTTP response header.</title> 3 <script src="/resources/testharness.js"></script> 4 <script src="/resources/testharnessreport.js"></script> 5 <script src="resources/test-helpers.sub.js"></script> 6 <body> 7 <script> 8 let lastCallbackId = 0; 9 let callbacks = {}; 10 function doTest(frame, type) { 11 return new Promise(function(resolve) { 12 var id = ++lastCallbackId; 13 callbacks[id] = resolve; 14 frame.contentWindow.postMessage({id: id, type: type}, '*'); 15 }); 16 } 17 18 // Asks the service worker for data about requests and clients seen. The 19 // worker posts a message back with |data| where: 20 // |data.requests|: the requests the worker received FetchEvents for 21 // |data.clients|: the URLs of all the worker's clients 22 // The worker clears its data after responding. 23 function getResultsFromWorker(worker) { 24 return new Promise(resolve => { 25 let channel = new MessageChannel(); 26 channel.port1.onmessage = msg => { 27 resolve(msg.data); 28 }; 29 worker.postMessage({port: channel.port2}, [channel.port2]); 30 }); 31 } 32 33 window.onmessage = function (e) { 34 message = e.data; 35 let id = message['id']; 36 let callback = callbacks[id]; 37 delete callbacks[id]; 38 callback(message['result']); 39 }; 40 41 const SCOPE = 'resources/sandboxed-iframe-fetch-event-iframe.py'; 42 const SCRIPT = 'resources/sandboxed-iframe-fetch-event-worker.js'; 43 const expected_base_url = new URL(SCOPE, location.href); 44 // A service worker controlling |SCOPE|. 45 let worker; 46 // An iframe whose response header has 47 // 'Content-Security-Policy: allow-scripts'. 48 // This should NOT be controlled by a service worker. 49 let sandboxed_frame_by_header; 50 // An iframe whose response header has 51 // 'Content-Security-Policy: allow-scripts allow-same-origin'. 52 // This should be controlled by a service worker. 53 let sandboxed_same_origin_frame_by_header; 54 55 promise_test(t => { 56 return service_worker_unregister_and_register(t, SCRIPT, SCOPE) 57 .then(function(registration) { 58 add_completion_callback(() => registration.unregister()); 59 worker = registration.installing; 60 return wait_for_state(t, registration.installing, 'activated'); 61 }); 62 }, 'Prepare a service worker.'); 63 64 promise_test(t => { 65 const iframe_full_url = expected_base_url + '?sandbox=allow-scripts&' + 66 'sandboxed-frame-by-header'; 67 return with_iframe(iframe_full_url) 68 .then(f => { 69 sandboxed_frame_by_header = f; 70 add_completion_callback(() => f.remove()); 71 return getResultsFromWorker(worker); 72 }) 73 .then(data => { 74 let requests = data.requests; 75 assert_equals(requests.length, 1, 76 'Service worker should provide the response'); 77 assert_equals(requests[0], iframe_full_url); 78 assert_false(data.clients.includes(iframe_full_url), 79 'Service worker should NOT control the sandboxed page'); 80 }); 81 }, 'Prepare an iframe sandboxed by CSP HTTP header with allow-scripts.'); 82 83 promise_test(t => { 84 const iframe_full_url = 85 expected_base_url + '?sandbox=allow-scripts%20allow-same-origin&' + 86 'sandboxed-iframe-same-origin-by-header'; 87 return with_iframe(iframe_full_url) 88 .then(f => { 89 sandboxed_same_origin_frame_by_header = f; 90 add_completion_callback(() => f.remove()); 91 return getResultsFromWorker(worker); 92 }) 93 .then(data => { 94 let requests = data.requests; 95 assert_equals(requests.length, 1); 96 assert_equals(requests[0], iframe_full_url); 97 assert_true(data.clients.includes(iframe_full_url)); 98 }) 99 }, 'Prepare an iframe sandboxed by CSP HTTP header with allow-scripts and ' + 100 'allow-same-origin.'); 101 102 promise_test(t => { 103 let frame = sandboxed_frame_by_header; 104 return doTest(frame, 'fetch-from-worker') 105 .then(result => { 106 assert_equals(result, 'done'); 107 return getResultsFromWorker(worker); 108 }) 109 .then(data => { 110 assert_equals(data.requests.length, 0, 111 'The request should NOT be handled by SW.'); 112 }); 113 }, 'Fetch request from a worker in iframe sandboxed by CSP HTTP header ' + 114 'allow-scripts flag'); 115 116 promise_test(t => { 117 let frame = sandboxed_same_origin_frame_by_header; 118 return doTest(frame, 'fetch-from-worker') 119 .then(result => { 120 assert_equals(result, 'done'); 121 return getResultsFromWorker(worker); 122 }) 123 .then(data => { 124 let requests = data.requests; 125 assert_equals(requests.length, 1, 126 'The request should be handled by SW.'); 127 assert_equals(requests[0], frame.src + '&test=fetch-from-worker'); 128 }); 129 }, 'Fetch request from a worker in iframe sandboxed by CSP HTTP header ' + 130 'with allow-scripts and allow-same-origin flag'); 131 </script> 132 </body>