Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2012, 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 #library("test_suite"); | 5 #library("test_suite"); |
| 6 | 6 |
| 7 #import("dart:io"); | 7 #import("dart:io"); |
| 8 #import("status_file_parser.dart"); | 8 #import("status_file_parser.dart"); |
| 9 #import("test_runner.dart"); | 9 #import("test_runner.dart"); |
| 10 #import("multitest.dart"); | 10 #import("multitest.dart"); |
| 11 | 11 |
| 12 #source("browser_test.dart"); | 12 #source("browser_test.dart"); |
| 13 | 13 |
| 14 /** | |
| 15 * Classes and methods for enumerating and preparing tests. | |
| 16 * | |
| 17 * This module includes: | |
|
Bob Nystrom
2012/02/07 18:41:24
Add a blank line after this one, and the subsequen
| |
| 18 * - Creating tests by listing all the Dart files in certain directories, | |
| 19 * and creating [TestCase]s for those files that meet the relevant criteria. | |
| 20 * - Preparing tests, including copying files and frameworks to temporary | |
| 21 * directories, and computing the command line and arguments to be run. | |
| 22 */ | |
| 23 | |
| 24 /** | |
| 25 * A [TestSuite] represents a collection of tests. It creates a [TestCase] | |
| 26 * object for each test to be run, and passes the test cases to a callback. | |
| 27 * | |
| 28 * Most [TestSuites] represent a directory or directory tree containing tests, | |
| 29 * and a status file containing the expected results when these tests are run. | |
| 30 */ | |
| 14 interface TestSuite { | 31 interface TestSuite { |
| 32 /** | |
| 33 * Call the callback function onTest with a [TestCase] argument for each | |
|
Bob Nystrom
2012/02/07 18:41:24
[onTest] and the other parameters mentioned.
You
Bill Hesse
2012/02/09 15:47:39
How can we reference fields or functions of class
Bob Nystrom
2012/02/09 21:23:48
I believe [B.field] should do that. If not, it's a
| |
| 34 * test in the suite. When all tests have been processed, call onDone. | |
| 35 * | |
| 36 * The testCache argument provides a persistent store that can be used to | |
| 37 * cache information about the test suite, so that directories do not need | |
| 38 * to be listed each time. If the tests require a temporary directory for | |
| 39 * their files, they can get one from globalTempDir. | |
| 40 */ | |
| 15 void forEachTest(Function onTest, Map testCache, String globalTempDir(), | 41 void forEachTest(Function onTest, Map testCache, String globalTempDir(), |
| 16 [Function onDone]); | 42 [Function onDone]); |
| 17 } | 43 } |
| 18 | 44 |
| 19 | |
| 20 class CCTestListerIsolate extends Isolate { | 45 class CCTestListerIsolate extends Isolate { |
| 21 CCTestListerIsolate() : super.heavy(); | 46 CCTestListerIsolate() : super.heavy(); |
| 22 | 47 |
| 23 void main() { | 48 void main() { |
| 24 port.receive((String runnerPath, SendPort replyTo) { | 49 port.receive((String runnerPath, SendPort replyTo) { |
| 25 var p = new Process.start(runnerPath, ["--list"]); | 50 var p = new Process.start(runnerPath, ["--list"]); |
| 26 StringInputStream stdoutStream = new StringInputStream(p.stdout); | 51 StringInputStream stdoutStream = new StringInputStream(p.stdout); |
| 27 List<String> tests = new List<String>(); | 52 List<String> tests = new List<String>(); |
| 28 stdoutStream.lineHandler = () { | 53 stdoutStream.lineHandler = () { |
| 29 String line = stdoutStream.readLine(); | 54 String line = stdoutStream.readLine(); |
| (...skipping 15 matching lines...) Expand all Loading... | |
| 45 replyTo.send(test); | 70 replyTo.send(test); |
| 46 } | 71 } |
| 47 replyTo.send(""); | 72 replyTo.send(""); |
| 48 }; | 73 }; |
| 49 port.close(); | 74 port.close(); |
| 50 }); | 75 }); |
| 51 } | 76 } |
| 52 } | 77 } |
| 53 | 78 |
| 54 | 79 |
| 80 /** | |
| 81 * A specialized [TestSuite] that runs tests written in C to unit test | |
| 82 * the Dart virtual machine and its API. | |
| 83 * | |
| 84 * The tests are compiled into a monolithic executable by the build step. | |
| 85 * The executable lists its tests when run with the --list command line flag. | |
| 86 * Individual tests are run by specifying them on the command line. | |
| 87 */ | |
| 55 class CCTestSuite implements TestSuite { | 88 class CCTestSuite implements TestSuite { |
| 56 Map configuration; | 89 Map configuration; |
| 57 final String suiteName; | 90 final String suiteName; |
| 58 String runnerPath; | 91 String runnerPath; |
| 59 final String dartDir; | 92 final String dartDir; |
| 60 List<String> statusFilePaths; | 93 List<String> statusFilePaths; |
| 61 Function doTest; | 94 Function doTest; |
| 62 Function doDone; | 95 Function doDone; |
| 63 ReceivePort receiveTestName; | 96 ReceivePort receiveTestName; |
| 64 TestExpectations testExpectations; | 97 TestExpectations testExpectations; |
| (...skipping 76 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 141 Map optionsFromFile; | 174 Map optionsFromFile; |
| 142 bool isNegative; | 175 bool isNegative; |
| 143 bool isNegativeIfChecked; | 176 bool isNegativeIfChecked; |
| 144 bool hasFatalTypeErrors; | 177 bool hasFatalTypeErrors; |
| 145 | 178 |
| 146 TestInformation(this.filename, this.optionsFromFile, this.isNegative, | 179 TestInformation(this.filename, this.optionsFromFile, this.isNegative, |
| 147 this.isNegativeIfChecked, this.hasFatalTypeErrors); | 180 this.isNegativeIfChecked, this.hasFatalTypeErrors); |
| 148 } | 181 } |
| 149 | 182 |
| 150 | 183 |
| 184 /** | |
| 185 * A standard [TestSuite] implementation that searches for tests in a | |
| 186 * directory, and creates [TestCase]s that compile and/or run them. | |
| 187 */ | |
| 151 class StandardTestSuite implements TestSuite { | 188 class StandardTestSuite implements TestSuite { |
| 152 Map configuration; | 189 Map configuration; |
| 153 String suiteName; | 190 String suiteName; |
| 154 String directoryPath; | 191 String directoryPath; |
| 155 List<String> statusFilePaths; | 192 List<String> statusFilePaths; |
| 156 Function doTest; | 193 Function doTest; |
| 157 Function doDone; | 194 Function doDone; |
| 158 int activeTestGenerators = 0; | 195 int activeTestGenerators = 0; |
| 159 bool listingDone = false; | 196 bool listingDone = false; |
| 160 TestExpectations testExpectations; | 197 TestExpectations testExpectations; |
| 161 List<TestInformation> cachedTests; | 198 List<TestInformation> cachedTests; |
| 162 final String dartDir; | 199 final String dartDir; |
| 163 Function globalTemporaryDirectory; | 200 Function globalTemporaryDirectory; |
| 164 | 201 |
| 165 StandardTestSuite(Map this.configuration, | 202 StandardTestSuite(Map this.configuration, |
| 166 String this.suiteName, | 203 String this.suiteName, |
| 167 String this.directoryPath, | 204 String this.directoryPath, |
| 168 List<String> this.statusFilePaths) | 205 List<String> this.statusFilePaths) |
| 169 : dartDir = TestUtils.dartDir(); | 206 : dartDir = TestUtils.dartDir(); |
| 170 | 207 |
| 208 /** | |
| 209 * The default implementation assumes a file is a test if | |
| 210 * it ends in "Test.dart". | |
| 211 */ | |
| 171 bool isTestFile(String filename) => filename.endsWith("Test.dart"); | 212 bool isTestFile(String filename) => filename.endsWith("Test.dart"); |
| 172 | 213 |
| 173 bool listRecursively() => false; | 214 bool listRecursively() => false; |
| 174 | 215 |
| 175 String shellPath() => TestUtils.dartShellFileName(configuration); | 216 String shellPath() => TestUtils.dartShellFileName(configuration); |
| 176 | 217 |
| 177 List<String> additionalOptions(String filename) => []; | 218 List<String> additionalOptions(String filename) => []; |
| 178 | 219 |
| 179 void forEachTest(Function onTest, Map testCache, String globalTempDir(), | 220 void forEachTest(Function onTest, Map testCache, String globalTempDir(), |
| 180 [Function onDone = null]) { | 221 [Function onDone = null]) { |
| (...skipping 166 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 347 DoMultitest(filename, | 388 DoMultitest(filename, |
| 348 TestUtils.buildDir(configuration), | 389 TestUtils.buildDir(configuration), |
| 349 directoryPath, | 390 directoryPath, |
| 350 createTestCase, | 391 createTestCase, |
| 351 testGeneratorDone); | 392 testGeneratorDone); |
| 352 } else { | 393 } else { |
| 353 createTestCase(filename, optionsFromFile['isNegative']); | 394 createTestCase(filename, optionsFromFile['isNegative']); |
| 354 } | 395 } |
| 355 } | 396 } |
| 356 | 397 |
| 398 /** | |
| 399 * The [StandardTestSuite] has support for testing components that | |
| 400 * compile a test from Dart to Javascript, and then run the resulting | |
| 401 * Javascript. This function creates a working directory to hold the | |
| 402 * Javascript version of the test, and copies the appropriate framework | |
| 403 * files to that directory. It creates a [BrowserTestCase], which has | |
| 404 * two sequential steps to be run by the [ProcessQueue when] the test is | |
| 405 * executed: a compilation | |
| 406 * step and an execution step, both with the appropriate executable and | |
| 407 * arguments. | |
| 408 */ | |
| 357 void enqueueBrowserTest(String filename, | 409 void enqueueBrowserTest(String filename, |
| 358 String testName, | 410 String testName, |
| 359 Map optionsFromFile, | 411 Map optionsFromFile, |
| 360 Set<String> expectations, | 412 Set<String> expectations, |
| 361 bool isNegative) { | 413 bool isNegative) { |
| 362 if (optionsFromFile['isMultitest']) return; | 414 if (optionsFromFile['isMultitest']) return; |
| 363 bool isWebTest = optionsFromFile['containsDomImport']; | 415 bool isWebTest = optionsFromFile['containsDomImport']; |
| 364 bool isLibraryDefinition = optionsFromFile['isLibraryDefinition']; | 416 bool isLibraryDefinition = optionsFromFile['isLibraryDefinition']; |
| 365 if (!isLibraryDefinition && optionsFromFile['containsSourceOrImport']) { | 417 if (!isLibraryDefinition && optionsFromFile['containsSourceOrImport']) { |
| 366 print('Warning for $filename: Browser tests require #library ' + | 418 print('Warning for $filename: Browser tests require #library ' + |
| (...skipping 146 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 513 optionsFromFile['isNegative']); | 565 optionsFromFile['isNegative']); |
| 514 doTest(testCase); | 566 doTest(testCase); |
| 515 } | 567 } |
| 516 } | 568 } |
| 517 | 569 |
| 518 bool get requiresCleanTemporaryDirectory() => | 570 bool get requiresCleanTemporaryDirectory() => |
| 519 configuration['component'] == 'dartc' || | 571 configuration['component'] == 'dartc' || |
| 520 configuration['component'] == 'chromium'; | 572 configuration['component'] == 'chromium'; |
| 521 | 573 |
| 522 /** | 574 /** |
| 523 * Create a directory for the generated test. Drop the path to the | 575 * Create a directory for the generated test. If a Dart language test |
| 524 * dart checkout and the final ".dart" from the test path, and replace | 576 * needs to be run in a browser, the Dart test needs to be embedded in |
| 525 * all path separators with underscores. | 577 * an HTML page, with a testing framework based on scripting and DOM events. |
| 578 * These scripts and pages are written to a generated_test directory, | |
| 579 * usually inside the build directory of the checkout. | |
| 580 * | |
| 581 * Some tests, such as those using the dartc compiler, need to be run | |
| 582 * with an empty directory as the compiler's work directory. These | |
| 583 * tests are copied to a subdirectory of a system-provided temporary | |
| 584 * directory, which is deleted at the end of the test run unless the | |
| 585 * --keep-temporary-files flag is given. | |
| 586 * | |
| 587 * Those tests which are already HTML web applications (web tests), with | |
| 588 * resources including CSS files and HTML files, need to be compiled into | |
| 589 * a work directory where the relative URLS to the resources work. | |
| 590 * We use a subdirectory of the build directory that is the same number | |
| 591 * of levels down in the checkout as the original path of the web test. | |
| 526 */ | 592 */ |
| 527 Directory createOutputDirectory(String testPath, String optionsName) { | 593 Directory createOutputDirectory(String testPath, String optionsName) { |
| 528 String testUniqueName = | 594 String testUniqueName = |
| 529 testPath.substring(dartDir.length + 1, testPath.length - 5); | 595 testPath.substring(dartDir.length + 1, testPath.length - 5); |
| 530 testUniqueName = testUniqueName.replaceAll('/', '_'); | 596 testUniqueName = testUniqueName.replaceAll('/', '_'); |
| 531 testUniqueName += '-$optionsName'; | 597 testUniqueName += '-$optionsName'; |
| 532 | 598 |
| 533 // Create '[build dir]/generated_tests/$component/$testUniqueName', | 599 // Create '[build dir]/generated_tests/$component/$testUniqueName', |
| 534 // including any intermediate directories that don't exist. | 600 // including any intermediate directories that don't exist. |
| 535 String debugMode = | 601 String debugMode = |
| (...skipping 527 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1063 * $noCrash tests are expected to be flaky but not crash | 1129 * $noCrash tests are expected to be flaky but not crash |
| 1064 * $pass tests are expected to pass | 1130 * $pass tests are expected to pass |
| 1065 * $failOk tests are expected to fail that we won't fix | 1131 * $failOk tests are expected to fail that we won't fix |
| 1066 * $fail tests are expected to fail that we should fix | 1132 * $fail tests are expected to fail that we should fix |
| 1067 * $crash tests are expected to crash that we should fix | 1133 * $crash tests are expected to crash that we should fix |
| 1068 * $timeout tests are allowed to timeout | 1134 * $timeout tests are allowed to timeout |
| 1069 """; | 1135 """; |
| 1070 print(report); | 1136 print(report); |
| 1071 } | 1137 } |
| 1072 } | 1138 } |
| OLD | NEW |