response-stream-with-broken-then.any.js (4084B)
1 // META: global=window,worker 2 // META: script=../resources/utils.js 3 4 promise_test(async () => { 5 // t.add_cleanup doesn't work when Object.prototype.then is overwritten, so 6 // these tests use add_completion_callback for cleanup instead. 7 add_completion_callback(() => delete Object.prototype.then); 8 const hello = new TextEncoder().encode('hello'); 9 const bye = new TextEncoder().encode('bye'); 10 const rs = new ReadableStream({ 11 start(controller) { 12 controller.enqueue(hello); 13 controller.close(); 14 } 15 }); 16 const resp = new Response(rs); 17 Object.prototype.then = (onFulfilled) => { 18 delete Object.prototype.then; 19 onFulfilled({done: false, value: bye}); 20 }; 21 const text = await resp.text(); 22 delete Object.prototype.then; 23 assert_equals(text, 'hello', 'The value should be "hello".'); 24 }, 'Attempt to inject {done: false, value: bye} via Object.prototype.then.'); 25 26 promise_test(async (t) => { 27 add_completion_callback(() => delete Object.prototype.then); 28 const hello = new TextEncoder().encode('hello'); 29 const rs = new ReadableStream({ 30 start(controller) { 31 controller.enqueue(hello); 32 controller.close(); 33 } 34 }); 35 const resp = new Response(rs); 36 Object.prototype.then = (onFulfilled) => { 37 delete Object.prototype.then; 38 onFulfilled({done: false, value: undefined}); 39 }; 40 const text = await resp.text(); 41 delete Object.prototype.then; 42 assert_equals(text, 'hello', 'The value should be "hello".'); 43 }, 'Attempt to inject value: undefined via Object.prototype.then.'); 44 45 promise_test(async (t) => { 46 add_completion_callback(() => delete Object.prototype.then); 47 const hello = new TextEncoder().encode('hello'); 48 const rs = new ReadableStream({ 49 start(controller) { 50 controller.enqueue(hello); 51 controller.close(); 52 } 53 }); 54 const resp = new Response(rs); 55 Object.prototype.then = (onFulfilled) => { 56 delete Object.prototype.then; 57 onFulfilled(undefined); 58 }; 59 const text = await resp.text(); 60 delete Object.prototype.then; 61 assert_equals(text, 'hello', 'The value should be "hello".'); 62 }, 'Attempt to inject undefined via Object.prototype.then.'); 63 64 promise_test(async (t) => { 65 add_completion_callback(() => delete Object.prototype.then); 66 const hello = new TextEncoder().encode('hello'); 67 const rs = new ReadableStream({ 68 start(controller) { 69 controller.enqueue(hello); 70 controller.close(); 71 } 72 }); 73 const resp = new Response(rs); 74 Object.prototype.then = (onFulfilled) => { 75 delete Object.prototype.then; 76 onFulfilled(8.2); 77 }; 78 const text = await resp.text(); 79 delete Object.prototype.then; 80 assert_equals(text, 'hello', 'The value should be "hello".'); 81 }, 'Attempt to inject 8.2 via Object.prototype.then.'); 82 83 promise_test(async () => { 84 add_completion_callback(() => delete Object.prototype.then); 85 const hello = new TextEncoder().encode('hello'); 86 const bye = new TextEncoder().encode('bye'); 87 const resp = new Response(hello); 88 Object.prototype.then = (onFulfilled) => { 89 delete Object.prototype.then; 90 onFulfilled({done: false, value: bye}); 91 }; 92 const text = await resp.text(); 93 delete Object.prototype.then; 94 assert_equals(text, 'hello', 'The value should be "hello".'); 95 }, 'intercepting arraybuffer to text conversion via Object.prototype.then ' + 96 'should not be possible'); 97 98 promise_test(async () => { 99 add_completion_callback(() => delete Object.prototype.then); 100 const u8a123 = new Uint8Array([1, 2, 3]); 101 const u8a456 = new Uint8Array([4, 5, 6]); 102 const resp = new Response(u8a123); 103 const writtenBytes = []; 104 const ws = new WritableStream({ 105 write(chunk) { 106 writtenBytes.push(...Array.from(chunk)); 107 } 108 }); 109 Object.prototype.then = (onFulfilled) => { 110 delete Object.prototype.then; 111 onFulfilled({done: false, value: u8a456}); 112 }; 113 await resp.body.pipeTo(ws); 114 delete Object.prototype.then; 115 assert_array_equals(writtenBytes, u8a123, 'The value should be [1, 2, 3]'); 116 }, 'intercepting arraybuffer to body readable stream conversion via ' + 117 'Object.prototype.then should not be possible');