OLD | NEW |
1 // Copyright 2014 The Chromium Authors. All rights reserved. | 1 // Copyright 2014 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 // Tests launched by extensions/renderer/api/serial/data_sender_unittest.cc | 5 // Tests launched by extensions/renderer/api/serial/data_sender_unittest.cc |
6 | 6 |
7 var test = require('test').binding; | 7 var test = require('test').binding; |
8 var unittestBindings = require('test_environment_specific_bindings'); | 8 var unittestBindings = require('test_environment_specific_bindings'); |
9 | 9 |
10 var BUFFER_SIZE = 11; | 10 var BUFFER_SIZE = 11; |
11 var FATAL_ERROR = 2; | 11 var FATAL_ERROR = 2; |
12 | 12 |
13 function generateData(size, pattern) { | 13 function generateData(size, pattern) { |
14 if (!pattern) | 14 if (!pattern) |
15 pattern = 'a'; | 15 pattern = 'a'; |
16 var buffer = new ArrayBuffer(size); | 16 var buffer = new ArrayBuffer(size); |
17 var intView = new Int8Array(buffer); | 17 var intView = new Int8Array(buffer); |
18 for (var i = 0; i < size; i++) { | 18 for (var i = 0; i < size; i++) { |
19 intView[i] = pattern.charCodeAt(i % pattern.length); | 19 intView[i] = pattern.charCodeAt(i % pattern.length); |
20 } | 20 } |
21 return buffer; | 21 return buffer; |
22 } | 22 } |
23 | 23 |
| 24 // Returns a promise to a newly created DataSender. |
24 function createSender() { | 25 function createSender() { |
25 return Promise.all([ | 26 return Promise.all([ |
26 requireAsync('content/public/renderer/service_provider'), | 27 requireAsync('content/public/renderer/service_provider'), |
27 requireAsync('data_sender'), | 28 requireAsync('data_sender'), |
28 requireAsync('device/serial/data_stream.mojom'), | 29 requireAsync('device/serial/data_stream.mojom'), |
29 ]).then(test.callbackPass(function(modules) { | 30 ]).then(function(modules) { |
30 var serviceProvider = modules[0]; | 31 var serviceProvider = modules[0]; |
31 var dataSender = modules[1]; | 32 var dataSender = modules[1]; |
32 var dataStream = modules[2]; | 33 var dataStream = modules[2]; |
33 return new dataSender.DataSender( | 34 return new dataSender.DataSender( |
34 serviceProvider.connectToService(dataStream.DataSinkProxy.NAME_), | 35 serviceProvider.connectToService(dataStream.DataSinkProxy.NAME_), |
35 BUFFER_SIZE, | 36 BUFFER_SIZE, |
36 FATAL_ERROR); | 37 FATAL_ERROR); |
37 })); | 38 }); |
| 39 } |
| 40 |
| 41 // Returns a function that sends data to a provided DataSender |sender|, |
| 42 // checks that the send completes successfully and returns a promise that will |
| 43 // resolve to |sender|. |
| 44 function sendAndExpectSuccess(data) { |
| 45 return function(sender) { |
| 46 return sender.send(data).then(function(bytesSent) { |
| 47 test.assertEq(data.byteLength, bytesSent); |
| 48 return sender; |
| 49 }); |
| 50 }; |
| 51 } |
| 52 |
| 53 // Returns a function that sends data to a provided DataSender |sender|, |
| 54 // checks that the send fails with the expected error and expected number of |
| 55 // bytes sent, and returns a promise that will resolve to |sender|. |
| 56 function sendAndExpectError(data, expectedError, expectedBytesSent) { |
| 57 return function(sender) { |
| 58 return sender.send(data).catch(function(result) { |
| 59 test.assertEq(expectedError, result.error); |
| 60 test.assertEq(expectedBytesSent, result.bytesSent); |
| 61 return sender; |
| 62 }); |
| 63 }; |
| 64 } |
| 65 |
| 66 // Returns a function that cancels sends on the provided DataSender |sender| |
| 67 // with error |cancelReason|, returning a promise that will resolve to |sender| |
| 68 // once the cancel completes. |
| 69 function cancelSend(cancelReason) { |
| 70 return function(sender) { |
| 71 return sender.cancel(cancelReason).then(function() { |
| 72 return sender; |
| 73 }); |
| 74 }; |
| 75 } |
| 76 |
| 77 // Checks that attempting to start a send with |sender| fails. |
| 78 function sendAfterClose(sender) { |
| 79 test.assertThrows(sender.send, sender, [], 'DataSender has been closed'); |
| 80 } |
| 81 |
| 82 // Checks that the provided promises resolve in order, returning the result of |
| 83 // the first. |
| 84 function expectOrder(promises) { |
| 85 var nextIndex = 0; |
| 86 function createOrderChecker(promise, expectedIndex) { |
| 87 return promise.then(function(sender) { |
| 88 test.assertEq(nextIndex, expectedIndex); |
| 89 nextIndex++; |
| 90 return sender; |
| 91 }); |
| 92 } |
| 93 var wrappedPromises = []; |
| 94 for (var i = 0; i < promises.length; i++) { |
| 95 wrappedPromises.push(createOrderChecker(promises[i], i)); |
| 96 } |
| 97 return Promise.all(wrappedPromises).then(function(results) { |
| 98 return results[0]; |
| 99 }); |
| 100 } |
| 101 |
| 102 // Serializes and deserializes the provided DataSender |sender|, returning a |
| 103 // promise that will resolve to the newly deserialized DataSender. |
| 104 function serializeRoundTrip(sender) { |
| 105 return Promise.all([ |
| 106 sender.serialize(), |
| 107 requireAsync('data_sender'), |
| 108 ]).then(function(promises) { |
| 109 var serialized = promises[0]; |
| 110 var dataSenderModule = promises[1]; |
| 111 return dataSenderModule.DataSender.deserialize(serialized); |
| 112 }); |
| 113 } |
| 114 |
| 115 function closeSender(sender) { |
| 116 sender.close(); |
| 117 return sender; |
38 } | 118 } |
39 | 119 |
40 unittestBindings.exportTests([ | 120 unittestBindings.exportTests([ |
41 function testSend() { | 121 function testSend() { |
42 createSender().then(test.callbackPass(function(sender) { | 122 var sender = createSender(); |
43 var seen = null; | 123 expectOrder([ |
44 sender.send(generateData(1)).then(test.callbackPass(function(bytesSent) { | 124 sender.then(sendAndExpectSuccess(generateData(1))), |
45 test.assertEq(1, bytesSent); | 125 sender.then(sendAndExpectSuccess(generateData(1))), |
46 test.assertEq(null, seen); | 126 ]) |
47 seen = 'first'; | 127 .then(closeSender) |
48 })); | 128 .then(test.succeed, test.fail); |
49 sender.send(generateData(1)).then(test.callbackPass(function(bytesSent) { | |
50 sender.close(); | |
51 test.assertEq(1, bytesSent); | |
52 test.assertEq('first', seen); | |
53 seen = 'second'; | |
54 })); | |
55 })); | |
56 }, | 129 }, |
57 | 130 |
58 function testLargeSend() { | 131 function testLargeSend() { |
59 createSender().then(test.callbackPass(function(sender) { | 132 createSender() |
60 sender.send(generateData(BUFFER_SIZE * 3, '123')).then( | 133 .then(sendAndExpectSuccess(generateData(BUFFER_SIZE * 3, '123'))) |
61 test.callbackPass(function(bytesSent) { | 134 .then(closeSender) |
62 test.assertEq(BUFFER_SIZE * 3, bytesSent); | 135 .then(test.succeed, test.fail); |
63 sender.close(); | |
64 })); | |
65 })); | |
66 }, | 136 }, |
67 | 137 |
68 function testSendError() { | 138 function testSendError() { |
69 createSender().then(test.callbackPass(function(sender) { | 139 createSender() |
70 sender.send(generateData(BUFFER_SIZE * 3, 'b')).catch(test.callbackPass( | 140 .then(sendAndExpectError(generateData(BUFFER_SIZE * 3, 'b'), 1, 0)) |
71 function(e) { | 141 .then(sendAndExpectSuccess(generateData(1))) |
72 test.assertEq(1, e.error); | 142 .then(closeSender) |
73 test.assertEq(0, e.bytesSent); | 143 .then(test.succeed, test.fail); |
74 sender.send(generateData(1)).then(test.callbackPass( | |
75 function(bytesSent) { | |
76 test.assertEq(1, bytesSent); | |
77 sender.close(); | |
78 })); | |
79 })); | |
80 })); | |
81 }, | 144 }, |
82 | 145 |
83 function testSendErrorPartialSuccess() { | 146 function testSendErrorPartialSuccess() { |
84 createSender().then(test.callbackPass(function(sender) { | 147 createSender() |
85 sender.send(generateData(BUFFER_SIZE * 3, 'b')).catch(test.callbackPass( | 148 .then(sendAndExpectError(generateData(BUFFER_SIZE * 3, 'b'), 1, 5)) |
86 function(e) { | 149 .then(sendAndExpectSuccess(generateData(1))) |
87 test.assertEq(1, e.error); | 150 .then(closeSender) |
88 test.assertEq(5, e.bytesSent); | 151 .then(test.succeed, test.fail); |
89 sender.send(generateData(1)).then(test.callbackPass( | |
90 function(bytesSent) { | |
91 test.assertEq(1, bytesSent); | |
92 sender.close(); | |
93 })); | |
94 })); | |
95 })); | |
96 }, | 152 }, |
97 | 153 |
98 function testSendErrorBetweenPackets() { | 154 function testSendErrorBetweenPackets() { |
99 createSender().then(test.callbackPass(function(sender) { | 155 var sender = createSender(); |
100 sender.send(generateData(2, 'b')).catch(test.callbackPass(function(e) { | 156 expectOrder([ |
101 test.assertEq(1, e.error); | 157 sender.then(sendAndExpectError(generateData(2, 'b'), 1, 2)), |
102 test.assertEq(2, e.bytesSent); | 158 sender.then(sendAndExpectError(generateData(2, 'b'), 1, 0)), |
103 })); | 159 ]) |
104 // After an error, all sends in progress will be cancelled. | 160 .then(sendAndExpectSuccess(generateData(1))) |
105 sender.send(generateData(2, 'b')).catch(test.callbackPass(function(e) { | 161 .then(closeSender) |
106 test.assertEq(1, e.error); | 162 .then(test.succeed, test.fail); |
107 test.assertEq(0, e.bytesSent); | |
108 sender.send(generateData(1)).then(test.callbackPass( | |
109 function(bytesSent) { | |
110 test.assertEq(1, bytesSent); | |
111 sender.close(); | |
112 })); | |
113 })); | |
114 })); | |
115 }, | 163 }, |
116 | 164 |
117 function testSendErrorInSecondPacket() { | 165 function testSendErrorInSecondPacket() { |
118 createSender().then(test.callbackPass(function(sender) { | 166 var sender = createSender(); |
119 sender.send(generateData(2, 'b')).then(test.callbackPass( | 167 expectOrder([ |
120 function(bytesSent) { | 168 sender.then(sendAndExpectSuccess(generateData(2, 'b'))), |
121 test.assertEq(2, bytesSent); | 169 sender.then(sendAndExpectError(generateData(2, 'b'), 1, 1)), |
122 })); | 170 ]) |
123 sender.send(generateData(2, 'b')).catch(test.callbackPass(function(e) { | 171 .then(sendAndExpectSuccess(generateData(1))) |
124 test.assertEq(1, e.error); | 172 .then(closeSender) |
125 test.assertEq(1, e.bytesSent); | 173 .then(test.succeed, test.fail); |
126 sender.send(generateData(1)).then(test.callbackPass( | |
127 function(bytesSent) { | |
128 test.assertEq(1, bytesSent); | |
129 sender.close(); | |
130 })); | |
131 })); | |
132 })); | |
133 }, | 174 }, |
134 | 175 |
135 function testSendErrorInLargeSend() { | 176 function testSendErrorInLargeSend() { |
136 createSender().then(test.callbackPass(function(sender) { | 177 createSender() |
137 sender.send(generateData(BUFFER_SIZE * 3, '1234567890')).catch( | 178 .then(sendAndExpectError( |
138 test.callbackPass(function(e) { | 179 generateData(BUFFER_SIZE * 3, '1234567890'), 1, 12)) |
139 test.assertEq(1, e.error); | 180 .then(sendAndExpectSuccess(generateData(1))) |
140 test.assertEq(12, e.bytesSent); | 181 .then(closeSender) |
141 sender.send(generateData(1)).then(test.callbackPass( | 182 .then(test.succeed, test.fail); |
142 function(bytesSent) { | |
143 test.assertEq(1, bytesSent); | |
144 sender.close(); | |
145 })); | |
146 })); | |
147 })); | |
148 }, | 183 }, |
149 | 184 |
150 function testSendErrorBeforeLargeSend() { | 185 function testSendErrorBeforeLargeSend() { |
151 createSender().then(test.callbackPass(function(sender) { | 186 var sender = createSender(); |
152 sender.send(generateData(5, 'b')).catch(test.callbackPass(function(e) { | 187 expectOrder([ |
153 test.assertEq(1, e.error); | 188 sender.then(sendAndExpectError(generateData(5, 'b'), 1, 2)), |
154 test.assertEq(2, e.bytesSent); | 189 sender.then(sendAndExpectError( |
155 })); | 190 generateData(BUFFER_SIZE * 3, '1234567890'), 1, 0)), |
156 sender.send(generateData(BUFFER_SIZE * 3, '1234567890')).catch( | 191 ]) |
157 test.callbackPass(function(e) { | 192 .then(sendAndExpectSuccess(generateData(1))) |
158 test.assertEq(1, e.error); | 193 .then(closeSender) |
159 test.assertEq(0, e.bytesSent); | 194 .then(test.succeed, test.fail); |
160 sender.send(generateData(1)).then(test.callbackPass( | |
161 function(bytesSent) { | |
162 test.assertEq(1, bytesSent); | |
163 sender.close(); | |
164 })); | |
165 })); | |
166 })); | |
167 }, | 195 }, |
168 | 196 |
169 function testCancelWithoutSend() { | 197 function testCancelWithoutSend() { |
170 createSender().then(test.callbackPass(function(sender) { | 198 createSender() |
171 sender.cancel(3).then(test.callbackPass(function() { | 199 .then(cancelSend(3)) |
172 sender.close(); | 200 .then(closeSender) |
173 })); | 201 .then(test.succeed, test.fail); |
174 })); | |
175 }, | 202 }, |
176 | 203 |
177 function testCancel() { | 204 function testCancel() { |
178 createSender().then(test.callbackPass(function(sender) { | 205 var sender = createSender(); |
179 var seen = null; | 206 expectOrder([ |
180 sender.send(generateData(1, 'b')).catch(test.callbackPass(function(e) { | 207 sender.then(sendAndExpectError(generateData(1, 'b'), 3, 0)), |
181 test.assertEq(3, e.error); | 208 sender.then(cancelSend(3)), |
182 test.assertEq(0, e.bytesSent); | 209 ]) |
183 test.assertEq(null, seen); | 210 .then(closeSender) |
184 seen = 'send'; | 211 .then(test.succeed, test.fail); |
185 })); | 212 sender.then(function(sender) { |
186 sender.cancel(3).then(test.callbackPass(function() { | |
187 test.assertEq('send', seen); | |
188 seen = 'cancel'; | |
189 sender.close(); | |
190 })); | |
191 test.assertThrows( | 213 test.assertThrows( |
192 sender.cancel, sender, [], 'Cancel already in progress'); | 214 sender.cancel, sender, [], 'Cancel already in progress'); |
193 test.assertThrows(sender.send, sender, [], 'Cancel in progress'); | 215 test.assertThrows(sender.send, sender, [], 'Cancel in progress'); |
194 })); | 216 }); |
195 }, | 217 }, |
196 | 218 |
197 function testClose() { | 219 function testClose() { |
198 createSender().then(test.callbackPass(function(sender) { | 220 var sender = createSender(); |
199 var seen = null; | 221 expectOrder([ |
200 sender.send(generateData(1, 'b')).catch(test.callbackPass(function(e) { | 222 sender.then(sendAndExpectError(generateData(1, 'b'), FATAL_ERROR, 0)), |
201 test.assertEq(FATAL_ERROR, e.error); | 223 sender.then(cancelSend(3)), |
202 test.assertEq(0, e.bytesSent); | 224 ]); |
203 test.assertEq(null, seen); | 225 sender |
204 seen = 'send'; | 226 .then(closeSender) |
205 })); | 227 .then(sendAfterClose) |
206 sender.cancel(3).then(test.callbackPass(function() { | 228 .then(test.succeed, test.fail); |
207 test.assertEq('send', seen); | 229 }, |
208 seen = 'cancel'; | 230 |
209 sender.close(); | 231 function testSendAfterSerialization() { |
210 })); | 232 var sender = createSender().then(serializeRoundTrip); |
211 sender.close(); | 233 expectOrder([ |
212 test.assertThrows( | 234 sender.then(sendAndExpectSuccess(generateData(1))), |
213 sender.cancel, sender, [], 'DataSender has been closed'); | 235 sender.then(sendAndExpectSuccess(generateData(1))), |
214 test.assertThrows(sender.send, sender, [], 'DataSender has been closed'); | 236 ]) |
215 })); | 237 .then(closeSender) |
| 238 .then(test.succeed, test.fail); |
| 239 }, |
| 240 |
| 241 function testSendErrorAfterSerialization() { |
| 242 createSender() |
| 243 .then(serializeRoundTrip) |
| 244 .then(sendAndExpectError(generateData(BUFFER_SIZE * 3, 'b'), 1, 0)) |
| 245 .then(sendAndExpectSuccess(generateData(1))) |
| 246 .then(closeSender) |
| 247 .then(test.succeed, test.fail); |
| 248 }, |
| 249 |
| 250 |
| 251 function testCancelAfterSerialization() { |
| 252 var sender = createSender().then(serializeRoundTrip); |
| 253 expectOrder([ |
| 254 sender.then(sendAndExpectError(generateData(1, 'b'), 4, 0)), |
| 255 sender.then(cancelSend(4)), |
| 256 ]) |
| 257 .then(closeSender) |
| 258 .then(test.succeed, test.fail); |
| 259 }, |
| 260 |
| 261 function testSerializeCancelsSendsInProgress() { |
| 262 var sender = createSender(); |
| 263 expectOrder([ |
| 264 sender.then(sendAndExpectError(generateData(1, 'b'), FATAL_ERROR, 0)), |
| 265 sender.then(sendAndExpectError(generateData(1, 'b'), FATAL_ERROR, 0)), |
| 266 sender.then(serializeRoundTrip), |
| 267 ]) |
| 268 .then(closeSender) |
| 269 .then(test.succeed, test.fail); |
| 270 }, |
| 271 |
| 272 function testSerializeWaitsForCancel() { |
| 273 var sender = createSender(); |
| 274 expectOrder([ |
| 275 sender.then(sendAndExpectError(generateData(1, 'b'), 3, 0)), |
| 276 sender.then(cancelSend(3)), |
| 277 sender.then(serializeRoundTrip), |
| 278 ]) |
| 279 .then(closeSender) |
| 280 .then(test.succeed, test.fail); |
| 281 }, |
| 282 |
| 283 function testSerializeAfterClose() { |
| 284 createSender() |
| 285 .then(closeSender) |
| 286 .then(serializeRoundTrip) |
| 287 .then(sendAfterClose) |
| 288 .then(test.succeed, test.fail); |
216 }, | 289 }, |
217 | 290 |
218 ], test.runTests, exports); | 291 ], test.runTests, exports); |
OLD | NEW |