Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(185)

Side by Side Diff: lib/unittest/unittest.dart

Issue 10545167: Some unit test fixes: (Closed) Base URL: http://dart.googlecode.com/svn/branches/bleeding_edge/dart/
Patch Set: Created 8 years, 6 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
« no previous file with comments | « lib/unittest/core_matchers.dart ('k') | tests/isolate/v2_unresolved_ports_negative_test.dart » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright (c) 2011, the Dart project authors. Please see the AUTHORS file 1 // Copyright (c) 2011, 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 /** 5 /**
6 * A library for writing dart unit tests. 6 * A library for writing dart unit tests.
7 * 7 *
8 * To import this library, specify the relative path to 8 * To import this library, specify the relative path to
9 * lib/unittest/unittest.dart. 9 * lib/unittest/unittest.dart.
10 * 10 *
(...skipping 279 matching lines...) Expand 10 before | Expand all | Expand 10 after
290 290
291 // TODO(sigmund): make a singleton const field when frog supports passing those 291 // TODO(sigmund): make a singleton const field when frog supports passing those
292 // as default values to named arguments. 292 // as default values to named arguments.
293 final _sentinel = const _Sentinel(); 293 final _sentinel = const _Sentinel();
294 294
295 /** Simulates spread arguments using named arguments. */ 295 /** Simulates spread arguments using named arguments. */
296 // TODO(sigmund): remove this class and simply use a closure with named 296 // TODO(sigmund): remove this class and simply use a closure with named
297 // arguments inside [_expectAsync], once bug 282 is fixed or frog is replaced by 297 // arguments inside [_expectAsync], once bug 282 is fixed or frog is replaced by
298 // dart2js. 298 // dart2js.
299 class _SpreadArgsHelper { 299 class _SpreadArgsHelper {
300 Function callback; 300 Function _callback;
301 int expectedCalls; 301 int _expectedCalls = 0;
302 int calls = 0; 302 int _calls = 0;
303 TestCase testCase; 303 TestCase _testCase;
304 _SpreadArgsHelper(this.callback, this.expectedCalls) { 304 Function _shouldCallBack;
305 Expect.isTrue(_currentTest < _tests.length); 305 Function _isDone;
306 testCase = _tests[_currentTest]; 306
307 testCase.callbacks++; 307 _init(Function callback, Function shouldCallBack, Function isDone,
308 [expectedCalls = 0]) {
309 assert(_currentTest < _tests.length);
310 _callback = callback;
311 _shouldCallBack = shouldCallBack;
312 _isDone = isDone;
313 _expectedCalls = expectedCalls;
314 _testCase = _tests[_currentTest];
315 _testCase.callbacks++;
316 }
317
318 _SpreadArgsHelper(callback, shouldCallBack, isDone) {
319 _init(callback, shouldCallBack, isDone);
320 }
321
322 _SpreadArgsHelper.fixedCallCount(callback, expectedCalls) {
323 _init(callback, _checkCallCount, _allCallsDone, expectedCalls);
324 }
325
326 _SpreadArgsHelper.variableCallCount(callback, isDone) {
327 _init(callback, _always, isDone);
328 }
329
330 _after() {
331 if (_isDone()) {
332 _handleAllCallbacksDone();
333 }
334 }
335
336 _allCallsDone() => _calls == _expectedCalls;
337
338 _always() {
339 // Always run except if the test is done.
340 if (_testCase.isComplete) {
341 _testCase.error(
342 'Callback called after already being marked as done ($_calls)',
343 '');
344 _state = _UNCAUGHT_ERROR;
345 return false;
346 } else {
347 return true;
348 }
308 } 349 }
309 350
310 invoke([arg0 = _sentinel, arg1 = _sentinel, arg2 = _sentinel, 351 invoke([arg0 = _sentinel, arg1 = _sentinel, arg2 = _sentinel,
311 arg3 = _sentinel, arg4 = _sentinel]) { 352 arg3 = _sentinel, arg4 = _sentinel]) {
312 return guardAsync(() { 353 return guardAsync(() {
313 if (!_incrementCall()) { 354 ++_calls;
355 if (!_shouldCallBack()) {
314 return; 356 return;
315 } else if (arg0 == _sentinel) { 357 } else if (arg0 == _sentinel) {
316 return callback(); 358 return _callback();
317 } else if (arg1 == _sentinel) { 359 } else if (arg1 == _sentinel) {
318 return callback(arg0); 360 return _callback(arg0);
319 } else if (arg2 == _sentinel) { 361 } else if (arg2 == _sentinel) {
320 return callback(arg0, arg1); 362 return _callback(arg0, arg1);
321 } else if (arg3 == _sentinel) { 363 } else if (arg3 == _sentinel) {
322 return callback(arg0, arg1, arg2); 364 return _callback(arg0, arg1, arg2);
323 } else if (arg4 == _sentinel) { 365 } else if (arg4 == _sentinel) {
324 return callback(arg0, arg1, arg2, arg3); 366 return _callback(arg0, arg1, arg2, arg3);
325 } else { 367 } else {
326 testCase.error( 368 _testCase.error(
327 'unittest lib does not support callbacks with more than 4 arguments', 369 'unittest lib does not support callbacks with more than 4 arguments',
328 ''); 370 '');
329 _state = _UNCAUGHT_ERROR; 371 _state = _UNCAUGHT_ERROR;
330 } 372 }
331 }, () { if (calls == expectedCalls) callbackDone(); }); 373 },
374 _after);
332 } 375 }
333 376
334 invoke0() { 377 invoke0() {
335 return guardAsync( 378 return guardAsync(
336 () => _incrementCall() ? callback() : null, 379 () { if (_shouldCallBack()) _callback(); },
337 () { if (calls == expectedCalls) callbackDone(); }); 380 _after);
338 } 381 }
339 382
340 invoke1(arg1) { 383 invoke1(arg1) {
341 return guardAsync( 384 return guardAsync(
342 () => _incrementCall() ? callback(arg1) : null, 385 () { if (_shouldCallBack()) _callback(arg1); },
343 () { if (calls == expectedCalls) callbackDone(); }); 386 _after);
344 } 387 }
345 388
346 invoke2(arg1, arg2) { 389 invoke2(arg1, arg2) {
347 return guardAsync( 390 return guardAsync(
348 () => _incrementCall() ? callback(arg1, arg2) : null, 391 () { if (_shouldCallBack()) _callback(arg1, arg2); },
349 () { if (calls == expectedCalls) callbackDone(); }); 392 _after);
350 } 393 }
351 394
352 /** Returns false if we exceded the number of expected calls. */ 395 /** Returns false if we exceded the number of expected calls. */
353 bool _incrementCall() { 396 bool _checkCallCount() {
354 calls++; 397 if (_calls > _expectedCalls) {
355 if (calls > expectedCalls) { 398 _testCase.error(
356 testCase.error( 399 'Callback called more times than expected '
357 'Callback called more times than expected ($calls > $expectedCalls)', 400 '($_calls > $_expectedCalls)',
358 ''); 401 '');
359 _state = _UNCAUGHT_ERROR; 402 _state = _UNCAUGHT_ERROR;
360 return false; 403 return false;
361 } 404 }
362 return true; 405 return true;
363 } 406 }
364 } 407 }
365 408
366 /** 409 /**
367 * Indicate that [callback] is expected to be called a [count] number of times 410 * Indicate that [callback] is expected to be called a [count] number of times
368 * (by default 1). The unittest framework will wait for the callback to run the 411 * (by default 1). The unittest framework will wait for the callback to run the
369 * specified [count] times before it continues with the following test. Using 412 * specified [count] times before it continues with the following test. Using
370 * [_expectAsync] will also ensure that errors that occur within [callback] are 413 * [_expectAsync] will also ensure that errors that occur within [callback] are
371 * tracked and reported. [callback] should take between 0 and 4 positional 414 * tracked and reported. [callback] should take between 0 and 4 positional
372 * arguments (named arguments are not supported here). 415 * arguments (named arguments are not supported here).
373 */ 416 */
374 Function _expectAsync(Function callback, [int count = 1]) { 417 Function _expectAsync(Function callback, [int count = 1]) {
375 return new _SpreadArgsHelper(callback, count).invoke; 418 return new _SpreadArgsHelper.fixedCallCount(callback, count).invoke;
376 } 419 }
377 420
378 /** 421 /**
379 * Indicate that [callback] is expected to be called a [count] number of times 422 * Indicate that [callback] is expected to be called a [count] number of times
380 * (by default 1). The unittest framework will wait for the callback to run the 423 * (by default 1). The unittest framework will wait for the callback to run the
381 * specified [count] times before it continues with the following test. Using 424 * specified [count] times before it continues with the following test. Using
382 * [expectAsync0] will also ensure that errors that occur within [callback] are 425 * [expectAsync0] will also ensure that errors that occur within [callback] are
383 * tracked and reported. [callback] should take 0 positional arguments (named 426 * tracked and reported. [callback] should take 0 positional arguments (named
384 * arguments are not supported). 427 * arguments are not supported).
385 */ 428 */
386 // TODO(sigmund): deprecate this API when issue 2706 is fixed. 429 // TODO(sigmund): deprecate this API when issue 2706 is fixed.
387 Function expectAsync0(Function callback, [int count = 1]) { 430 Function expectAsync0(Function callback, [int count = 1]) {
388 return new _SpreadArgsHelper(callback, count).invoke0; 431 return new _SpreadArgsHelper.fixedCallCount(callback, count).invoke0;
389 } 432 }
390 433
391 /** Like [expectAsync0] but [callback] should take 1 positional argument. */ 434 /** Like [expectAsync0] but [callback] should take 1 positional argument. */
392 // TODO(sigmund): deprecate this API when issue 2706 is fixed. 435 // TODO(sigmund): deprecate this API when issue 2706 is fixed.
393 Function expectAsync1(Function callback, [int count = 1]) { 436 Function expectAsync1(Function callback, [int count = 1]) {
394 return new _SpreadArgsHelper(callback, count).invoke1; 437 return new _SpreadArgsHelper.fixedCallCount(callback, count).invoke1;
395 } 438 }
396 439
397 /** Like [expectAsync0] but [callback] should take 2 positional arguments. */ 440 /** Like [expectAsync0] but [callback] should take 2 positional arguments. */
398 // TODO(sigmund): deprecate this API when issue 2706 is fixed. 441 // TODO(sigmund): deprecate this API when issue 2706 is fixed.
399 Function expectAsync2(Function callback, [int count = 1]) { 442 Function expectAsync2(Function callback, [int count = 1]) {
400 return new _SpreadArgsHelper(callback, count).invoke2; 443 return new _SpreadArgsHelper.fixedCallCount(callback, count).invoke2;
444 }
445
446 /**
447 * Indicate that [callback] is expected to be called until [isDone] returns
448 * true. The unittest framework checks [isDone] after each callback and only
449 * when it returns true will it continue with the following test. Using
450 * [expectAsyncUntil] will also ensure that errors that occur within
451 * [callback] are tracked and reported. [callback] should take between 0 and
452 * 4 positional arguments (named arguments are not supported).
453 */
454 Function _expectAsyncUntil(Function callback, Function isDone) {
455 return new _SpreadArgsHelper.variableCallCount(callback, isDone).invoke;
456 }
457
458 /**
459 * Indicate that [callback] is expected to be called until [isDone] returns
460 * true. The unittest framework check [isDone] after each callback and only
461 * when it returns true will it continue with the following test. Using
462 * [expectAsyncUntil0] will also ensure that errors that occur within
463 * [callback] are tracked and reported. [callback] should take 0 positional
464 * arguments (named arguments are not supported).
465 */
466 // TODO(sigmund): deprecate this API when issue 2706 is fixed.
467 Function expectAsyncUntil0(Function callback, Function isDone) {
468 return new _SpreadArgsHelper.variableCallCount(callback, isDone).invoke0;
469 }
470
471 /**
472 * Like [expectAsyncUntil0] but [callback] should take 1 positional argument.
473 */
474 // TODO(sigmund): deprecate this API when issue 2706 is fixed.
475 Function expectAsyncUntil1(Function callback, Function isDone) {
476 return new _SpreadArgsHelper.variableCallCount(callback, isDone).invoke1;
477 }
478
479 /**
480 * Like [expectAsyncUntil0] but [callback] should take 2 positional arguments.
481 */
482 // TODO(sigmund): deprecate this API when issue 2706 is fixed.
483 Function expectAsyncUntil2(Function callback, Function isDone) {
484 return new _SpreadArgsHelper.variableCallCount(callback, isDone).invoke2;
401 } 485 }
402 486
403 /** 487 /**
404 * Creates a new named group of tests. Calls to group() or test() within the 488 * Creates a new named group of tests. Calls to group() or test() within the
405 * body of the function passed to this will inherit this group's description. 489 * body of the function passed to this will inherit this group's description.
406 */ 490 */
407 void group(String description, void body()) { 491 void group(String description, void body()) {
408 ensureInitialized(); 492 ensureInitialized();
409 493
410 // Concatenate the new group. 494 // Concatenate the new group.
411 final oldGroup = _currentGroup; 495 final oldGroup = _currentGroup;
412 if (_currentGroup != '') { 496 if (_currentGroup != '') {
413 // Add a space. 497 // Add a space.
414 _currentGroup = '$_currentGroup $description'; 498 _currentGroup = '$_currentGroup $description';
415 } else { 499 } else {
416 // The first group. 500 // The first group.
417 _currentGroup = description; 501 _currentGroup = description;
418 } 502 }
419 503
420 try { 504 try {
421 body(); 505 body();
422 } finally { 506 } finally {
423 // Now that the group is over, restore the previous one. 507 // Now that the group is over, restore the previous one.
424 _currentGroup = oldGroup; 508 _currentGroup = oldGroup;
425 } 509 }
426 } 510 }
427 511
428 /** Called by subclasses to indicate that an asynchronous test completed. */ 512 /** Called by subclasses to indicate that an asynchronous test completed. */
429 void callbackDone() { 513 void _handleAllCallbacksDone() {
430 // TODO (gram): we defer this to give the nextBatch recursive 514 // TODO (gram): we defer this to give the nextBatch recursive
431 // stack a chance to unwind. This is a temporary hack but 515 // stack a chance to unwind. This is a temporary hack but
432 // really a bunch of code here needs to be fixed. We have a 516 // really a bunch of code here needs to be fixed. We have a
433 // single array that is being iterated through by nextBatch(), 517 // single array that is being iterated through by nextBatch(),
434 // which is recursively invoked in the case of async tests that 518 // which is recursively invoked in the case of async tests that
435 // run synchronously. Bad things can then happen. 519 // run synchronously. Bad things can then happen.
436 _defer(() { 520 _defer(() {
437 _callbacksCalled++; 521 _callbacksCalled++;
438 if (_currentTest < _tests.length) { 522 if (_currentTest < _tests.length) {
439 final testCase = _tests[_currentTest]; 523 final testCase = _tests[_currentTest];
(...skipping 95 matching lines...) Expand 10 before | Expand all | Expand 10 after
535 * Runs a batch of tests, yielding whenever an asynchronous test starts 619 * Runs a batch of tests, yielding whenever an asynchronous test starts
536 * running. Tests will resume executing when such asynchronous test calls 620 * running. Tests will resume executing when such asynchronous test calls
537 * [done] or if it fails with an exception. 621 * [done] or if it fails with an exception.
538 */ 622 */
539 _nextBatch() { 623 _nextBatch() {
540 while (_currentTest < _tests.length) { 624 while (_currentTest < _tests.length) {
541 final testCase = _tests[_currentTest]; 625 final testCase = _tests[_currentTest];
542 guardAsync(() { 626 guardAsync(() {
543 _callbacksCalled = 0; 627 _callbacksCalled = 0;
544 _state = _RUNNING_TEST; 628 _state = _RUNNING_TEST;
545
546 testCase.test(); 629 testCase.test();
547 630
548 if (_state != _UNCAUGHT_ERROR) { 631 if (_state != _UNCAUGHT_ERROR) {
549 if (testCase.callbacks == _callbacksCalled) { 632 if (testCase.callbacks == _callbacksCalled) {
550 testCase.pass(); 633 testCase.pass();
551 } 634 }
552 } 635 }
553 }); 636 });
554 637
555 if (!testCase.isComplete && testCase.callbacks > 0) return; 638 if (!testCase.isComplete && testCase.callbacks > 0) return;
(...skipping 33 matching lines...) Expand 10 before | Expand all | Expand 10 after
589 throw new ExpectException(message); 672 throw new ExpectException(message);
590 } 673 }
591 674
592 /** 675 /**
593 * Lazily initializes the test library if not already initialized. 676 * Lazily initializes the test library if not already initialized.
594 */ 677 */
595 ensureInitialized() { 678 ensureInitialized() {
596 if (_state != _UNINITIALIZED) return; 679 if (_state != _UNINITIALIZED) return;
597 680
598 _tests = <TestCase>[]; 681 _tests = <TestCase>[];
682 _uncaughtErrorMessage = null;
683 _currentTest = 0;
599 _currentGroup = ''; 684 _currentGroup = '';
600 _state = _READY; 685 _state = _READY;
601 _testRunner = _nextBatch; 686 _testRunner = _nextBatch;
602 687
603 if (_config == null) { 688 if (_config == null) {
604 _config = new Configuration(); 689 _config = new Configuration();
605 } 690 }
606 _config.onInit(); 691 _config.onInit();
607 692
608 // Immediately queue the suite up. It will run after a timeout (i.e. after 693 // Immediately queue the suite up. It will run after a timeout (i.e. after
609 // main() has returned). 694 // main() has returned).
610 _defer(_runTests); 695 _defer(_runTests);
611 } 696 }
612 697
613 /** Signature for a test function. */ 698 /** Signature for a test function. */
614 typedef void TestFunction(); 699 typedef void TestFunction();
OLDNEW
« no previous file with comments | « lib/unittest/core_matchers.dart ('k') | tests/isolate/v2_unresolved_ports_negative_test.dart » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698