TestCase class
testcase.dart: this file is sourced by unittest.dart. It defines TestCase and assumes unittest defines the type TestFunction.
Summarizes information about a single test case.
class TestCase { /** Identifier for this test. */ final int id; /** A description of what the test is specifying. */ final String description; /** The setup function to call before the test, if any. */ Function _setUp; Function get setUp => _setUp; set setUp(Function value) => _setUp = value; /** The teardown function to call after the test, if any. */ Function _tearDown; Function get tearDown => _tearDown; set tearDown(Function value) => _tearDown = value; /** The body of the test case. */ TestFunction test; /** * Remaining number of callbacks functions that must reach a 'done' state * to wait for before the test completes. */ int callbackFunctionsOutstanding; /** Error or failure message. */ String message = ''; /** * One of [PASS], [FAIL], [ERROR], or [null] if the test hasn't run yet. */ String result; /** Stack trace associated with this test, or null if it succeeded. */ String stackTrace; /** The group (or groups) under which this test is running. */ final String currentGroup; DateTime startTime; Duration runningTime; bool enabled = true; bool _doneTeardown = false; Completer _testComplete; TestCase(this.id, this.description, this.test, this.callbackFunctionsOutstanding) : currentGroup = _currentGroup, _setUp = _testSetup, _tearDown = _testTeardown; bool get isComplete => !enabled || result != null; void _prepTest() { _config.onTestStart(this); startTime = new DateTime.now(); runningTime = null; } void _runTest() { _prepTest(); test(); if (result == null && callbackFunctionsOutstanding == 0) { pass(); } } /** * Perform any associated [setUp] function and run the test. Returns * a [Future] that can be used to schedule the next test. If the test runs * to completion synchronously, or is disabled, we return null, to * tell unittest to schedule the next test immediately. */ Future run() { if (!enabled) return null; result = stackTrace = null; message = ''; _doneTeardown = false; var rtn = _setUp == null ? null : _setUp(); if (rtn is Future) { rtn.then(expectAsync1((_) =>_runTest(), id: '[Async setUp completion handler]')) .catchError((e) { _prepTest(); // Calling error() will result in the tearDown being done. // One could debate whether tearDown should be done after // a failed setUp. There is no right answer, but doing it // seems to be the more conservative approach, because // unittest will not stop at a test failure. error("$description: Test setup failed: ${e.error}"); }); } else { _runTest(); } if (result == null) { // Not complete. _testComplete = new Completer(); return _testComplete.future; } return null; } void _notifyComplete() { if (_testComplete != null) { _testComplete.complete(this); _testComplete = null; } } void _complete() { if (runningTime == null) { // TODO(gram): currently the duration measurement code is blocked // by issue 4437. When that is fixed replace the line below with: // runningTime = new DateTime.now().difference(startTime); runningTime = new Duration(milliseconds: 0); } if (!_doneTeardown) { _doneTeardown = true; if (_tearDown != null) { var rtn = _tearDown(); if (rtn is Future) { rtn.then((_) { if (result == null) { // The test passed. In some cases we will already // have set this result (e.g. if the test was async // and all callbacks completed). If not, we do it here. pass(); } else { // The test has already been marked as pass/fail. // Just report the updated result. _config.onTestResult(this); } _notifyComplete(); }) .catchError((e) { // We don't call fail() as that will potentially result in // spurious messages like 'test failed more than once'. result = ERROR; message = "$description: Test teardown failed: ${e.error}"; _config.onTestResult(this); _notifyComplete(); }); return; } } } _config.onTestResult(this); _notifyComplete(); } void pass() { result = PASS; _complete(); } void fail(String messageText, [String stack = '']) { if (result != null) { if (result == PASS) { error('Test failed after initially passing: $messageText', stack); } else if (result == FAIL) { error('Test failed more than once: $messageText', stack); } } else { result = FAIL; message = messageText; stackTrace = stack; _complete(); } } void error(String messageText, [String stack = '']) { result = ERROR; message = messageText; stackTrace = stack; _complete(); } }
Constructors
new TestCase(int id, String description, TestFunction test, int callbackFunctionsOutstanding) #
TestCase(this.id, this.description, this.test, this.callbackFunctionsOutstanding) : currentGroup = _currentGroup, _setUp = _testSetup, _tearDown = _testTeardown;
Properties
int callbackFunctionsOutstanding #
callbackFunctionsOutstanding
final String currentGroup #
currentGroup
final String description #
description
bool enabled #
enabled = true
final int id #
id
final bool isComplete #
bool get isComplete => !enabled || result != null;
String message #
message = ''
String result #
result
Duration runningTime #
runningTime
Function setUp #
Function get setUp => _setUp;
set setUp(Function value) => _setUp = value;
String stackTrace #
stackTrace
DateTime startTime #
startTime
Function tearDown #
Function get tearDown => _tearDown;
set tearDown(Function value) => _tearDown = value;
TestFunction test #
test
Methods
void error(String messageText, [String stack = '']) #
void error(String messageText, [String stack = '']) { result = ERROR; message = messageText; stackTrace = stack; _complete(); }
void fail(String messageText, [String stack = '']) #
void fail(String messageText, [String stack = '']) { if (result != null) { if (result == PASS) { error('Test failed after initially passing: $messageText', stack); } else if (result == FAIL) { error('Test failed more than once: $messageText', stack); } } else { result = FAIL; message = messageText; stackTrace = stack; _complete(); } }
void pass() #
void pass() { result = PASS; _complete(); }
Future run() #
Perform any associated setUp function and run the test. Returns
a Future
that can be used to schedule the next test. If the test runs
to completion synchronously, or is disabled, we return null, to
tell unittest to schedule the next test immediately.
Future run() { if (!enabled) return null; result = stackTrace = null; message = ''; _doneTeardown = false; var rtn = _setUp == null ? null : _setUp(); if (rtn is Future) { rtn.then(expectAsync1((_) =>_runTest(), id: '[Async setUp completion handler]')) .catchError((e) { _prepTest(); // Calling error() will result in the tearDown being done. // One could debate whether tearDown should be done after // a failed setUp. There is no right answer, but doing it // seems to be the more conservative approach, because // unittest will not stop at a test failure. error("$description: Test setup failed: ${e.error}"); }); } else { _runTest(); } if (result == null) { // Not complete. _testComplete = new Completer(); return _testComplete.future; } return null; }