OLD | NEW |
(Empty) | |
| 1 'use strict'; |
| 2 |
| 3 if (self.importScripts) { |
| 4 self.importScripts('../resources/rs-utils.js'); |
| 5 self.importScripts('/resources/testharness.js'); |
| 6 } |
| 7 |
| 8 var test1 = async_test('ReadableStream cancellation: integration test on an infi
nite stream derived from a random push source'); |
| 9 test1.step(function() { |
| 10 var randomSource = new RandomPushSource(); |
| 11 |
| 12 var cancellationFinished = false; |
| 13 var rs = new ReadableStream({ |
| 14 start: function(c) { |
| 15 randomSource.ondata = c.enqueue.bind(c); |
| 16 randomSource.onend = c.close.bind(c); |
| 17 randomSource.onerror = c.error.bind(c); |
| 18 }, |
| 19 |
| 20 pull: function() { |
| 21 randomSource.readStart(); |
| 22 }, |
| 23 |
| 24 cancel: function() { |
| 25 randomSource.readStop(); |
| 26 randomSource.onend(); |
| 27 |
| 28 return new Promise(test1.step_func(function(resolve) { |
| 29 setTimeout(test1.step_func(function() { |
| 30 cancellationFinished = true; |
| 31 resolve(); |
| 32 }), 500); |
| 33 })); |
| 34 } |
| 35 }); |
| 36 var reader = rs.getReader(); |
| 37 |
| 38 readableStreamToArray(rs, reader).then(test1.step_func(function(chunks) { |
| 39 assert_equals(cancellationFinished, false, 'it did not wait for the canc
ellation process to finish before closing'); |
| 40 assert_greater_than(chunks.length, 0, 'at least one chunk should be read
'); |
| 41 for (var i = 0; i < chunks.length; i++) { |
| 42 assert_equals(chunks[i].length, 128, 'chunk ' + i + ' should have 12
8 bytes'); |
| 43 } |
| 44 }), test1.step_func(function(e) { assert_unreached(e); })); |
| 45 |
| 46 setTimeout(test1.step_func(function() { |
| 47 reader.cancel().then(test1.step_func(function() { |
| 48 assert_equals(cancellationFinished, true, 'it returns a promise that
is fulfilled when the cancellation finishes'); |
| 49 test1.done(); |
| 50 })).catch(test1.step_func(function(e) { assert_unreached(e); })); |
| 51 }), 1000); |
| 52 }); |
| 53 |
| 54 test(function() { |
| 55 var recordedReason; |
| 56 var rs = new ReadableStream({ |
| 57 cancel: function(reason) { |
| 58 recordedReason = reason; |
| 59 } |
| 60 }); |
| 61 |
| 62 var passedReason = new Error('Sorry, it just wasn\'t meant to be.'); |
| 63 rs.cancel(passedReason); |
| 64 |
| 65 assert_equals(recordedReason, passedReason, |
| 66 'the error passed to the underlying source\'s cancel method sh
ould equal the one passed to the stream\'s cancel'); |
| 67 }, 'ReadableStream cancellation: cancel(reason) should pass through the given re
ason to the underlying source'); |
| 68 |
| 69 var test2 = async_test('ReadableStream cancellation: cancel() on a locked stream
should fail and not call the underlying source cancel'); |
| 70 test2.step(function() { |
| 71 var rs = new ReadableStream({ |
| 72 start: function(c) { |
| 73 c.enqueue('a'); |
| 74 c.close(); |
| 75 }, |
| 76 cancel: function() { |
| 77 assert_unreached('underlying source cancel() should not have been ca
lled'); |
| 78 } |
| 79 }); |
| 80 |
| 81 var reader = rs.getReader(); |
| 82 |
| 83 rs.cancel().catch(test2.step_func(function(e) { |
| 84 assert_throws(new TypeError(), e, 'cancel() should be rejected with a Ty
peError') |
| 85 })); |
| 86 |
| 87 reader.read().then(test2.step_func(function(result) { |
| 88 assert_object_equals(result, { value: 'a', done: false }, 'read() should
still work after the attempted cancel'); |
| 89 })); |
| 90 |
| 91 reader.closed.then(test2.step_func(function() { |
| 92 test2.done('closed should fulfill without underlying source cancel ever
being called'); |
| 93 })); |
| 94 }); |
| 95 |
| 96 var test3 = async_test('ReadableStream cancellation: should fulfill promise when
cancel callback went fine'); |
| 97 test3.step(function() |
| 98 { |
| 99 var cancelReceived = false; |
| 100 var cancelReason = new Error('I am tired of this stream, I prefer to cancel
it'); |
| 101 var rs = new ReadableStream({ |
| 102 cancel: function(reason) { |
| 103 cancelReceived = true; |
| 104 assert_equals(reason, cancelReason, 'cancellation reason given to th
e underlying source should be equal to the one passed'); |
| 105 } |
| 106 }); |
| 107 |
| 108 rs.cancel(cancelReason).then( |
| 109 test3.step_func(function() { |
| 110 assert_true(cancelReceived); |
| 111 test3.done('stream was successfully cancelled'); |
| 112 }), |
| 113 test3.step_func(function(e) { |
| 114 assert_unreached("received error " + e) |
| 115 })); |
| 116 }); |
| 117 |
| 118 var test4 = async_test('ReadableStream cancellation: returning a value from the
underlying source\'s cancel should not affect the fulfillment value of the promi
se returned by the stream\'s cancel'); |
| 119 test4.step(function() { |
| 120 var rs = new ReadableStream({ |
| 121 cancel: function(reason) { |
| 122 return 'Hello'; |
| 123 } |
| 124 }); |
| 125 |
| 126 rs.cancel().then(test4.step_func(function(v) { |
| 127 assert_equals(v, undefined, 'cancel() return value should be fulfilled w
ith undefined'); |
| 128 test4.done(); |
| 129 }), test4.step_func(function() { |
| 130 assert_unreached('cancel() return value should not be rejected'); |
| 131 })); |
| 132 }); |
| 133 |
| 134 var test5 = async_test('ReadableStream cancellation: should reject promise when
cancel callback raises an exception'); |
| 135 test5.step(function() |
| 136 { |
| 137 var thrownError = new Error('test'); |
| 138 var cancelCalled = false; |
| 139 |
| 140 var rs = new ReadableStream({ |
| 141 cancel: function() { |
| 142 cancelCalled = true; |
| 143 throw thrownError; |
| 144 } |
| 145 }); |
| 146 |
| 147 rs.cancel('test').then( |
| 148 test5.step_func(function() { assert_unreached('cancel should reject'); }
), |
| 149 test5.step_func(function(e) { |
| 150 assert_true(cancelCalled); |
| 151 assert_equals(e, thrownError); |
| 152 test5.done(); |
| 153 }) |
| 154 ); |
| 155 }); |
| 156 |
| 157 var test6 = async_test('ReadableStream cancellation: if the underlying source\'s
cancel method returns a promise, the promise returned by the stream\'s cancel s
hould fulfill when that one does (1)'); |
| 158 test6.step(function() |
| 159 { |
| 160 var cancelReason = new Error('test'); |
| 161 |
| 162 var rs = new ReadableStream({ |
| 163 cancel: function(error) { |
| 164 assert_equals(error, cancelReason); |
| 165 return new Promise(test6.step_func(function(resolve, reject) { |
| 166 setTimeout(test6.step_func(function() { |
| 167 resolve(); |
| 168 }), 500); |
| 169 })) |
| 170 } |
| 171 }) |
| 172 |
| 173 rs.cancel(cancelReason).then( |
| 174 test6.step_func(function() { |
| 175 test6.done('stream successfully cancelled'); |
| 176 }), |
| 177 test6.step_func(function(e) { |
| 178 assert_unreached("received error " + e) |
| 179 })) |
| 180 }); |
| 181 |
| 182 var test7 = async_test('ReadableStream cancellation: if the underlying source\'s
cancel method returns a promise, the promise returned by the stream\'s cancel s
hould fulfill when that one does (2)'); |
| 183 test7.step(function() { |
| 184 var resolveSourceCancelPromise; |
| 185 var sourceCancelPromiseHasFulfilled = false; |
| 186 var rs = new ReadableStream({ |
| 187 cancel: function() { |
| 188 var sourceCancelPromise = new Promise(test7.step_func(function(resol
ve, reject) { |
| 189 resolveSourceCancelPromise = resolve; |
| 190 })); |
| 191 |
| 192 sourceCancelPromise.then(test7.step_func(function() { |
| 193 sourceCancelPromiseHasFulfilled = true; |
| 194 })); |
| 195 |
| 196 return sourceCancelPromise; |
| 197 } |
| 198 }); |
| 199 |
| 200 |
| 201 rs.cancel().then( |
| 202 test7.step_func(function(value) { |
| 203 assert_true(sourceCancelPromiseHasFulfilled, 'cancel() return value
should be fulfilled only after the promise returned by the underlying source\'s
cancel'); |
| 204 assert_equals(value, undefined, 'cancel() return value should be ful
filled with undefined'); |
| 205 test7.done(); |
| 206 }), |
| 207 test7.step_func(function() { assert_unreached('cancel() return value sho
uld not be rejected'); }) |
| 208 ); |
| 209 |
| 210 setTimeout(test7.step_func(function() { |
| 211 resolveSourceCancelPromise('Hello'); |
| 212 }), 500); |
| 213 }); |
| 214 |
| 215 var test8 = async_test('ReadableStream cancellation: if the underlying source\'s
cancel method returns a promise, the promise returned by the stream\'s cancel s
hould reject when that one does'); |
| 216 test8.step(function() { |
| 217 var rejectSourceCancelPromise; |
| 218 var sourceCancelPromiseHasRejected = false; |
| 219 var rs = new ReadableStream({ |
| 220 cancel: function() { |
| 221 var sourceCancelPromise = new Promise(test8.step_func(function(resol
ve, reject) { |
| 222 rejectSourceCancelPromise = reject; |
| 223 })); |
| 224 |
| 225 sourceCancelPromise.catch(test8.step_func(function() { |
| 226 sourceCancelPromiseHasRejected = true; |
| 227 })); |
| 228 |
| 229 return sourceCancelPromise; |
| 230 } |
| 231 }); |
| 232 |
| 233 var errorInCancel = new Error('Sorry, it just wasn\'t meant to be.'); |
| 234 |
| 235 rs.cancel().then( |
| 236 test8.step_func(function() { assert_unreached('cancel() return value sho
uld not be rejected'); }), |
| 237 test8.step_func(function(r) { |
| 238 assert_true(sourceCancelPromiseHasRejected, 'cancel() return value s
hould be rejected only after the promise returned by the underlying source\'s ca
ncel'); |
| 239 assert_equals(r, errorInCancel, 'cancel() return value should be rej
ected with the underlying source\'s rejection reason'); |
| 240 test8.done(); |
| 241 }) |
| 242 ); |
| 243 |
| 244 setTimeout(test8.step_func(function() { |
| 245 rejectSourceCancelPromise(errorInCancel); |
| 246 }), 500); |
| 247 }); |
| 248 |
| 249 var test9 = async_test('ReadableStream cancellation: cancelling before start fin
ishes should prevent pull() from being called'); |
| 250 test9.step(function() { |
| 251 var rs = new ReadableStream({ |
| 252 pull: function() { |
| 253 assert_unreached('pull should not have been called'); |
| 254 } |
| 255 }); |
| 256 |
| 257 Promise.all([rs.cancel(), rs.getReader().closed]).then(test9.step_func(funct
ion() { |
| 258 test9.done('pull should never have been called'); |
| 259 })).catch(test9.step_func(function(e) { assert_reached(e); } )); |
| 260 }); |
| 261 |
| 262 done(); |
OLD | NEW |