| // META: timeout=long |
| // META: script=/common/utils.js |
| // META: script=beacon-common.sub.js |
| |
| 'use strict'; |
| |
| // TODO(yhirano): Check the sec-fetch-mode request header once WebKit supports |
| // the feature. |
| |
| parallelPromiseTest(async (t) => { |
| const iframe = document.createElement('iframe'); |
| document.body.appendChild(iframe); |
| t.add_cleanup(() => iframe.remove()); |
| |
| const id = token(); |
| const url = `/beacon/resources/beacon.py?cmd=store&id=${id}`; |
| assert_true(iframe.contentWindow.navigator.sendBeacon(url)); |
| iframe.remove(); |
| |
| const result = await waitForResult(id); |
| assert_equals(result.type, '(missing)', 'content-type'); |
| }, `simple case: with no payload`); |
| |
| parallelPromiseTest(async (t) => { |
| const iframe = document.createElement('iframe'); |
| document.body.appendChild(iframe); |
| t.add_cleanup(() => iframe.remove()); |
| |
| const id = token(); |
| const url = `/beacon/resources/beacon.py?cmd=store&id=${id}`; |
| assert_true(iframe.contentWindow.navigator.sendBeacon(url, null)); |
| iframe.remove(); |
| |
| const result = await waitForResult(id); |
| assert_equals(result.type, '(missing)', 'content-type'); |
| }, `simple case: with null payload`); |
| |
| for (const size of [EMPTY, SMALL, LARGE, MAX]) { |
| for (const type of [STRING, ARRAYBUFFER, FORM, BLOB]) { |
| if (size === MAX && type === FORM) { |
| // It is difficult to estimate the size of a form accurately, so we cannot |
| // test this case. |
| continue; |
| } |
| parallelPromiseTest(async (t) => { |
| const iframe = document.createElement('iframe'); |
| document.body.appendChild(iframe); |
| t.add_cleanup(() => iframe.remove()); |
| |
| const payload = makePayload(size, type); |
| const id = token(); |
| const url = `/beacon/resources/beacon.py?cmd=store&id=${id}`; |
| assert_true(iframe.contentWindow.navigator.sendBeacon(url, payload)); |
| iframe.remove(); |
| |
| const result = await waitForResult(id); |
| if (getContentType(type) === null) { |
| assert_equals(result.type, '(missing)', 'content-type'); |
| } else { |
| assert_true(result.type.includes(getContentType(type)), 'content-type'); |
| } |
| }, `simple case: type = ${type} and size = ${size}`); |
| } |
| } |
| |
| for (const type of [STRING, ARRAYBUFFER, FORM, BLOB]) { |
| parallelPromiseTest(async (t) => { |
| const iframe = document.createElement('iframe'); |
| document.body.appendChild(iframe); |
| t.add_cleanup(() => iframe.remove()); |
| |
| const payload = makePayload(TOOLARGE, type); |
| const id = token(); |
| const url = `/beacon/resources/beacon.py?cmd=store&id=${id}`; |
| assert_false(iframe.contentWindow.navigator.sendBeacon(url, payload)); |
| }, `Too large payload should be rejected: type = ${type}`); |
| } |
| |
| for (const type of [STRING, ARRAYBUFFER, BLOB]) { |
| parallelPromiseTest(async (t) => { |
| const iframe = document.createElement('iframe'); |
| document.body.appendChild(iframe); |
| t.add_cleanup(() => iframe.remove()); |
| |
| assert_true(iframe.contentWindow.navigator.sendBeacon( |
| `/beacon/resources/beacon.py?cmd=store&id=${token()}`, |
| makePayload(MAX, type))); |
| assert_true(iframe.contentWindow.navigator.sendBeacon( |
| `/beacon/resources/beacon.py?cmd=store&id=${token()}`, '')); |
| assert_false(iframe.contentWindow.navigator.sendBeacon( |
| `/beacon/resources/beacon.py?cmd=store&id=${token()}`, 'x')); |
| }, `Payload size restriction should be accumulated: type = ${type}`); |
| } |
| |
| test(() => { |
| assert_throws_js( |
| TypeError, () => navigator.sendBeacon('...', new ReadableStream())); |
| }, 'sendBeacon() with a stream does not work due to the keepalive flag being set'); |