OLD | NEW |
1 // Copyright (c) 2014, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2014, the Dart project authors. Please see the AUTHORS file |
2 // for details. All rights reserved. Use of this source code is governed by a | 2 // for details. All rights reserved. Use of this source code is governed by a |
3 // BSD-style license that can be found in the LICENSE file. | 3 // BSD-style license that can be found in the LICENSE file. |
4 | 4 |
5 import 'dart:async'; | 5 import 'dart:async'; |
6 | 6 |
7 import 'package:fake_async/fake_async.dart'; | 7 import 'package:fake_async/fake_async.dart'; |
8 import 'package:pool/pool.dart'; | 8 import 'package:pool/pool.dart'; |
9 import 'package:stack_trace/stack_trace.dart'; | 9 import 'package:stack_trace/stack_trace.dart'; |
10 import 'package:test/test.dart'; | 10 import 'package:test/test.dart'; |
(...skipping 253 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
264 expect(innerZone, isNot(equals(outerZone))); | 264 expect(innerZone, isNot(equals(outerZone))); |
265 | 265 |
266 resource.allowRelease(expectAsync(() { | 266 resource.allowRelease(expectAsync(() { |
267 expect(Zone.current, equals(innerZone)); | 267 expect(Zone.current, equals(innerZone)); |
268 })); | 268 })); |
269 }); | 269 }); |
270 | 270 |
271 pool.request(); | 271 pool.request(); |
272 }); | 272 }); |
273 }); | 273 }); |
| 274 |
| 275 group("close()", () { |
| 276 test("disallows request() and withResource()", () { |
| 277 var pool = new Pool(1)..close(); |
| 278 expect(pool.request, throwsStateError); |
| 279 expect(() => pool.withResource(() {}), throwsStateError); |
| 280 }); |
| 281 |
| 282 test("pending requests are fulfilled", () async { |
| 283 var pool = new Pool(1); |
| 284 var resource1 = await pool.request(); |
| 285 expect(pool.request().then((resource2) { |
| 286 resource2.release(); |
| 287 }), completes); |
| 288 expect(pool.close(), completes); |
| 289 resource1.release(); |
| 290 }); |
| 291 |
| 292 test("pending requests are fulfilled with allowRelease", () async { |
| 293 var pool = new Pool(1); |
| 294 var resource1 = await pool.request(); |
| 295 |
| 296 var completer = new Completer(); |
| 297 expect(pool.request().then((resource2) { |
| 298 expect(completer.isCompleted, isTrue); |
| 299 resource2.release(); |
| 300 }), completes); |
| 301 expect(pool.close(), completes); |
| 302 |
| 303 resource1.allowRelease(() => completer.future); |
| 304 await new Future.delayed(Duration.ZERO); |
| 305 |
| 306 completer.complete(); |
| 307 }); |
| 308 |
| 309 test("doesn't complete until all resources are released", () async { |
| 310 var pool = new Pool(2); |
| 311 var resource1 = await pool.request(); |
| 312 var resource2 = await pool.request(); |
| 313 var resource3Future = pool.request(); |
| 314 |
| 315 var resource1Released = false; |
| 316 var resource2Released = false; |
| 317 var resource3Released = false; |
| 318 expect(pool.close().then((_) { |
| 319 expect(resource1Released, isTrue); |
| 320 expect(resource2Released, isTrue); |
| 321 expect(resource3Released, isTrue); |
| 322 }), completes); |
| 323 |
| 324 resource1Released = true; |
| 325 resource1.release(); |
| 326 await new Future.delayed(Duration.ZERO); |
| 327 |
| 328 resource2Released = true; |
| 329 resource2.release(); |
| 330 await new Future.delayed(Duration.ZERO); |
| 331 |
| 332 var resource3 = await resource3Future; |
| 333 resource3Released = true; |
| 334 resource3.release(); |
| 335 }); |
| 336 |
| 337 test("active onReleases complete as usual", () async { |
| 338 var pool = new Pool(1); |
| 339 var resource = await pool.request(); |
| 340 |
| 341 // Set up an onRelease callback whose completion is controlled by |
| 342 // [completer]. |
| 343 var completer = new Completer(); |
| 344 resource.allowRelease(() => completer.future); |
| 345 expect(pool.request().then((_) { |
| 346 expect(completer.isCompleted, isTrue); |
| 347 }), completes); |
| 348 |
| 349 await new Future.delayed(Duration.ZERO); |
| 350 pool.close(); |
| 351 |
| 352 await new Future.delayed(Duration.ZERO); |
| 353 completer.complete(); |
| 354 }); |
| 355 |
| 356 test("inactive onReleases fire", () async { |
| 357 var pool = new Pool(2); |
| 358 var resource1 = await pool.request(); |
| 359 var resource2 = await pool.request(); |
| 360 |
| 361 var completer1 = new Completer(); |
| 362 resource1.allowRelease(() => completer1.future); |
| 363 var completer2 = new Completer(); |
| 364 resource2.allowRelease(() => completer2.future); |
| 365 |
| 366 expect(pool.close().then((_) { |
| 367 expect(completer1.isCompleted, isTrue); |
| 368 expect(completer2.isCompleted, isTrue); |
| 369 }), completes); |
| 370 |
| 371 await new Future.delayed(Duration.ZERO); |
| 372 completer1.complete(); |
| 373 |
| 374 await new Future.delayed(Duration.ZERO); |
| 375 completer2.complete(); |
| 376 }); |
| 377 |
| 378 test("new allowReleases fire immediately", () async { |
| 379 var pool = new Pool(1); |
| 380 var resource = await pool.request(); |
| 381 |
| 382 var completer = new Completer(); |
| 383 expect(pool.close().then((_) { |
| 384 expect(completer.isCompleted, isTrue); |
| 385 }), completes); |
| 386 |
| 387 await new Future.delayed(Duration.ZERO); |
| 388 resource.allowRelease(() => completer.future); |
| 389 |
| 390 await new Future.delayed(Duration.ZERO); |
| 391 completer.complete(); |
| 392 }); |
| 393 |
| 394 test("an onRelease error is piped to the return value", () async { |
| 395 var pool = new Pool(1); |
| 396 var resource = await pool.request(); |
| 397 |
| 398 var completer = new Completer(); |
| 399 resource.allowRelease(() => completer.future); |
| 400 |
| 401 expect(pool.close(), throwsA("oh no!")); |
| 402 |
| 403 await new Future.delayed(Duration.ZERO); |
| 404 completer.completeError("oh no!"); |
| 405 }); |
| 406 }); |
274 } | 407 } |
275 | 408 |
276 /// Returns a function that will cause the test to fail if it's called. | 409 /// Returns a function that will cause the test to fail if it's called. |
277 /// | 410 /// |
278 /// This should only be called within a [FakeAsync.run] zone. | 411 /// This should only be called within a [FakeAsync.run] zone. |
279 Function expectNoAsync() { | 412 Function expectNoAsync() { |
280 var stack = new Trace.current(1); | 413 var stack = new Trace.current(1); |
281 return () => registerException( | 414 return () => registerException( |
282 new TestFailure("Expected function not to be called."), stack); | 415 new TestFailure("Expected function not to be called."), stack); |
283 } | 416 } |
284 | 417 |
285 /// A matcher for Futures that asserts that they don't complete. | 418 /// A matcher for Futures that asserts that they don't complete. |
286 /// | 419 /// |
287 /// This should only be called within a [FakeAsync.run] zone. | 420 /// This should only be called within a [FakeAsync.run] zone. |
288 Matcher get doesNotComplete => predicate((future) { | 421 Matcher get doesNotComplete => predicate((future) { |
289 expect(future, new isInstanceOf<Future>()); | 422 expect(future, new isInstanceOf<Future>()); |
290 | 423 |
291 var stack = new Trace.current(1); | 424 var stack = new Trace.current(1); |
292 future.then((_) => registerException( | 425 future.then((_) => registerException( |
293 new TestFailure("Expected future not to complete."), stack)); | 426 new TestFailure("Expected future not to complete."), stack)); |
294 return true; | 427 return true; |
295 }); | 428 }); |
OLD | NEW |