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 /** | 5 /** |
6 * Classes and methods for enumerating and preparing tests. | 6 * Classes and methods for enumerating and preparing tests. |
7 * | 7 * |
8 * This library includes: | 8 * This library includes: |
9 * | 9 * |
10 * - Creating tests by listing all the Dart files in certain directories, | 10 * - Creating tests by listing all the Dart files in certain directories, |
11 * and creating [TestCase]s for those files that meet the relevant criteria. | 11 * and creating [TestCase]s for those files that meet the relevant criteria. |
12 * - Preparing tests, including copying files and frameworks to temporary | 12 * - Preparing tests, including copying files and frameworks to temporary |
13 * directories, and computing the command line and arguments to be run. | 13 * directories, and computing the command line and arguments to be run. |
14 */ | 14 */ |
15 import 'dart:async'; | 15 library test_suite; |
16 import 'dart:io'; | 16 |
17 import 'dart:math'; | 17 import "dart:async"; |
| 18 import "dart:io"; |
| 19 import "dart:math"; |
| 20 import "drt_updater.dart"; |
| 21 import "html_test.dart" as htmlTest; |
| 22 import "http_server.dart"; |
| 23 import "path.dart"; |
| 24 import "multitest.dart"; |
| 25 import "expectation.dart"; |
| 26 import "expectation_set.dart"; |
| 27 import "summary_report.dart"; |
| 28 import "test_runner.dart"; |
| 29 import "utils.dart"; |
| 30 import "http_server.dart" show PREFIX_BUILDDIR, PREFIX_DARTDIR; |
| 31 |
| 32 import "compiler_configuration.dart" |
| 33 show CommandArtifact, CompilerConfiguration; |
| 34 |
| 35 import "runtime_configuration.dart" show RuntimeConfiguration; |
18 | 36 |
19 import 'browser_test.dart'; | 37 import 'browser_test.dart'; |
20 import 'compiler_configuration.dart'; | |
21 import 'configuration.dart'; | |
22 import 'drt_updater.dart'; | |
23 import 'expectation.dart'; | |
24 import 'expectation_set.dart'; | |
25 import 'html_test.dart' as html_test; | |
26 import 'http_server.dart'; | |
27 import 'multitest.dart'; | |
28 import 'path.dart'; | |
29 import 'summary_report.dart'; | |
30 import 'test_configurations.dart'; | |
31 import 'test_runner.dart'; | |
32 import 'utils.dart'; | |
33 | 38 |
34 RegExp multiHtmlTestGroupRegExp = new RegExp(r"\s*[^/]\s*group\('[^,']*"); | 39 RegExp multiHtmlTestGroupRegExp = new RegExp(r"\s*[^/]\s*group\('[^,']*"); |
35 RegExp multiHtmlTestRegExp = new RegExp(r"useHtmlIndividualConfiguration()"); | 40 RegExp multiHtmlTestRegExp = new RegExp(r"useHtmlIndividualConfiguration()"); |
36 // Require at least one non-space character before '//[/#]' | 41 // Require at least one non-space character before '//[/#]' |
37 RegExp multiTestRegExp = new RegExp(r"\S *" | 42 RegExp multiTestRegExp = new RegExp(r"\S *" |
38 r"//[#/] \w+:(.*)"); | 43 r"//[#/] \w+:(.*)"); |
39 RegExp dartExtension = new RegExp(r'\.dart$'); | 44 RegExp dartExtension = new RegExp(r'\.dart$'); |
40 | 45 |
41 /** | 46 /** |
42 * A simple function that tests [arg] and returns `true` or `false`. | 47 * A simple function that tests [arg] and returns `true` or `false`. |
(...skipping 36 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
79 /** | 84 /** |
80 * Wait for [task] to complete (assuming this barrier has not already been | 85 * Wait for [task] to complete (assuming this barrier has not already been |
81 * marked as completed, otherwise you'll get an exception indicating that a | 86 * marked as completed, otherwise you'll get an exception indicating that a |
82 * future has already been completed). | 87 * future has already been completed). |
83 */ | 88 */ |
84 void add(Future task) { | 89 void add(Future task) { |
85 if (_pending == _FINISHED) { | 90 if (_pending == _FINISHED) { |
86 throw new Exception("FutureFutureAlreadyCompleteException"); | 91 throw new Exception("FutureFutureAlreadyCompleteException"); |
87 } | 92 } |
88 _pending++; | 93 _pending++; |
89 var handledTaskFuture = task.catchError((e, StackTrace s) { | 94 var handledTaskFuture = task.catchError((e) { |
90 if (!wasCompleted) { | 95 if (!wasCompleted) { |
91 _completer.completeError(e, s); | 96 _completer.completeError(e); |
92 wasCompleted = true; | 97 wasCompleted = true; |
93 } | 98 } |
94 }).then((_) { | 99 }).then((_) { |
95 _pending--; | 100 _pending--; |
96 if (_pending == 0) { | 101 if (_pending == 0) { |
97 _pending = _FINISHED; | 102 _pending = _FINISHED; |
98 if (!wasCompleted) { | 103 if (!wasCompleted) { |
99 _completer.complete(futures); | 104 _completer.complete(futures); |
100 wasCompleted = true; | 105 wasCompleted = true; |
101 } | 106 } |
102 } | 107 } |
103 }); | 108 }); |
104 futures.add(handledTaskFuture); | 109 futures.add(handledTaskFuture); |
105 } | 110 } |
106 | 111 |
107 Future<List> get future => _completer.future; | 112 Future<List> get future => _completer.future; |
108 } | 113 } |
109 | 114 |
110 /** | 115 /** |
111 * A TestSuite represents a collection of tests. It creates a [TestCase] | 116 * A TestSuite represents a collection of tests. It creates a [TestCase] |
112 * object for each test to be run, and passes the test cases to a callback. | 117 * object for each test to be run, and passes the test cases to a callback. |
113 * | 118 * |
114 * Most TestSuites represent a directory or directory tree containing tests, | 119 * Most TestSuites represent a directory or directory tree containing tests, |
115 * and a status file containing the expected results when these tests are run. | 120 * and a status file containing the expected results when these tests are run. |
116 */ | 121 */ |
117 abstract class TestSuite { | 122 abstract class TestSuite { |
118 final Configuration configuration; | 123 final Map<String, dynamic> configuration; |
119 final String suiteName; | 124 final String suiteName; |
120 // This function is set by subclasses before enqueueing starts. | 125 // This function is set by subclasses before enqueueing starts. |
121 Function doTest; | 126 Function doTest; |
122 Map<String, String> _environmentOverrides; | 127 Map<String, String> _environmentOverrides; |
| 128 RuntimeConfiguration runtimeConfiguration; |
123 | 129 |
124 TestSuite(this.configuration, this.suiteName) { | 130 TestSuite(this.configuration, this.suiteName) { |
125 _environmentOverrides = { | 131 TestUtils.buildDir(configuration); // Sets configuration_directory. |
126 'DART_CONFIGURATION': configuration.configurationDirectory | 132 if (configuration['configuration_directory'] != null) { |
127 }; | 133 _environmentOverrides = { |
| 134 'DART_CONFIGURATION': configuration['configuration_directory'] as String |
| 135 }; |
| 136 } |
| 137 runtimeConfiguration = new RuntimeConfiguration(configuration); |
128 } | 138 } |
129 | 139 |
130 Map<String, String> get environmentOverrides => _environmentOverrides; | 140 Map<String, String> get environmentOverrides => _environmentOverrides; |
131 | 141 |
132 /** | 142 /** |
133 * Whether or not binaries should be found in the root build directory or | 143 * Whether or not binaries should be found in the root build directory or |
134 * in the built SDK. | 144 * in the built SDK. |
135 */ | 145 */ |
136 bool get useSdk { | 146 bool get useSdk { |
137 // The pub suite always uses the SDK. | 147 // The pub suite always uses the SDK. |
138 // TODO(rnystrom): Eventually, all test suites should run out of the SDK | 148 // TODO(rnystrom): Eventually, all test suites should run out of the SDK |
139 // and this check should go away. | 149 // and this check should go away. |
140 // TODO(ahe): This check is broken for several reasons: | 150 // TODO(ahe): This check is broken for several reasons: |
141 // First, it is not true that all tests should be running out of the | 151 // First, it is not true that all tests should be running out of the |
142 // SDK. It is absolutely critical to VM development that you can test the | 152 // SDK. It is absolutely critical to VM development that you can test the |
143 // VM without building the SDK. | 153 // VM without building the SDK. |
144 // Second, it is convenient for dart2js developers to run tests without | 154 // Second, it is convenient for dart2js developers to run tests without |
145 // rebuilding the SDK, and similarly, it should be convenient for pub | 155 // rebuilding the SDK, and similarly, it should be convenient for pub |
146 // developers. | 156 // developers. |
147 // Third, even if pub can only run from the SDK directory, this is the | 157 // Third, even if pub can only run from the SDK directory, this is the |
148 // wrong place to work around that problem. Instead, test_options.dart | 158 // wrong place to work around that problem. Instead, test_options.dart |
149 // should have been modified so that configuration['use_sdk'] is always | 159 // should have been modified so that configuration['use_sdk'] is always |
150 // true when testing pub. Attempting to override the value here is brittle | 160 // true when testing pub. Attempting to override the value here is brittle |
151 // because we read configuration['use_sdk'] directly in many places without | 161 // because we read configuration['use_sdk'] directly in many places without |
152 // using this getter. | 162 // using this getter. |
153 if (suiteName == 'pub') return true; | 163 if (suiteName == 'pub') return true; |
154 | 164 |
155 return configuration.useSdk; | 165 return configuration['use_sdk'] as bool; |
156 } | 166 } |
157 | 167 |
158 /** | 168 /** |
159 * The output directory for this suite's configuration. | 169 * The output directory for this suite's configuration. |
160 */ | 170 */ |
161 String get buildDir => configuration.buildDirectory; | 171 String get buildDir => TestUtils.buildDir(configuration); |
162 | 172 |
163 /** | 173 /** |
164 * The path to the compiler for this suite's configuration. Returns `null` if | 174 * The path to the compiler for this suite's configuration. Returns `null` if |
165 * no compiler should be used. | 175 * no compiler should be used. |
166 */ | 176 */ |
167 String get compilerPath { | 177 String get compilerPath { |
168 var compilerConfiguration = configuration.compilerConfiguration; | 178 var compilerConfiguration = new CompilerConfiguration(configuration); |
169 if (!compilerConfiguration.hasCompiler) return null; | 179 if (!compilerConfiguration.hasCompiler) return null; |
170 var name = compilerConfiguration.computeCompilerPath(buildDir); | 180 var name = compilerConfiguration.computeCompilerPath(buildDir); |
171 // TODO(ahe): Only validate this once, in test_options.dart. | 181 // TODO(ahe): Only validate this once, in test_options.dart. |
172 TestUtils.ensureExists(name, configuration); | 182 TestUtils.ensureExists(name, configuration); |
173 return name; | 183 return name; |
174 } | 184 } |
175 | 185 |
176 String get pubPath { | 186 String get pubPath { |
177 var prefix = 'sdk/bin/'; | 187 var prefix = 'sdk/bin/'; |
178 if (configuration.useSdk) { | 188 if (configuration['use_sdk'] as bool) { |
179 prefix = '$buildDir/dart-sdk/bin/'; | 189 prefix = '$buildDir/dart-sdk/bin/'; |
180 } | 190 } |
181 var suffix = getExecutableSuffix('pub'); | 191 var suffix = getExecutableSuffix('pub'); |
182 var name = '${prefix}pub$suffix'; | 192 var name = '${prefix}pub$suffix'; |
183 TestUtils.ensureExists(name, configuration); | 193 TestUtils.ensureExists(name, configuration); |
184 return name; | 194 return name; |
185 } | 195 } |
186 | 196 |
187 /// Returns the name of the Dart VM executable. | 197 /// Returns the name of the Dart VM executable. |
188 String get dartVmBinaryFileName { | 198 String get dartVmBinaryFileName { |
189 // Controlled by user with the option "--dart". | 199 // Controlled by user with the option "--dart". |
190 var dartExecutable = configuration.dartPath; | 200 var dartExecutable = configuration['dart'] as String; |
191 | 201 |
192 if (dartExecutable == null) { | 202 if (dartExecutable == '') { |
193 var suffix = executableBinarySuffix; | 203 var suffix = executableBinarySuffix; |
194 dartExecutable = useSdk | 204 dartExecutable = useSdk |
195 ? '$buildDir/dart-sdk/bin/dart$suffix' | 205 ? '$buildDir/dart-sdk/bin/dart$suffix' |
196 : '$buildDir/dart$suffix'; | 206 : '$buildDir/dart$suffix'; |
197 } | 207 } |
198 | 208 |
199 TestUtils.ensureExists(dartExecutable, configuration); | 209 TestUtils.ensureExists(dartExecutable, configuration); |
200 return dartExecutable; | 210 return dartExecutable; |
201 } | 211 } |
202 | 212 |
203 /// Returns the name of the flutter engine executable. | 213 /// Returns the name of the flutter engine executable. |
204 String get flutterEngineBinaryFileName { | 214 String get flutterEngineBinaryFileName { |
205 // Controlled by user with the option "--flutter". | 215 // Controlled by user with the option "--flutter". |
206 var flutterExecutable = configuration.flutterPath; | 216 var flutterExecutable = configuration['flutter'] as String; |
207 TestUtils.ensureExists(flutterExecutable, configuration); | 217 TestUtils.ensureExists(flutterExecutable, configuration); |
208 return flutterExecutable; | 218 return flutterExecutable; |
209 } | 219 } |
210 | 220 |
211 String get dartPrecompiledBinaryFileName { | 221 String get dartPrecompiledBinaryFileName { |
212 // Controlled by user with the option "--dart_precompiled". | 222 // Controlled by user with the option "--dart_precompiled". |
213 var dartExecutable = configuration.dartPrecompiledPath; | 223 var dartExecutable = configuration['dart_precompiled'] as String; |
214 | 224 |
215 if (dartExecutable == null || dartExecutable == '') { | 225 if (dartExecutable == null || dartExecutable == '') { |
216 var suffix = executableBinarySuffix; | 226 var suffix = executableBinarySuffix; |
217 dartExecutable = '$buildDir/dart_precompiled_runtime$suffix'; | 227 dartExecutable = '$buildDir/dart_precompiled_runtime$suffix'; |
218 } | 228 } |
219 | 229 |
220 TestUtils.ensureExists(dartExecutable, configuration); | 230 TestUtils.ensureExists(dartExecutable, configuration); |
221 return dartExecutable; | 231 return dartExecutable; |
222 } | 232 } |
223 | 233 |
(...skipping 51 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
275 [VoidFunction onDone]); | 285 [VoidFunction onDone]); |
276 | 286 |
277 // This function will be called for every TestCase of this test suite. | 287 // This function will be called for every TestCase of this test suite. |
278 // It will | 288 // It will |
279 // - handle sharding | 289 // - handle sharding |
280 // - update SummaryReport | 290 // - update SummaryReport |
281 // - handle SKIP/SKIP_BY_DESIGN markers | 291 // - handle SKIP/SKIP_BY_DESIGN markers |
282 // - test if the selector matches | 292 // - test if the selector matches |
283 // and will enqueue the test (if necessary). | 293 // and will enqueue the test (if necessary). |
284 void enqueueNewTestCase(TestCase testCase) { | 294 void enqueueNewTestCase(TestCase testCase) { |
285 if (testCase.isNegative && | 295 if (testCase.isNegative && runtimeConfiguration.shouldSkipNegativeTests) { |
286 configuration.runtimeConfiguration.shouldSkipNegativeTests) { | |
287 return; | 296 return; |
288 } | 297 } |
289 var expectations = testCase.expectedOutcomes; | 298 var expectations = testCase.expectedOutcomes; |
290 | 299 |
291 // Handle sharding based on the original test path (i.e. all multitests | 300 // Handle sharding based on the original test path (i.e. all multitests |
292 // of a given original test belong to the same shard) | 301 // of a given original test belong to the same shard) |
293 if (configuration.shardCount > 1 && | 302 var shards = configuration['shards'] as int; |
294 testCase.hash % configuration.shardCount != configuration.shard - 1) { | 303 if (shards > 1 && |
| 304 testCase.hash % shards != (configuration['shard'] as int) - 1) { |
295 return; | 305 return; |
296 } | 306 } |
297 | |
298 // Test if the selector includes this test. | 307 // Test if the selector includes this test. |
299 var pattern = configuration.selectors[suiteName]; | 308 var pattern = configuration['selectors'][suiteName] as RegExp; |
300 if (!pattern.hasMatch(testCase.displayName)) { | 309 if (!pattern.hasMatch(testCase.displayName)) { |
301 return; | 310 return; |
302 } | 311 } |
303 | 312 |
304 if (configuration.hotReload || configuration.hotReloadRollback) { | 313 if ((configuration['hot_reload'] as bool) || |
| 314 (configuration['hot_reload_rollback'] as bool)) { |
305 // Handle reload special cases. | 315 // Handle reload special cases. |
306 if (expectations.contains(Expectation.compileTimeError) || | 316 if (expectations.contains(Expectation.compileTimeError) || |
307 testCase.hasCompileError || | 317 testCase.hasCompileError || |
308 testCase.expectCompileError) { | 318 testCase.expectCompileError) { |
309 // Running a test that expects a compilation error with hot reloading | 319 // Running a test that expects a compilation error with hot reloading |
310 // is redundant with a regular run of the test. | 320 // is redundant with a regular run of the test. |
311 return; | 321 return; |
312 } | 322 } |
313 } | 323 } |
314 | 324 |
315 // Update Summary report | 325 // Update Summary report |
316 if (configuration.printReport) { | 326 if (configuration['report'] as bool) { |
317 if (testCase.expectCompileError && | 327 if (testCase.expectCompileError && |
318 configuration.runtime.isBrowser && | 328 TestUtils.isBrowserRuntime(configuration['runtime'] as String) && |
319 configuration.compilerConfiguration.hasCompiler) { | 329 new CompilerConfiguration(configuration).hasCompiler) { |
320 summaryReport.addCompileErrorSkipTest(); | 330 summaryReport.addCompileErrorSkipTest(); |
321 return; | 331 return; |
322 } else { | 332 } else { |
323 summaryReport.add(testCase); | 333 summaryReport.add(testCase); |
324 } | 334 } |
325 } | 335 } |
326 | 336 |
327 // Handle skipped tests | 337 // Handle skipped tests |
328 if (expectations.contains(Expectation.skip) || | 338 if (expectations.contains(Expectation.skip) || |
329 expectations.contains(Expectation.skipByDesign) || | 339 expectations.contains(Expectation.skipByDesign) || |
(...skipping 42 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
372 testName = concat(testName, multitestName); | 382 testName = concat(testName, multitestName); |
373 return testName; | 383 return testName; |
374 } | 384 } |
375 | 385 |
376 /** | 386 /** |
377 * Create a directories for generated assets (tests, html files, | 387 * Create a directories for generated assets (tests, html files, |
378 * pubspec checkouts ...). | 388 * pubspec checkouts ...). |
379 */ | 389 */ |
380 | 390 |
381 String createOutputDirectory(Path testPath, String optionsName) { | 391 String createOutputDirectory(Path testPath, String optionsName) { |
382 var checked = configuration.isChecked ? '-checked' : ''; | 392 var checked = configuration['checked'] as bool ? '-checked' : ''; |
383 var strong = configuration.isStrong ? '-strong' : ''; | 393 var strong = configuration['strong'] as bool ? '-strong' : ''; |
384 var minified = configuration.isMinified ? '-minified' : ''; | 394 var minified = configuration['minified'] as bool ? '-minified' : ''; |
385 var sdk = configuration.useSdk ? '-sdk' : ''; | 395 var sdk = configuration['use_sdk'] as bool ? '-sdk' : ''; |
386 var dirName = "${configuration.compiler.name}-${configuration.runtime.name}" | 396 var dirName = "${configuration['compiler']}-${configuration['runtime']}" |
387 "$checked$strong$minified$sdk"; | 397 "$checked$strong$minified$sdk"; |
388 return createGeneratedTestDirectoryHelper( | 398 return createGeneratedTestDirectoryHelper( |
389 "tests", dirName, testPath, optionsName); | 399 "tests", dirName, testPath, optionsName); |
390 } | 400 } |
391 | 401 |
392 String createCompilationOutputDirectory(Path testPath) { | 402 String createCompilationOutputDirectory(Path testPath) { |
393 var checked = configuration.isChecked ? '-checked' : ''; | 403 var checked = configuration['checked'] as bool ? '-checked' : ''; |
394 var strong = configuration.isStrong ? '-strong' : ''; | 404 var strong = configuration['strong'] as bool ? '-strong' : ''; |
395 var minified = configuration.isMinified ? '-minified' : ''; | 405 var minified = configuration['minified'] as bool ? '-minified' : ''; |
396 var csp = configuration.isCsp ? '-csp' : ''; | 406 var csp = configuration['csp'] as bool ? '-csp' : ''; |
397 var sdk = configuration.useSdk ? '-sdk' : ''; | 407 var sdk = configuration['use_sdk'] as bool ? '-sdk' : ''; |
398 var dirName = "${configuration.compiler.name}" | 408 var dirName = "${configuration['compiler']}" |
399 "$checked$strong$minified$csp$sdk"; | 409 "$checked$strong$minified$csp$sdk"; |
400 return createGeneratedTestDirectoryHelper( | 410 return createGeneratedTestDirectoryHelper( |
401 "compilations", dirName, testPath, ""); | 411 "compilations", dirName, testPath, ""); |
402 } | 412 } |
403 | 413 |
404 String createPubspecCheckoutDirectory(Path directoryOfPubspecYaml) { | 414 String createPubspecCheckoutDirectory(Path directoryOfPubspecYaml) { |
405 var sdk = configuration.useSdk ? 'sdk' : ''; | 415 var sdk = configuration['use_sdk'] as bool ? 'sdk' : ''; |
406 return createGeneratedTestDirectoryHelper( | 416 return createGeneratedTestDirectoryHelper( |
407 "pubspec_checkouts", sdk, directoryOfPubspecYaml, ""); | 417 "pubspec_checkouts", sdk, directoryOfPubspecYaml, ""); |
408 } | 418 } |
409 | 419 |
410 String createPubPackageBuildsDirectory(Path directoryOfPubspecYaml) { | 420 String createPubPackageBuildsDirectory(Path directoryOfPubspecYaml) { |
411 return createGeneratedTestDirectoryHelper( | 421 return createGeneratedTestDirectoryHelper( |
412 "pub_package_builds", 'public_packages', directoryOfPubspecYaml, ""); | 422 "pub_package_builds", 'public_packages', directoryOfPubspecYaml, ""); |
413 } | 423 } |
414 } | 424 } |
415 | 425 |
(...skipping 18 matching lines...) Expand all Loading... |
434 * The executable lists its tests when run with the --list command line flag. | 444 * The executable lists its tests when run with the --list command line flag. |
435 * Individual tests are run by specifying them on the command line. | 445 * Individual tests are run by specifying them on the command line. |
436 */ | 446 */ |
437 class CCTestSuite extends TestSuite { | 447 class CCTestSuite extends TestSuite { |
438 final String testPrefix; | 448 final String testPrefix; |
439 String targetRunnerPath; | 449 String targetRunnerPath; |
440 String hostRunnerPath; | 450 String hostRunnerPath; |
441 final String dartDir; | 451 final String dartDir; |
442 List<String> statusFilePaths; | 452 List<String> statusFilePaths; |
443 | 453 |
444 CCTestSuite(Configuration configuration, String suiteName, String runnerName, | 454 CCTestSuite(Map<String, dynamic> configuration, String suiteName, |
445 this.statusFilePaths, | 455 String runnerName, this.statusFilePaths, |
446 {this.testPrefix: ''}) | 456 {this.testPrefix: ''}) |
447 : dartDir = TestUtils.dartDir.toNativePath(), | 457 : dartDir = TestUtils.dartDir.toNativePath(), |
448 super(configuration, suiteName) { | 458 super(configuration, suiteName) { |
449 // For running the tests we use the given '$runnerName' binary | 459 // For running the tests we use the given '$runnerName' binary |
450 targetRunnerPath = '$buildDir/$runnerName'; | 460 targetRunnerPath = '$buildDir/$runnerName'; |
451 | 461 |
452 // For listing the tests we use the '$runnerName.host' binary if it exists | 462 // For listing the tests we use the '$runnerName.host' binary if it exists |
453 // and use '$runnerName' if it doesn't. | 463 // and use '$runnerName' if it doesn't. |
454 var binarySuffix = Platform.operatingSystem == 'windows' ? '.exe' : ''; | 464 var binarySuffix = Platform.operatingSystem == 'windows' ? '.exe' : ''; |
455 var hostBinary = '$targetRunnerPath.host$binarySuffix'; | 465 var hostBinary = '$targetRunnerPath.host$binarySuffix'; |
456 if (new File(hostBinary).existsSync()) { | 466 if (new File(hostBinary).existsSync()) { |
457 hostRunnerPath = hostBinary; | 467 hostRunnerPath = hostBinary; |
458 } else { | 468 } else { |
459 hostRunnerPath = targetRunnerPath; | 469 hostRunnerPath = targetRunnerPath; |
460 } | 470 } |
461 } | 471 } |
462 | 472 |
463 void testNameHandler(ExpectationSet testExpectations, String testName) { | 473 void testNameHandler(ExpectationSet testExpectations, String testName) { |
464 // Only run the tests that match the pattern. Use the name | 474 // Only run the tests that match the pattern. Use the name |
465 // "suiteName/testName" for cc tests. | 475 // "suiteName/testName" for cc tests. |
466 String constructedName = '$suiteName/$testPrefix$testName'; | 476 String constructedName = '$suiteName/$testPrefix$testName'; |
467 | 477 |
468 var expectations = testExpectations.expectations('$testPrefix$testName'); | 478 var expectations = testExpectations.expectations('$testPrefix$testName'); |
469 | 479 |
470 var args = configuration.standardOptions.toList(); | 480 var args = TestUtils.standardOptions(configuration); |
471 if (configuration.compilerConfiguration.useDfe) { | 481 var compilerConfiguration = new CompilerConfiguration(configuration); |
| 482 if (compilerConfiguration.useDfe) { |
472 args.add('--use-dart-frontend'); | 483 args.add('--use-dart-frontend'); |
473 // '--dfe' has to be the first argument for run_vm_test to pick it up. | 484 // '--dfe' has to be the first argument for run_vm_test to pick it up. |
474 args.insert(0, '--dfe=$buildDir/gen/kernel-service.dart.snapshot'); | 485 args.insert(0, '--dfe=$buildDir/gen/kernel-service.dart.snapshot'); |
475 } | 486 } |
476 | |
477 args.add(testName); | 487 args.add(testName); |
478 | 488 |
479 var command = CommandBuilder.instance.getProcessCommand( | 489 var command = CommandBuilder.instance.getProcessCommand( |
480 'run_vm_unittest', targetRunnerPath, args, environmentOverrides); | 490 'run_vm_unittest', targetRunnerPath, args, environmentOverrides); |
481 enqueueNewTestCase( | 491 enqueueNewTestCase( |
482 new TestCase(constructedName, [command], configuration, expectations)); | 492 new TestCase(constructedName, [command], configuration, expectations)); |
483 } | 493 } |
484 | 494 |
485 Future<Null> forEachTest(Function onTest, Map testCache, | 495 Future<Null> forEachTest(Function onTest, Map testCache, |
486 [VoidFunction onDone]) async { | 496 [VoidFunction onDone]) async { |
(...skipping 14 matching lines...) Expand all Loading... |
501 } catch (error) { | 511 } catch (error) { |
502 print("Fatal error occured: $error"); | 512 print("Fatal error occured: $error"); |
503 exit(1); | 513 exit(1); |
504 } | 514 } |
505 } | 515 } |
506 } | 516 } |
507 | 517 |
508 class TestInformation { | 518 class TestInformation { |
509 Path filePath; | 519 Path filePath; |
510 Path originTestPath; | 520 Path originTestPath; |
511 Map<String, dynamic> optionsFromFile; | 521 Map optionsFromFile; |
512 bool hasCompileError; | 522 bool hasCompileError; |
513 bool hasRuntimeError; | 523 bool hasRuntimeError; |
514 bool isNegativeIfChecked; | 524 bool isNegativeIfChecked; |
515 bool hasCompileErrorIfChecked; | 525 bool hasCompileErrorIfChecked; |
516 bool hasStaticWarning; | 526 bool hasStaticWarning; |
517 String multitestKey; | 527 String multitestKey; |
518 | 528 |
519 TestInformation( | 529 TestInformation( |
520 this.filePath, | 530 this.filePath, |
521 this.originTestPath, | 531 this.originTestPath, |
(...skipping 32 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
554 final Path suiteDir; | 564 final Path suiteDir; |
555 final List<String> statusFilePaths; | 565 final List<String> statusFilePaths; |
556 ExpectationSet testExpectations; | 566 ExpectationSet testExpectations; |
557 List<TestInformation> cachedTests; | 567 List<TestInformation> cachedTests; |
558 final Path dartDir; | 568 final Path dartDir; |
559 Predicate<String> isTestFilePredicate; | 569 Predicate<String> isTestFilePredicate; |
560 final bool listRecursively; | 570 final bool listRecursively; |
561 final List<String> extraVmOptions; | 571 final List<String> extraVmOptions; |
562 List<Uri> _dart2JsBootstrapDependencies; | 572 List<Uri> _dart2JsBootstrapDependencies; |
563 | 573 |
564 StandardTestSuite(Configuration configuration, String suiteName, | 574 StandardTestSuite(Map<String, dynamic> configuration, String suiteName, |
565 Path suiteDirectory, this.statusFilePaths, | 575 Path suiteDirectory, this.statusFilePaths, |
566 {this.isTestFilePredicate, bool recursive: false}) | 576 {this.isTestFilePredicate, bool recursive: false}) |
567 : dartDir = TestUtils.dartDir, | 577 : dartDir = TestUtils.dartDir, |
568 listRecursively = recursive, | 578 listRecursively = recursive, |
569 suiteDir = TestUtils.dartDir.join(suiteDirectory), | 579 suiteDir = TestUtils.dartDir.join(suiteDirectory), |
570 extraVmOptions = configuration.vmOptions, | 580 extraVmOptions = TestUtils.getExtraVmOptions(configuration), |
571 super(configuration, suiteName) { | 581 super(configuration, suiteName) { |
572 if (!useSdk) { | 582 if (!useSdk) { |
573 _dart2JsBootstrapDependencies = []; | 583 _dart2JsBootstrapDependencies = []; |
574 } else { | 584 } else { |
575 var snapshotPath = TestUtils | 585 var snapshotPath = TestUtils |
576 .absolutePath( | 586 .absolutePath( |
577 new Path(buildDir).join(new Path('dart-sdk/bin/snapshots/' | 587 new Path(buildDir).join(new Path('dart-sdk/bin/snapshots/' |
578 'utils_wrapper.dart.snapshot'))) | 588 'utils_wrapper.dart.snapshot'))) |
579 .toString(); | 589 .toString(); |
580 _dart2JsBootstrapDependencies = [ | 590 _dart2JsBootstrapDependencies = [ |
(...skipping 23 matching lines...) Expand all Loading... |
604 * | 614 * |
605 * If you follow that convention, then you can construct one of these like: | 615 * If you follow that convention, then you can construct one of these like: |
606 * | 616 * |
607 * new StandardTestSuite.forDirectory(configuration, 'path/to/mytestsuite'); | 617 * new StandardTestSuite.forDirectory(configuration, 'path/to/mytestsuite'); |
608 * | 618 * |
609 * instead of having to create a custom [StandardTestSuite] subclass. In | 619 * instead of having to create a custom [StandardTestSuite] subclass. In |
610 * particular, if you add 'path/to/mytestsuite' to [TEST_SUITE_DIRECTORIES] | 620 * particular, if you add 'path/to/mytestsuite' to [TEST_SUITE_DIRECTORIES] |
611 * in test.dart, this will all be set up for you. | 621 * in test.dart, this will all be set up for you. |
612 */ | 622 */ |
613 factory StandardTestSuite.forDirectory( | 623 factory StandardTestSuite.forDirectory( |
614 Configuration configuration, Path directory) { | 624 Map<String, dynamic> configuration, Path directory) { |
615 var name = directory.filename; | 625 var name = directory.filename; |
616 var status_paths = [ | 626 var status_paths = [ |
617 '$directory/$name.status', | 627 '$directory/$name.status', |
618 '$directory/.status', | 628 '$directory/.status', |
619 '$directory/${name}_dart2js.status', | 629 '$directory/${name}_dart2js.status', |
620 '$directory/${name}_analyzer2.status', | 630 '$directory/${name}_analyzer2.status', |
621 '$directory/${name}_kernel.status' | 631 '$directory/${name}_kernel.status' |
622 ]; | 632 ]; |
623 | 633 |
624 return new StandardTestSuite(configuration, name, directory, status_paths, | 634 return new StandardTestSuite(configuration, name, directory, status_paths, |
(...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
663 doTest = null; | 673 doTest = null; |
664 if (onDone != null) onDone(); | 674 if (onDone != null) onDone(); |
665 } | 675 } |
666 | 676 |
667 /** | 677 /** |
668 * If Content shell/Dartium is required, and not yet updated, waits for | 678 * If Content shell/Dartium is required, and not yet updated, waits for |
669 * the update then completes. Otherwise completes immediately. | 679 * the update then completes. Otherwise completes immediately. |
670 */ | 680 */ |
671 Future updateDartium() { | 681 Future updateDartium() { |
672 var completer = new Completer(); | 682 var completer = new Completer(); |
673 var updater = runtimeUpdater(configuration.runtime, configuration.drtPath, | 683 var updater = runtimeUpdater(configuration); |
674 configuration.dartiumPath); | |
675 if (updater == null || updater.updated) { | 684 if (updater == null || updater.updated) { |
676 return new Future.value(null); | 685 return new Future.value(null); |
677 } | 686 } |
678 | 687 |
679 assert(updater.isActive); | 688 assert(updater.isActive); |
680 updater.onUpdated.add(() => completer.complete(null)); | 689 updater.onUpdated.add(() => completer.complete(null)); |
681 | 690 |
682 return completer.future; | 691 return completer.future; |
683 } | 692 } |
684 | 693 |
(...skipping 30 matching lines...) Expand all Loading... |
715 .list(recursive: listRecursively) | 724 .list(recursive: listRecursively) |
716 .where((fse) => fse is File) | 725 .where((fse) => fse is File) |
717 .forEach((FileSystemEntity entity) { | 726 .forEach((FileSystemEntity entity) { |
718 enqueueFile((entity as File).path, group); | 727 enqueueFile((entity as File).path, group); |
719 }); | 728 }); |
720 group.add(lister); | 729 group.add(lister); |
721 } | 730 } |
722 | 731 |
723 void enqueueFile(String filename, FutureGroup group) { | 732 void enqueueFile(String filename, FutureGroup group) { |
724 if (isHtmlTestFile(filename)) { | 733 if (isHtmlTestFile(filename)) { |
725 var info = html_test.getInformation(filename); | 734 var info = htmlTest.getInformation(filename); |
726 if (info == null) { | 735 if (info == null) { |
727 DebugLogger | 736 DebugLogger |
728 .error("HtmlTest $filename does not contain required annotations"); | 737 .error("HtmlTest $filename does not contain required annotations"); |
729 return; | 738 return; |
730 } | 739 } |
731 cachedTests.add(info); | 740 cachedTests.add(info); |
732 enqueueTestCaseFromTestInformation(info); | 741 enqueueTestCaseFromTestInformation(info); |
733 return; | 742 return; |
734 } | 743 } |
735 if (!isTestFile(filename)) return; | 744 if (!isTestFile(filename)) return; |
736 Path filePath = new Path(filename); | 745 Path filePath = new Path(filename); |
737 | 746 |
738 var optionsFromFile = readOptionsFromFile(filePath); | 747 var optionsFromFile = readOptionsFromFile(filePath); |
739 CreateTest createTestCase = makeTestCaseCreator(optionsFromFile); | 748 CreateTest createTestCase = makeTestCaseCreator(optionsFromFile); |
740 | 749 |
741 if (optionsFromFile['isMultitest'] as bool) { | 750 if (optionsFromFile['isMultitest'] as bool) { |
742 group.add(doMultitest(filePath, buildDir, suiteDir, createTestCase, | 751 group.add(doMultitest( |
743 configuration.hotReload || configuration.hotReloadRollback)); | 752 filePath, |
| 753 buildDir, |
| 754 suiteDir, |
| 755 createTestCase, |
| 756 ((configuration['hot_reload'] as bool) || |
| 757 (configuration['hot_reload_rollback'] as bool)))); |
744 } else { | 758 } else { |
745 createTestCase( | 759 createTestCase( |
746 filePath, | 760 filePath, |
747 filePath, | 761 filePath, |
748 optionsFromFile['hasCompileError'] as bool, | 762 optionsFromFile['hasCompileError'] as bool, |
749 optionsFromFile['hasRuntimeError'] as bool, | 763 optionsFromFile['hasRuntimeError'] as bool, |
750 hasStaticWarning: optionsFromFile['hasStaticWarning'] as bool); | 764 hasStaticWarning: optionsFromFile['hasStaticWarning'] as bool); |
751 } | 765 } |
752 } | 766 } |
753 | 767 |
(...skipping 29 matching lines...) Expand all Loading... |
783 var optionsFromFile = info.optionsFromFile; | 797 var optionsFromFile = info.optionsFromFile; |
784 | 798 |
785 // If this test is inside a package, we will check if there is a | 799 // If this test is inside a package, we will check if there is a |
786 // pubspec.yaml file and if so, create a custom package root for it. | 800 // pubspec.yaml file and if so, create a custom package root for it. |
787 List<Command> baseCommands = <Command>[]; | 801 List<Command> baseCommands = <Command>[]; |
788 Path packageRoot; | 802 Path packageRoot; |
789 Path packages; | 803 Path packages; |
790 | 804 |
791 if (optionsFromFile['packageRoot'] == null && | 805 if (optionsFromFile['packageRoot'] == null && |
792 optionsFromFile['packages'] == null) { | 806 optionsFromFile['packages'] == null) { |
793 if (configuration.packageRoot != null) { | 807 if (configuration['package_root'] != null) { |
794 packageRoot = new Path(configuration.packageRoot); | 808 packageRoot = new Path(configuration['package_root'] as String); |
795 optionsFromFile['packageRoot'] = packageRoot.toNativePath(); | 809 optionsFromFile['packageRoot'] = packageRoot.toNativePath(); |
796 } | 810 } |
797 if (configuration.packages != null) { | 811 if (configuration['packages'] != null) { |
798 Path packages = new Path(configuration.packages); | 812 Path packages = new Path(configuration['packages'] as String); |
799 optionsFromFile['packages'] = packages.toNativePath(); | 813 optionsFromFile['packages'] = packages.toNativePath(); |
800 } | 814 } |
801 } | 815 } |
802 if (configuration.compilerConfiguration.hasCompiler && | 816 if (new CompilerConfiguration(configuration).hasCompiler && |
803 expectCompileError(info)) { | 817 expectCompileError(info)) { |
804 // If a compile-time error is expected, and we're testing a | 818 // If a compile-time error is expected, and we're testing a |
805 // compiler, we never need to attempt to run the program (in a | 819 // compiler, we never need to attempt to run the program (in a |
806 // browser or otherwise). | 820 // browser or otherwise). |
807 enqueueStandardTest(baseCommands, info, testName, expectations); | 821 enqueueStandardTest(baseCommands, info, testName, expectations); |
808 } else if (configuration.runtime.isBrowser) { | 822 } else if (TestUtils.isBrowserRuntime(configuration['runtime'] as String)) { |
809 if (info.optionsFromFile['isMultiHtmlTest'] as bool) { | 823 if (info.optionsFromFile['isMultiHtmlTest'] as bool) { |
810 // A browser multi-test has multiple expectations for one test file. | 824 // A browser multi-test has multiple expectations for one test file. |
811 // Find all the different sub-test expecations for one entire test file. | 825 // Find all the different sub-test expecations for one entire test file. |
812 var subtestNames = info.optionsFromFile['subtestNames'] as List<String>; | 826 var subtestNames = info.optionsFromFile['subtestNames'] as List<String>; |
813 var multiHtmlTestExpectations = <String, Set<Expectation>>{}; | 827 var multiHtmlTestExpectations = <String, Set<Expectation>>{}; |
814 for (var name in subtestNames) { | 828 for (var name in subtestNames) { |
815 var fullTestName = '$testName/$name'; | 829 var fullTestName = '$testName/$name'; |
816 multiHtmlTestExpectations[fullTestName] = | 830 multiHtmlTestExpectations[fullTestName] = |
817 testExpectations.expectations(fullTestName); | 831 testExpectations.expectations(fullTestName); |
818 } | 832 } |
(...skipping 29 matching lines...) Expand all Loading... |
848 commands.addAll( | 862 commands.addAll( |
849 makeCommands(info, vmOptionsVariant, allVmOptions, commonArguments)); | 863 makeCommands(info, vmOptionsVariant, allVmOptions, commonArguments)); |
850 enqueueNewTestCase(new TestCase( | 864 enqueueNewTestCase(new TestCase( |
851 '$suiteName/$testName', commands, configuration, expectations, | 865 '$suiteName/$testName', commands, configuration, expectations, |
852 isNegative: isNegative(info), info: info)); | 866 isNegative: isNegative(info), info: info)); |
853 } | 867 } |
854 } | 868 } |
855 | 869 |
856 bool expectCompileError(TestInformation info) { | 870 bool expectCompileError(TestInformation info) { |
857 return info.hasCompileError || | 871 return info.hasCompileError || |
858 (configuration.isChecked && info.hasCompileErrorIfChecked); | 872 ((configuration['checked'] as bool) && info.hasCompileErrorIfChecked); |
859 } | 873 } |
860 | 874 |
861 bool isNegative(TestInformation info) { | 875 bool isNegative(TestInformation info) { |
862 bool negative = expectCompileError(info) || | 876 bool negative = expectCompileError(info) || |
863 (configuration.isChecked && info.isNegativeIfChecked); | 877 ((configuration['checked'] as bool) && info.isNegativeIfChecked); |
864 if (info.hasRuntimeError && hasRuntime) { | 878 if (info.hasRuntimeError && hasRuntime) { |
865 negative = true; | 879 negative = true; |
866 } | 880 } |
867 return negative; | 881 return negative; |
868 } | 882 } |
869 | 883 |
870 List<Command> makeCommands(TestInformation info, int vmOptionsVarient, | 884 List<Command> makeCommands(TestInformation info, int vmOptionsVarient, |
871 List<String> vmOptions, List<String> args) { | 885 List<String> vmOptions, List<String> args) { |
872 var commands = <Command>[]; | 886 var commands = <Command>[]; |
873 var compilerConfiguration = configuration.compilerConfiguration; | 887 var compilerConfiguration = new CompilerConfiguration(configuration); |
874 var sharedOptions = info.optionsFromFile['sharedOptions'] as List<String>; | 888 var sharedOptions = info.optionsFromFile['sharedOptions'] as List<String>; |
875 | 889 |
876 var compileTimeArguments = <String>[]; | 890 var compileTimeArguments = <String>[]; |
877 String tempDir; | 891 String tempDir; |
878 if (compilerConfiguration.hasCompiler) { | 892 if (compilerConfiguration.hasCompiler) { |
879 compileTimeArguments = compilerConfiguration.computeCompilerArguments( | 893 compileTimeArguments = compilerConfiguration.computeCompilerArguments( |
880 vmOptions, sharedOptions, args); | 894 vmOptions, sharedOptions, args); |
881 // Avoid doing this for analyzer. | 895 // Avoid doing this for analyzer. |
882 var path = info.filePath; | 896 var path = info.filePath; |
883 if (vmOptionsVarient != 0) { | 897 if (vmOptionsVarient != 0) { |
(...skipping 12 matching lines...) Expand all Loading... |
896 } | 910 } |
897 } | 911 } |
898 | 912 |
899 CommandArtifact compilationArtifact = | 913 CommandArtifact compilationArtifact = |
900 compilerConfiguration.computeCompilationArtifact( | 914 compilerConfiguration.computeCompilationArtifact( |
901 buildDir, | 915 buildDir, |
902 tempDir, | 916 tempDir, |
903 CommandBuilder.instance, | 917 CommandBuilder.instance, |
904 compileTimeArguments, | 918 compileTimeArguments, |
905 environmentOverrides); | 919 environmentOverrides); |
906 if (!configuration.skipCompilation) { | 920 if (!(configuration['skip-compilation'] as bool)) { |
907 commands.addAll(compilationArtifact.commands); | 921 commands.addAll(compilationArtifact.commands); |
908 } | 922 } |
909 | 923 |
910 if (expectCompileError(info) && compilerConfiguration.hasCompiler) { | 924 if (expectCompileError(info) && compilerConfiguration.hasCompiler) { |
911 // Do not attempt to run the compiled result. A compilation | 925 // Do not attempt to run the compiled result. A compilation |
912 // error should be reported by the compilation command. | 926 // error should be reported by the compilation command. |
913 return commands; | 927 return commands; |
914 } | 928 } |
915 | 929 |
916 List<String> runtimeArguments = | 930 List<String> runtimeArguments = |
917 compilerConfiguration.computeRuntimeArguments( | 931 compilerConfiguration.computeRuntimeArguments( |
918 configuration.runtimeConfiguration, | 932 runtimeConfiguration, |
919 buildDir, | 933 buildDir, |
920 info, | 934 info, |
921 vmOptions, | 935 vmOptions, |
922 sharedOptions, | 936 sharedOptions, |
923 args, | 937 args, |
924 compilationArtifact); | 938 compilationArtifact); |
925 | 939 |
926 return commands | 940 return commands |
927 ..addAll(configuration.runtimeConfiguration.computeRuntimeCommands( | 941 ..addAll(runtimeConfiguration.computeRuntimeCommands( |
928 this, | 942 this, |
929 CommandBuilder.instance, | 943 CommandBuilder.instance, |
930 compilationArtifact, | 944 compilationArtifact, |
931 runtimeArguments, | 945 runtimeArguments, |
932 environmentOverrides)); | 946 environmentOverrides)); |
933 } | 947 } |
934 | 948 |
935 CreateTest makeTestCaseCreator(Map<String, dynamic> optionsFromFile) { | 949 CreateTest makeTestCaseCreator(Map optionsFromFile) { |
936 return (Path filePath, Path originTestPath, bool hasCompileError, | 950 return (Path filePath, Path originTestPath, bool hasCompileError, |
937 bool hasRuntimeError, | 951 bool hasRuntimeError, |
938 {bool isNegativeIfChecked: false, | 952 {bool isNegativeIfChecked: false, |
939 bool hasCompileErrorIfChecked: false, | 953 bool hasCompileErrorIfChecked: false, |
940 bool hasStaticWarning: false, | 954 bool hasStaticWarning: false, |
941 String multitestKey}) { | 955 String multitestKey}) { |
942 // Cache the test information for each test case. | 956 // Cache the test information for each test case. |
943 var info = new TestInformation( | 957 var info = new TestInformation( |
944 filePath, | 958 filePath, |
945 originTestPath, | 959 originTestPath, |
(...skipping 13 matching lines...) Expand all Loading... |
959 * _createUrlPathFromFile takes a [file], which is either located in the dart | 973 * _createUrlPathFromFile takes a [file], which is either located in the dart |
960 * or in the build directory, and will return a String representing | 974 * or in the build directory, and will return a String representing |
961 * the relative path to either the dart or the build directory. | 975 * the relative path to either the dart or the build directory. |
962 * Thus, the returned [String] will be the path component of the URL | 976 * Thus, the returned [String] will be the path component of the URL |
963 * corresponding to [file] (the http server serves files relative to the | 977 * corresponding to [file] (the http server serves files relative to the |
964 * dart/build directories). | 978 * dart/build directories). |
965 */ | 979 */ |
966 String _createUrlPathFromFile(Path file) { | 980 String _createUrlPathFromFile(Path file) { |
967 file = TestUtils.absolutePath(file); | 981 file = TestUtils.absolutePath(file); |
968 | 982 |
969 var relativeBuildDir = new Path(configuration.buildDirectory); | 983 var relativeBuildDir = new Path(TestUtils.buildDir(configuration)); |
970 var buildDir = TestUtils.absolutePath(relativeBuildDir); | 984 var buildDir = TestUtils.absolutePath(relativeBuildDir); |
971 var dartDir = TestUtils.absolutePath(TestUtils.dartDir); | 985 var dartDir = TestUtils.absolutePath(TestUtils.dartDir); |
972 | 986 |
973 var fileString = file.toString(); | 987 var fileString = file.toString(); |
974 if (fileString.startsWith(buildDir.toString())) { | 988 if (fileString.startsWith(buildDir.toString())) { |
975 var fileRelativeToBuildDir = file.relativeTo(buildDir); | 989 var fileRelativeToBuildDir = file.relativeTo(buildDir); |
976 return "/$PREFIX_BUILDDIR/$fileRelativeToBuildDir"; | 990 return "/$PREFIX_BUILDDIR/$fileRelativeToBuildDir"; |
977 } else if (fileString.startsWith(dartDir.toString())) { | 991 } else if (fileString.startsWith(dartDir.toString())) { |
978 var fileRelativeToDartDir = file.relativeTo(dartDir); | 992 var fileRelativeToDartDir = file.relativeTo(dartDir); |
979 return "/$PREFIX_DARTDIR/$fileRelativeToDartDir"; | 993 return "/$PREFIX_DARTDIR/$fileRelativeToDartDir"; |
980 } | 994 } |
981 // Unreachable | 995 // Unreachable |
982 print("Cannot create URL for path $file. Not in build or dart directory."); | 996 print("Cannot create URL for path $file. Not in build or dart directory."); |
983 exit(1); | 997 exit(1); |
984 return null; | 998 return null; |
985 } | 999 } |
986 | 1000 |
987 Uri _getUriForBrowserTest(String pathComponent, String subtestName) { | 1001 Uri _getUriForBrowserTest(String pathComponent, String subtestName) { |
988 // Note: If we run test.py with the "--list" option, no http servers | 1002 // Note: If we run test.py with the "--list" option, no http servers |
989 // will be started. So we return a dummy url instead. | 1003 // will be started. So we return a dummy url instead. |
990 if (configuration.listTests) { | 1004 if (configuration['list'] as bool) { |
991 return Uri.parse('http://listing_the_tests_only'); | 1005 return Uri.parse('http://listing_the_tests_only'); |
992 } | 1006 } |
993 | 1007 assert(configuration.containsKey('_servers_')); |
994 var serverPort = configuration.servers.port; | 1008 var servers = configuration['_servers_'] as TestingServers; |
995 var crossOriginPort = configuration.servers.crossOriginPort; | 1009 var serverPort = servers.port; |
| 1010 var crossOriginPort = servers.crossOriginPort; |
996 var parameters = {'crossOriginPort': crossOriginPort.toString()}; | 1011 var parameters = {'crossOriginPort': crossOriginPort.toString()}; |
997 if (subtestName != null) { | 1012 if (subtestName != null) { |
998 parameters['group'] = subtestName; | 1013 parameters['group'] = subtestName; |
999 } | 1014 } |
1000 return new Uri( | 1015 return new Uri( |
1001 scheme: 'http', | 1016 scheme: 'http', |
1002 host: configuration.localIP, | 1017 host: configuration['local_ip'] as String, |
1003 port: serverPort, | 1018 port: serverPort, |
1004 path: pathComponent, | 1019 path: pathComponent, |
1005 queryParameters: parameters); | 1020 queryParameters: parameters); |
1006 } | 1021 } |
1007 | 1022 |
1008 void _createWrapperFile( | 1023 void _createWrapperFile( |
1009 String dartWrapperFilename, Path localDartLibraryFilename) { | 1024 String dartWrapperFilename, Path localDartLibraryFilename) { |
1010 File file = new File(dartWrapperFilename); | 1025 File file = new File(dartWrapperFilename); |
1011 RandomAccessFile dartWrapper = file.openSync(mode: FileMode.WRITE); | 1026 RandomAccessFile dartWrapper = file.openSync(mode: FileMode.WRITE); |
1012 | 1027 |
(...skipping 41 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1054 Path packageRoot, | 1069 Path packageRoot, |
1055 Path packages, | 1070 Path packages, |
1056 TestInformation info, | 1071 TestInformation info, |
1057 String testName, | 1072 String testName, |
1058 /* Set<Expectation> | Map<String, Set<Expectation>> */ expectations, | 1073 /* Set<Expectation> | Map<String, Set<Expectation>> */ expectations, |
1059 List<String> vmOptions, | 1074 List<String> vmOptions, |
1060 String tempDir) { | 1075 String tempDir) { |
1061 // TODO(Issue 14651): If we're on dartium, we need to pass [packageRoot] | 1076 // TODO(Issue 14651): If we're on dartium, we need to pass [packageRoot] |
1062 // on to the browser (it may be test specific). | 1077 // on to the browser (it may be test specific). |
1063 | 1078 |
1064 var filePath = info.filePath; | 1079 Path filePath = info.filePath; |
1065 var fileName = filePath.toString(); | 1080 String filename = filePath.toString(); |
1066 | 1081 |
1067 var optionsFromFile = info.optionsFromFile; | 1082 var compiler = configuration['compiler'] as String; |
| 1083 var runtime = configuration['runtime'] as String; |
| 1084 final Map optionsFromFile = info.optionsFromFile; |
1068 | 1085 |
1069 var compilationTempDir = createCompilationOutputDirectory(info.filePath); | 1086 final String compilationTempDir = |
| 1087 createCompilationOutputDirectory(info.filePath); |
1070 | 1088 |
1071 var dartWrapperFilename = '$tempDir/test.dart'; | 1089 String dartWrapperFilename = '$tempDir/test.dart'; |
1072 var compiledDartWrapperFilename = '$compilationTempDir/test.js'; | 1090 String compiledDartWrapperFilename = '$compilationTempDir/test.js'; |
1073 | 1091 |
1074 String content = null; | 1092 String content = null; |
1075 var dir = filePath.directoryPath; | 1093 Path dir = filePath.directoryPath; |
1076 var nameNoExt = filePath.filenameWithoutExtension; | 1094 String nameNoExt = filePath.filenameWithoutExtension; |
1077 | 1095 |
1078 var customHtmlPath = dir.append('$nameNoExt.html').toNativePath(); | 1096 String customHtmlPath = dir.append('$nameNoExt.html').toNativePath(); |
1079 var customHtml = new File(customHtmlPath); | 1097 File customHtml = new File(customHtmlPath); |
1080 | 1098 |
1081 // Construct the command(s) that compile all the inputs needed by the | 1099 // Construct the command(s) that compile all the inputs needed by the |
1082 // browser test. For running Dart in DRT, this will be noop commands. | 1100 // browser test. For running Dart in DRT, this will be noop commands. |
1083 var commands = baseCommands.toList(); | 1101 List<Command> commands = []..addAll(baseCommands); |
1084 | 1102 |
1085 // Use existing HTML document if available. | 1103 // Use existing HTML document if available. |
1086 String htmlPath; | 1104 String htmlPath; |
1087 if (customHtml.existsSync()) { | 1105 if (customHtml.existsSync()) { |
1088 // If necessary, run the Polymer deploy steps. | 1106 // If necessary, run the Polymer deploy steps. |
1089 // TODO(jmesserly): this should be generalized for any tests that | 1107 // TODO(jmesserly): this should be generalized for any tests that |
1090 // require Pub deploy, not just polymer. | 1108 // require Pub deploy, not just polymer. |
1091 if (customHtml.readAsStringSync().contains('<!--polymer-test')) { | 1109 if (customHtml.readAsStringSync().contains('<!--polymer-test')) { |
1092 if (configuration.compiler != Compiler.none) { | 1110 if (compiler != 'none') { |
1093 commands.add( | 1111 commands.add( |
1094 _polymerDeployCommand(customHtmlPath, tempDir, optionsFromFile)); | 1112 _polymerDeployCommand(customHtmlPath, tempDir, optionsFromFile)); |
1095 | 1113 |
1096 Path pubspecYamlFile = _findPubspecYamlFile(filePath); | 1114 Path pubspecYamlFile = _findPubspecYamlFile(filePath); |
1097 Path homeDir = | 1115 Path homeDir = |
1098 (pubspecYamlFile == null) ? dir : pubspecYamlFile.directoryPath; | 1116 (pubspecYamlFile == null) ? dir : pubspecYamlFile.directoryPath; |
1099 htmlPath = '$tempDir/${dir.relativeTo(homeDir)}/$nameNoExt.html'; | 1117 htmlPath = '$tempDir/${dir.relativeTo(homeDir)}/$nameNoExt.html'; |
1100 dartWrapperFilename = '${htmlPath}_bootstrap.dart'; | 1118 dartWrapperFilename = '${htmlPath}_bootstrap.dart'; |
1101 compiledDartWrapperFilename = '$dartWrapperFilename.js'; | 1119 compiledDartWrapperFilename = '$dartWrapperFilename.js'; |
1102 } else { | 1120 } else { |
1103 htmlPath = customHtmlPath; | 1121 htmlPath = customHtmlPath; |
1104 } | 1122 } |
1105 } else { | 1123 } else { |
1106 htmlPath = '$tempDir/test.html'; | 1124 htmlPath = '$tempDir/test.html'; |
1107 dartWrapperFilename = filePath.toNativePath(); | 1125 dartWrapperFilename = filePath.toNativePath(); |
1108 | 1126 |
1109 var htmlContents = customHtml.readAsStringSync(); | 1127 var htmlContents = customHtml.readAsStringSync(); |
1110 if (configuration.compiler == Compiler.none) { | 1128 if (compiler == 'none') { |
1111 var dartUrl = _createUrlPathFromFile(filePath); | 1129 var dartUrl = _createUrlPathFromFile(filePath); |
1112 var dartScript = | 1130 var dartScript = |
1113 '<script type="application/dart" src="$dartUrl"></script>'; | 1131 '<script type="application/dart" src="$dartUrl"></script>'; |
1114 var jsUrl = '/packages/browser/dart.js'; | 1132 var jsUrl = '/packages/browser/dart.js'; |
1115 var jsScript = | 1133 var jsScript = |
1116 '<script type="text/javascript" src="$jsUrl"></script>'; | 1134 '<script type="text/javascript" src="$jsUrl"></script>'; |
1117 htmlContents = htmlContents.replaceAll( | 1135 htmlContents = htmlContents.replaceAll( |
1118 '%TEST_SCRIPTS%', '$dartScript\n$jsScript'); | 1136 '%TEST_SCRIPTS%', '$dartScript\n$jsScript'); |
1119 } else { | 1137 } else { |
1120 compiledDartWrapperFilename = '$tempDir/$nameNoExt.js'; | 1138 compiledDartWrapperFilename = '$tempDir/$nameNoExt.js'; |
1121 var jsUrl = '$nameNoExt.js'; | 1139 var jsUrl = '$nameNoExt.js'; |
1122 htmlContents = htmlContents.replaceAll( | 1140 htmlContents = htmlContents.replaceAll( |
1123 '%TEST_SCRIPTS%', '<script src="$jsUrl"></script>'); | 1141 '%TEST_SCRIPTS%', '<script src="$jsUrl"></script>'); |
1124 } | 1142 } |
1125 new File(htmlPath).writeAsStringSync(htmlContents); | 1143 new File(htmlPath).writeAsStringSync(htmlContents); |
1126 } | 1144 } |
1127 } else { | 1145 } else { |
1128 htmlPath = '$tempDir/test.html'; | 1146 htmlPath = '$tempDir/test.html'; |
1129 if (configuration.compiler != Compiler.dart2js) { | 1147 if (configuration['compiler'] != 'dart2js') { |
1130 // test.dart will import the dart test. | 1148 // test.dart will import the dart test. |
1131 _createWrapperFile(dartWrapperFilename, filePath); | 1149 _createWrapperFile(dartWrapperFilename, filePath); |
1132 } else { | 1150 } else { |
1133 dartWrapperFilename = fileName; | 1151 dartWrapperFilename = filename; |
1134 } | 1152 } |
1135 | 1153 |
1136 // Create the HTML file for the test. | 1154 // Create the HTML file for the test. |
1137 var htmlTest = new File(htmlPath).openSync(mode: FileMode.WRITE); | 1155 RandomAccessFile htmlTest = |
| 1156 new File(htmlPath).openSync(mode: FileMode.WRITE); |
1138 | 1157 |
1139 var scriptPath = dartWrapperFilename; | 1158 String scriptPath = dartWrapperFilename; |
1140 if (configuration.compiler != Compiler.none) { | 1159 if (compiler != 'none') { |
1141 scriptPath = compiledDartWrapperFilename; | 1160 scriptPath = compiledDartWrapperFilename; |
1142 } | 1161 } |
1143 scriptPath = _createUrlPathFromFile(new Path(scriptPath)); | 1162 scriptPath = _createUrlPathFromFile(new Path(scriptPath)); |
1144 | 1163 |
1145 content = getHtmlContents(fileName, scriptType, new Path("$scriptPath")); | 1164 content = getHtmlContents(filename, scriptType, new Path("$scriptPath")); |
1146 htmlTest.writeStringSync(content); | 1165 htmlTest.writeStringSync(content); |
1147 htmlTest.closeSync(); | 1166 htmlTest.closeSync(); |
1148 } | 1167 } |
1149 | 1168 |
1150 if (configuration.compiler != Compiler.none) { | 1169 if (compiler != 'none') { |
1151 assert(configuration.compiler == Compiler.dart2js); | |
1152 | |
1153 commands.add(_compileCommand(dartWrapperFilename, | 1170 commands.add(_compileCommand(dartWrapperFilename, |
1154 compiledDartWrapperFilename, tempDir, optionsFromFile)); | 1171 compiledDartWrapperFilename, compiler, tempDir, optionsFromFile)); |
1155 } | 1172 } |
1156 | 1173 |
1157 // some tests require compiling multiple input scripts. | 1174 // some tests require compiling multiple input scripts. |
1158 var otherScripts = optionsFromFile['otherScripts'] as List<String>; | 1175 var otherScripts = optionsFromFile['otherScripts'] as List<String>; |
1159 for (var name in otherScripts) { | 1176 for (var name in otherScripts) { |
1160 var namePath = new Path(name); | 1177 var namePath = new Path(name); |
| 1178 var fileName = namePath.filename; |
1161 var fromPath = filePath.directoryPath.join(namePath); | 1179 var fromPath = filePath.directoryPath.join(namePath); |
1162 | 1180 if (compiler != 'none') { |
1163 if (configuration.compiler != Compiler.none) { | |
1164 assert(configuration.compiler == Compiler.dart2js); | |
1165 assert(namePath.extension == 'dart'); | 1181 assert(namePath.extension == 'dart'); |
1166 | |
1167 commands.add(_compileCommand(fromPath.toNativePath(), | 1182 commands.add(_compileCommand(fromPath.toNativePath(), |
1168 '$tempDir/${namePath.filename}.js', tempDir, optionsFromFile)); | 1183 '$tempDir/$fileName.js', compiler, tempDir, optionsFromFile)); |
1169 } | 1184 } |
1170 | 1185 if (compiler == 'none') { |
1171 if (configuration.compiler == Compiler.none) { | |
1172 // For the tests that require multiple input scripts but are not | 1186 // For the tests that require multiple input scripts but are not |
1173 // compiled, move the input scripts over with the script so they can | 1187 // compiled, move the input scripts over with the script so they can |
1174 // be accessed. | 1188 // be accessed. |
1175 var result = new File(fromPath.toNativePath()).readAsStringSync(); | 1189 var result = new File(fromPath.toNativePath()).readAsStringSync(); |
1176 new File('$tempDir/${namePath.filename}').writeAsStringSync(result); | 1190 new File('$tempDir/$fileName').writeAsStringSync(result); |
1177 } | 1191 } |
1178 } | 1192 } |
1179 | 1193 |
1180 // Variables for browser multi-tests. | 1194 // Variables for browser multi-tests. |
1181 var multitest = info.optionsFromFile['isMultiHtmlTest'] as bool; | 1195 var multitest = info.optionsFromFile['isMultiHtmlTest'] as bool; |
1182 var subtestNames = multitest | 1196 var subtestNames = multitest |
1183 ? (info.optionsFromFile['subtestNames'] as List<String>) | 1197 ? (info.optionsFromFile['subtestNames'] as List<String>) |
1184 : <String>[null]; | 1198 : <String>[null]; |
1185 for (var subtestName in subtestNames) { | 1199 for (var subtestName in subtestNames) { |
1186 // Construct the command that executes the browser test | 1200 // Construct the command that executes the browser test |
1187 var commandSet = commands.toList(); | 1201 var commandSet = commands.toList(); |
1188 | 1202 |
1189 var htmlPath_subtest = _createUrlPathFromFile(new Path(htmlPath)); | 1203 var htmlPath_subtest = _createUrlPathFromFile(new Path(htmlPath)); |
1190 var fullHtmlPath = | 1204 var fullHtmlPath = |
1191 _getUriForBrowserTest(htmlPath_subtest, subtestName).toString(); | 1205 _getUriForBrowserTest(htmlPath_subtest, subtestName).toString(); |
1192 | 1206 |
1193 if (configuration.runtime == Runtime.drt) { | 1207 if (runtime == "drt") { |
1194 var dartFlags = <String>[]; | 1208 var dartFlags = <String>[]; |
1195 var contentShellOptions = ['--no-timeout', '--run-layout-test']; | 1209 var contentShellOptions = ['--no-timeout', '--run-layout-test']; |
1196 | 1210 |
1197 // Disable the GPU under Linux and Dartium. If the GPU is enabled, | 1211 // Disable the GPU under Linux and Dartium. If the GPU is enabled, |
1198 // Chrome may send a termination signal to a test. The test will be | 1212 // Chrome may send a termination signal to a test. The test will be |
1199 // terminated if a machine (bot) doesn't have a GPU or if a test is | 1213 // terminated if a machine (bot) doesn't have a GPU or if a test is |
1200 // still running after a certain period of time. | 1214 // still running after a certain period of time. |
1201 if (configuration.system == System.linux && | 1215 if (configuration['system'] == 'linux' && |
1202 configuration.runtime == Runtime.drt) { | 1216 configuration['runtime'] == 'drt') { |
1203 contentShellOptions.add('--disable-gpu'); | 1217 contentShellOptions.add('--disable-gpu'); |
1204 // TODO(terry): Roll 50 need this in conjection with disable-gpu. | 1218 // TODO(terry): Roll 50 need this in conjection with disable-gpu. |
1205 contentShellOptions.add('--disable-gpu-early-init'); | 1219 contentShellOptions.add('--disable-gpu-early-init'); |
1206 } | 1220 } |
1207 | 1221 if (compiler == 'none') { |
1208 if (configuration.compiler == Compiler.none) { | |
1209 dartFlags.add('--ignore-unrecognized-flags'); | 1222 dartFlags.add('--ignore-unrecognized-flags'); |
1210 if (configuration.isChecked) { | 1223 if (configuration["checked"] as bool) { |
1211 dartFlags.add('--enable_asserts'); | 1224 dartFlags.add('--enable_asserts'); |
1212 dartFlags.add("--enable_type_checks"); | 1225 dartFlags.add("--enable_type_checks"); |
1213 } | 1226 } |
1214 dartFlags.addAll(vmOptions); | 1227 dartFlags.addAll(vmOptions); |
1215 } | 1228 } |
1216 | 1229 |
1217 commandSet.add(CommandBuilder.instance.getContentShellCommand( | 1230 commandSet.add(CommandBuilder.instance.getContentShellCommand( |
1218 contentShellFilename, | 1231 contentShellFilename, |
1219 fullHtmlPath, | 1232 fullHtmlPath, |
1220 contentShellOptions, | 1233 contentShellOptions, |
1221 dartFlags, | 1234 dartFlags, |
1222 environmentOverrides)); | 1235 environmentOverrides)); |
1223 } else { | 1236 } else { |
1224 commandSet.add(CommandBuilder.instance.getBrowserTestCommand( | 1237 commandSet.add(CommandBuilder.instance.getBrowserTestCommand( |
1225 fullHtmlPath, configuration, !isNegative(info))); | 1238 runtime, fullHtmlPath, configuration, !isNegative(info))); |
1226 } | 1239 } |
1227 | 1240 |
1228 // Create BrowserTestCase and queue it. | 1241 // Create BrowserTestCase and queue it. |
1229 var fullTestName = multitest ? '$testName/$subtestName' : testName; | 1242 var fullTestName = multitest ? '$testName/$subtestName' : testName; |
1230 var expectation = (multitest ? expectations[fullTestName] : expectations) | 1243 var expectation = (multitest ? expectations[fullTestName] : expectations) |
1231 as Set<Expectation>; | 1244 as Set<Expectation>; |
1232 var testCase = new BrowserTestCase('$suiteName/$fullTestName', commandSet, | 1245 var testCase = new BrowserTestCase('$suiteName/$fullTestName', commandSet, |
1233 configuration, expectation, info, isNegative(info), fullHtmlPath); | 1246 configuration, expectation, info, isNegative(info), fullHtmlPath); |
1234 | 1247 |
1235 enqueueNewTestCase(testCase); | 1248 enqueueNewTestCase(testCase); |
1236 } | 1249 } |
1237 } | 1250 } |
1238 | 1251 |
1239 void enqueueHtmlTest(HtmlTestInformation info, String testName, | 1252 void enqueueHtmlTest(HtmlTestInformation info, String testName, |
1240 Set<Expectation> expectations) { | 1253 Set<Expectation> expectations) { |
1241 var compiler = configuration.compiler; | 1254 var compiler = configuration['compiler'] as String; |
1242 var runtime = configuration.runtime; | 1255 var runtime = configuration['runtime'] as String; |
| 1256 // Html tests work only with the browser controller. |
| 1257 if (!TestUtils.isBrowserRuntime(runtime) || runtime == 'drt') { |
| 1258 return; |
| 1259 } |
| 1260 bool compileToJS = (compiler == 'dart2js'); |
1243 | 1261 |
1244 // HTML tests work only with the browser controller. | 1262 final Path filePath = info.filePath; |
1245 if (!runtime.isBrowser || runtime == Runtime.drt) return; | 1263 final String tempDir = createOutputDirectory(filePath, ''); |
| 1264 final Uri tempUri = new Uri.file('$tempDir/'); |
| 1265 String contents = htmlTest.getContents(info, compileToJS); |
| 1266 final commands = <Command>[]; |
1246 | 1267 |
1247 var compileToJS = compiler == Compiler.dart2js; | 1268 void Fail(String message) { |
1248 | |
1249 var filePath = info.filePath; | |
1250 var tempDir = createOutputDirectory(filePath, ''); | |
1251 var tempUri = new Uri.file('$tempDir/'); | |
1252 var contents = html_test.getContents(info, compileToJS); | |
1253 var commands = <Command>[]; | |
1254 | |
1255 void fail(String message) { | |
1256 var msg = "$message: ${info.filePath}"; | 1269 var msg = "$message: ${info.filePath}"; |
1257 DebugLogger.warning(msg); | 1270 DebugLogger.warning(msg); |
1258 contents = html_test.makeFailingHtmlFile(msg); | 1271 contents = htmlTest.makeFailingHtmlFile(msg); |
1259 } | 1272 } |
1260 | 1273 |
1261 if (info.scripts.length > 0) { | 1274 if (info.scripts.length > 0) { |
1262 var testUri = new Uri.file(filePath.toNativePath()); | 1275 Uri testUri = new Uri.file(filePath.toNativePath()); |
1263 for (var scriptPath in info.scripts) { | 1276 for (String scriptPath in info.scripts) { |
1264 if (!scriptPath.endsWith('.dart') && !scriptPath.endsWith('.js')) { | 1277 if (!scriptPath.endsWith('.dart') && !scriptPath.endsWith('.js')) { |
1265 fail('HTML test scripts must be dart or javascript: $scriptPath'); | 1278 Fail('HTML test scripts must be dart or javascript: $scriptPath'); |
1266 break; | 1279 break; |
1267 } | 1280 } |
1268 | 1281 Uri uri = Uri.parse(scriptPath); |
1269 var uri = Uri.parse(scriptPath); | |
1270 if (uri.isAbsolute) { | 1282 if (uri.isAbsolute) { |
1271 fail('HTML test scripts must have relative paths: $scriptPath'); | 1283 Fail('HTML test scripts must have relative paths: $scriptPath'); |
1272 break; | 1284 break; |
1273 } | 1285 } |
1274 | |
1275 if (uri.pathSegments.length > 1) { | 1286 if (uri.pathSegments.length > 1) { |
1276 fail('HTML test scripts must be in test directory: $scriptPath'); | 1287 Fail('HTML test scripts must be in test directory: $scriptPath'); |
1277 break; | 1288 break; |
1278 } | 1289 } |
1279 | 1290 Uri script = testUri.resolveUri(uri); |
1280 var script = testUri.resolveUri(uri); | 1291 Uri copiedScript = tempUri.resolveUri(uri); |
1281 var copiedScript = tempUri.resolveUri(uri); | 1292 if (compiler == 'none' || scriptPath.endsWith('.js')) { |
1282 if (compiler == Compiler.none || scriptPath.endsWith('.js')) { | |
1283 new File.fromUri(copiedScript) | 1293 new File.fromUri(copiedScript) |
1284 .writeAsStringSync(new File.fromUri(script).readAsStringSync()); | 1294 .writeAsStringSync(new File.fromUri(script).readAsStringSync()); |
1285 } else { | 1295 } else { |
1286 var destination = copiedScript.toFilePath(); | 1296 var destination = copiedScript.toFilePath(); |
1287 if (compileToJS) { | 1297 if (compileToJS) { |
1288 destination = destination.replaceFirst(dartExtension, '.js'); | 1298 destination = destination.replaceFirst(dartExtension, '.js'); |
1289 } | 1299 } |
1290 | 1300 commands.add(_compileCommand(script.toFilePath(), destination, |
1291 assert(compiler == Compiler.dart2js); | 1301 compiler, tempDir, info.optionsFromFile)); |
1292 | |
1293 commands.add(_compileCommand( | |
1294 script.toFilePath(), destination, tempDir, info.optionsFromFile)); | |
1295 } | 1302 } |
1296 } | 1303 } |
1297 } | 1304 } |
1298 | 1305 final Uri htmlFile = tempUri.resolve(filePath.filename); |
1299 var htmlFile = tempUri.resolve(filePath.filename); | |
1300 new File.fromUri(htmlFile).writeAsStringSync(contents); | 1306 new File.fromUri(htmlFile).writeAsStringSync(contents); |
1301 | 1307 |
1302 var htmlPath = _createUrlPathFromFile(new Path(htmlFile.toFilePath())); | 1308 var htmlPath = _createUrlPathFromFile(new Path(htmlFile.toFilePath())); |
1303 var fullHtmlPath = _getUriForBrowserTest(htmlPath, null).toString(); | 1309 var fullHtmlPath = _getUriForBrowserTest(htmlPath, null).toString(); |
1304 commands.add(CommandBuilder.instance.getBrowserHtmlTestCommand( | 1310 commands.add(CommandBuilder.instance.getBrowserHtmlTestCommand(runtime, |
1305 fullHtmlPath, configuration, info.expectedMessages, !isNegative(info))); | 1311 fullHtmlPath, configuration, info.expectedMessages, !isNegative(info))); |
1306 var testDisplayName = '$suiteName/$testName'; | 1312 String testDisplayName = '$suiteName/$testName'; |
1307 var testCase = new BrowserTestCase(testDisplayName, commands, configuration, | 1313 var testCase = new BrowserTestCase(testDisplayName, commands, configuration, |
1308 expectations, info, isNegative(info), fullHtmlPath); | 1314 expectations, info, isNegative(info), fullHtmlPath); |
1309 enqueueNewTestCase(testCase); | 1315 enqueueNewTestCase(testCase); |
| 1316 return; |
1310 } | 1317 } |
1311 | 1318 |
1312 /** Helper to create a compilation command for a single input file. */ | 1319 /** Helper to create a compilation command for a single input file. */ |
1313 Command _compileCommand(String inputFile, String outputFile, String dir, | 1320 Command _compileCommand(String inputFile, String outputFile, String compiler, |
1314 Map<String, dynamic> optionsFromFile) { | 1321 String dir, Map optionsFromFile) { |
1315 var args = <String>[]; | 1322 assert(compiler == 'dart2js'); |
1316 | 1323 List<String> args; |
1317 if (compilerPath.endsWith('.dart')) { | 1324 if (compilerPath.endsWith('.dart')) { |
1318 // Run the compiler script via the Dart VM. | 1325 // Run the compiler script via the Dart VM. |
1319 args.add(compilerPath); | 1326 args = [compilerPath]; |
| 1327 } else { |
| 1328 args = []; |
1320 } | 1329 } |
1321 | 1330 args.addAll(TestUtils.standardOptions(configuration)); |
1322 args.addAll(configuration.standardOptions); | |
1323 | |
1324 var packages = packagesArgument(optionsFromFile['packageRoot'] as String, | 1331 var packages = packagesArgument(optionsFromFile['packageRoot'] as String, |
1325 optionsFromFile['packages'] as String); | 1332 optionsFromFile['packages'] as String); |
1326 if (packages != null) args.add(packages); | 1333 if (packages != null) args.add(packages); |
1327 | |
1328 args.add('--out=$outputFile'); | 1334 args.add('--out=$outputFile'); |
1329 args.add(inputFile); | 1335 args.add(inputFile); |
1330 | |
1331 var options = optionsFromFile['sharedOptions'] as List<String>; | 1336 var options = optionsFromFile['sharedOptions'] as List<String>; |
1332 if (options != null) args.addAll(options); | 1337 if (options != null) args.addAll(options); |
1333 | |
1334 return CommandBuilder.instance.getCompilationCommand( | 1338 return CommandBuilder.instance.getCompilationCommand( |
1335 Compiler.dart2js.name, | 1339 compiler, |
1336 outputFile, | 1340 outputFile, |
1337 !useSdk, | 1341 !useSdk, |
1338 dart2JsBootstrapDependencies, | 1342 dart2JsBootstrapDependencies, |
1339 compilerPath, | 1343 compilerPath, |
1340 args, | 1344 args, |
1341 environmentOverrides); | 1345 environmentOverrides); |
1342 } | 1346 } |
1343 | 1347 |
1344 /** Helper to create a Polymer deploy command for a single HTML file. */ | 1348 /** Helper to create a Polymer deploy command for a single HTML file. */ |
1345 Command _polymerDeployCommand(String inputFile, String outputDir, | 1349 Command _polymerDeployCommand( |
1346 Map<String, dynamic> optionsFromFile) { | 1350 String inputFile, String outputDir, Map optionsFromFile) { |
1347 var args = <String>[]; | 1351 List<String> args = []; |
1348 var packages = packagesArgument(optionsFromFile['packageRoot'] as String, | 1352 String packages = packagesArgument(optionsFromFile['packageRoot'] as String, |
1349 optionsFromFile['packages'] as String); | 1353 optionsFromFile['packages'] as String); |
1350 if (packages != null) args.add(packages); | 1354 if (packages != null) args.add(packages); |
1351 args | 1355 args |
1352 ..add('package:polymer/deploy.dart') | 1356 ..add('package:polymer/deploy.dart') |
1353 ..add('--test') | 1357 ..add('--test') |
1354 ..add(inputFile) | 1358 ..add(inputFile) |
1355 ..add('--out') | 1359 ..add('--out') |
1356 ..add(outputDir) | 1360 ..add(outputDir) |
1357 ..add('--file-filter') | 1361 ..add('--file-filter') |
1358 ..add('.svn'); | 1362 ..add('.svn'); |
1359 if (configuration.isCsp) args.add('--csp'); | 1363 if (configuration['csp'] as bool) args.add('--csp'); |
1360 | 1364 |
1361 return CommandBuilder.instance.getProcessCommand( | 1365 return CommandBuilder.instance.getProcessCommand( |
1362 'polymer_deploy', dartVmBinaryFileName, args, environmentOverrides); | 1366 'polymer_deploy', dartVmBinaryFileName, args, environmentOverrides); |
1363 } | 1367 } |
1364 | 1368 |
1365 String get scriptType { | 1369 String get scriptType { |
1366 switch (configuration.compiler) { | 1370 switch (configuration['compiler'] as String) { |
1367 case Compiler.none: | 1371 case 'none': |
1368 return 'application/dart'; | 1372 return 'application/dart'; |
1369 case Compiler.dart2js: | 1373 case 'dart2js': |
1370 case Compiler.dart2analyzer: | 1374 case 'dart2analyzer': |
1371 return 'text/javascript'; | 1375 return 'text/javascript'; |
1372 default: | 1376 default: |
1373 print('Non-web runtime, so no scriptType for: ' | 1377 print('Non-web runtime, so no scriptType for: ' |
1374 '${configuration.compiler.name}'); | 1378 '${configuration["compiler"]}'); |
1375 exit(1); | 1379 exit(1); |
1376 return null; | 1380 return null; |
1377 } | 1381 } |
1378 } | 1382 } |
1379 | 1383 |
1380 bool get hasRuntime => configuration.runtime != Runtime.none; | 1384 bool get hasRuntime { |
| 1385 switch (configuration['runtime'] as String) { |
| 1386 case 'none': |
| 1387 return false; |
| 1388 default: |
| 1389 return true; |
| 1390 } |
| 1391 } |
1381 | 1392 |
1382 String get contentShellFilename { | 1393 String get contentShellFilename { |
1383 if (configuration.drtPath != null) return configuration.drtPath; | 1394 if (configuration['drt'] != '') { |
1384 | 1395 return configuration['drt'] as String; |
| 1396 } |
1385 if (Platform.operatingSystem == 'macos') { | 1397 if (Platform.operatingSystem == 'macos') { |
1386 final path = dartDir.append( | 1398 final path = dartDir.append( |
1387 '/client/tests/drt/Content Shell.app/Contents/MacOS/Content Shell'); | 1399 '/client/tests/drt/Content Shell.app/Contents/MacOS/Content Shell'); |
1388 return path.toNativePath(); | 1400 return path.toNativePath(); |
1389 } | 1401 } |
1390 return dartDir.append('client/tests/drt/content_shell').toNativePath(); | 1402 return dartDir.append('client/tests/drt/content_shell').toNativePath(); |
1391 } | 1403 } |
1392 | 1404 |
1393 List<String> commonArgumentsFromFile( | 1405 List<String> commonArgumentsFromFile(Path filePath, Map optionsFromFile) { |
1394 Path filePath, Map<String, dynamic> optionsFromFile) { | 1406 var args = TestUtils.standardOptions(configuration); |
1395 var args = configuration.standardOptions.toList(); | |
1396 | 1407 |
1397 String packages = packagesArgument(optionsFromFile['packageRoot'] as String, | 1408 String packages = packagesArgument(optionsFromFile['packageRoot'] as String, |
1398 optionsFromFile['packages'] as String); | 1409 optionsFromFile['packages'] as String); |
1399 if (packages != null) { | 1410 if (packages != null) { |
1400 args.add(packages); | 1411 args.add(packages); |
1401 } | 1412 } |
1402 args.addAll(additionalOptions(filePath)); | 1413 args.addAll(additionalOptions(filePath)); |
1403 if (configuration.compiler == Compiler.dart2analyzer) { | 1414 if (configuration['analyzer'] as bool) { |
1404 args.add('--format=machine'); | 1415 args.add('--format=machine'); |
1405 args.add('--no-hints'); | 1416 args.add('--no-hints'); |
| 1417 } |
1406 | 1418 |
1407 if (filePath.filename.contains("dart2js") || | 1419 if (configuration["compiler"] == "dart2analyzer" && |
1408 filePath.directoryPath.segments().last.contains('html_common')) { | 1420 (filePath.filename.contains("dart2js") || |
1409 args.add("--use-dart2js-libraries"); | 1421 filePath.directoryPath.segments().last.contains('html_common'))) { |
1410 } | 1422 args.add("--use-dart2js-libraries"); |
1411 } | 1423 } |
1412 | 1424 |
1413 var isMultitest = optionsFromFile["isMultitest"] as bool; | 1425 var isMultitest = optionsFromFile["isMultitest"] as bool; |
1414 var dartOptions = optionsFromFile["dartOptions"] as List<String>; | 1426 var dartOptions = optionsFromFile["dartOptions"] as List<String>; |
1415 | 1427 |
1416 assert(!isMultitest || dartOptions == null); | 1428 assert(!isMultitest || dartOptions == null); |
1417 args.add(filePath.toNativePath()); | 1429 args.add(filePath.toNativePath()); |
1418 if (dartOptions != null) { | 1430 if (dartOptions != null) { |
1419 args.addAll(dartOptions); | 1431 args.addAll(dartOptions); |
1420 } | 1432 } |
(...skipping 71 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1492 * an image, if the expectation ends in .png. 'test.dart' will compare the | 1504 * an image, if the expectation ends in .png. 'test.dart' will compare the |
1493 * snapshot to the expectation file. When tests fail, 'test.dart' saves the | 1505 * snapshot to the expectation file. When tests fail, 'test.dart' saves the |
1494 * new snapshot into a file so it can be visualized or copied over. | 1506 * new snapshot into a file so it can be visualized or copied over. |
1495 * Expectations can be recorded for the first time by creating an empty file | 1507 * Expectations can be recorded for the first time by creating an empty file |
1496 * with the right name (touch test_name_test.png), running the test, and | 1508 * with the right name (touch test_name_test.png), running the test, and |
1497 * executing the copy command printed by the test script. | 1509 * executing the copy command printed by the test script. |
1498 * | 1510 * |
1499 * This method is static as the map is cached and shared amongst | 1511 * This method is static as the map is cached and shared amongst |
1500 * configurations, so it may not use [configuration]. | 1512 * configurations, so it may not use [configuration]. |
1501 */ | 1513 */ |
1502 Map<String, dynamic> readOptionsFromFile(Path filePath) { | 1514 Map readOptionsFromFile(Path filePath) { |
1503 if (filePath.filename.endsWith('.dill')) { | 1515 if (filePath.filename.endsWith('.dill')) { |
1504 return optionsFromKernelFile(); | 1516 return optionsFromKernelFile(); |
1505 } else if (filePath.segments().contains('co19')) { | 1517 } else if (filePath.segments().contains('co19')) { |
1506 return readOptionsFromCo19File(filePath); | 1518 return readOptionsFromCo19File(filePath); |
1507 } | 1519 } |
1508 RegExp testOptionsRegExp = new RegExp(r"// VMOptions=(.*)"); | 1520 RegExp testOptionsRegExp = new RegExp(r"// VMOptions=(.*)"); |
1509 RegExp sharedOptionsRegExp = new RegExp(r"// SharedOptions=(.*)"); | 1521 RegExp sharedOptionsRegExp = new RegExp(r"// SharedOptions=(.*)"); |
1510 RegExp dartOptionsRegExp = new RegExp(r"// DartOptions=(.*)"); | 1522 RegExp dartOptionsRegExp = new RegExp(r"// DartOptions=(.*)"); |
1511 RegExp otherScriptsRegExp = new RegExp(r"// OtherScripts=(.*)"); | 1523 RegExp otherScriptsRegExp = new RegExp(r"// OtherScripts=(.*)"); |
1512 RegExp otherResourcesRegExp = new RegExp(r"// OtherResources=(.*)"); | 1524 RegExp otherResourcesRegExp = new RegExp(r"// OtherResources=(.*)"); |
1513 RegExp packageRootRegExp = new RegExp(r"// PackageRoot=(.*)"); | 1525 RegExp packageRootRegExp = new RegExp(r"// PackageRoot=(.*)"); |
1514 RegExp packagesRegExp = new RegExp(r"// Packages=(.*)"); | 1526 RegExp packagesRegExp = new RegExp(r"// Packages=(.*)"); |
1515 RegExp isolateStubsRegExp = new RegExp(r"// IsolateStubs=(.*)"); | 1527 RegExp isolateStubsRegExp = new RegExp(r"// IsolateStubs=(.*)"); |
1516 // TODO(gram) Clean these up once the old directives are not supported. | 1528 // TODO(gram) Clean these up once the old directives are not supported. |
1517 RegExp domImportRegExp = new RegExp( | 1529 RegExp domImportRegExp = new RegExp( |
1518 r"^[#]?import.*dart:(html|web_audio|indexed_db|svg|web_sql)", | 1530 r"^[#]?import.*dart:(html|web_audio|indexed_db|svg|web_sql)", |
1519 multiLine: true); | 1531 multiLine: true); |
1520 | 1532 |
1521 var bytes = new File(filePath.toNativePath()).readAsBytesSync(); | 1533 var bytes = new File(filePath.toNativePath()).readAsBytesSync(); |
1522 String contents = decodeUtf8(bytes); | 1534 String contents = decodeUtf8(bytes); |
1523 bytes = null; | 1535 bytes = null; |
1524 | 1536 |
1525 // Find the options in the file. | 1537 // Find the options in the file. |
1526 var result = <List<String>>[]; | 1538 var result = <List<String>>[]; |
1527 List<String> dartOptions; | 1539 List<String> dartOptions; |
1528 List<String> sharedOptions; | 1540 List<String> sharedOptions; |
1529 String packageRoot; | 1541 String packageRoot; |
1530 String packages; | 1542 String packages; |
1531 | 1543 |
1532 var matches = testOptionsRegExp.allMatches(contents); | 1544 Iterable<Match> matches = testOptionsRegExp.allMatches(contents); |
1533 for (var match in matches) { | 1545 for (var match in matches) { |
1534 result.add(match[1].split(' ').where((e) => e != '').toList()); | 1546 result.add(match[1].split(' ').where((e) => e != '').toList()); |
1535 } | 1547 } |
1536 if (result.isEmpty) result.add([]); | 1548 if (result.isEmpty) result.add([]); |
1537 | 1549 |
1538 matches = dartOptionsRegExp.allMatches(contents); | 1550 matches = dartOptionsRegExp.allMatches(contents); |
1539 for (var match in matches) { | 1551 for (var match in matches) { |
1540 if (dartOptions != null) { | 1552 if (dartOptions != null) { |
1541 throw new Exception( | 1553 throw new Exception( |
1542 'More than one "// DartOptions=" line in test $filePath'); | 1554 'More than one "// DartOptions=" line in test $filePath'); |
(...skipping 77 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1620 "otherScripts": otherScripts, | 1632 "otherScripts": otherScripts, |
1621 "otherResources": otherResources, | 1633 "otherResources": otherResources, |
1622 "isMultitest": isMultitest, | 1634 "isMultitest": isMultitest, |
1623 "isMultiHtmlTest": isMultiHtmlTest, | 1635 "isMultiHtmlTest": isMultiHtmlTest, |
1624 "subtestNames": subtestNames, | 1636 "subtestNames": subtestNames, |
1625 "isolateStubs": isolateStubs, | 1637 "isolateStubs": isolateStubs, |
1626 "containsDomImport": containsDomImport | 1638 "containsDomImport": containsDomImport |
1627 }; | 1639 }; |
1628 } | 1640 } |
1629 | 1641 |
1630 Map<String, dynamic> optionsFromKernelFile() { | 1642 Map optionsFromKernelFile() { |
1631 return const { | 1643 return const { |
1632 "vmOptions": const [const []], | 1644 "vmOptions": const [const []], |
1633 "sharedOptions": const [], | 1645 "sharedOptions": const [], |
1634 "dartOptions": null, | 1646 "dartOptions": null, |
1635 "packageRoot": null, | 1647 "packageRoot": null, |
1636 "packages": null, | 1648 "packages": null, |
1637 "hasCompileError": false, | 1649 "hasCompileError": false, |
1638 "hasRuntimeError": false, | 1650 "hasRuntimeError": false, |
1639 "hasStaticWarning": false, | 1651 "hasStaticWarning": false, |
1640 "otherScripts": const [], | 1652 "otherScripts": const [], |
1641 "isMultitest": false, | 1653 "isMultitest": false, |
1642 "isMultiHtmlTest": false, | 1654 "isMultiHtmlTest": false, |
1643 "subtestNames": const [], | 1655 "subtestNames": const [], |
1644 "isolateStubs": '', | 1656 "isolateStubs": '', |
1645 "containsDomImport": false, | 1657 "containsDomImport": false, |
1646 }; | 1658 }; |
1647 } | 1659 } |
1648 | 1660 |
1649 List<List<String>> getVmOptions(Map<String, dynamic> optionsFromFile) { | 1661 List<List<String>> getVmOptions(Map optionsFromFile) { |
1650 const compilers = const [ | 1662 var COMPILERS = const ['none', 'dartk', 'dartkp', 'precompiler', 'app_jit']; |
1651 Compiler.none, | 1663 var RUNTIMES = const [ |
1652 Compiler.dartk, | 1664 'none', |
1653 Compiler.dartkp, | 1665 'dart_precompiled', |
1654 Compiler.precompiler, | 1666 'vm', |
1655 Compiler.appJit | 1667 'drt', |
| 1668 'dartium', |
| 1669 'ContentShellOnAndroid', |
| 1670 'DartiumOnAndroid' |
1656 ]; | 1671 ]; |
1657 | 1672 var needsVmOptions = COMPILERS.contains(configuration['compiler']) && |
1658 const runtimes = const [ | 1673 RUNTIMES.contains(configuration['runtime']); |
1659 Runtime.none, | |
1660 Runtime.dartPrecompiled, | |
1661 Runtime.vm, | |
1662 Runtime.drt, | |
1663 Runtime.dartium, | |
1664 Runtime.contentShellOnAndroid, | |
1665 Runtime.dartiumOnAndroid | |
1666 ]; | |
1667 | |
1668 var needsVmOptions = compilers.contains(configuration.compiler) && | |
1669 runtimes.contains(configuration.runtime); | |
1670 if (!needsVmOptions) return [[]]; | 1674 if (!needsVmOptions) return [[]]; |
1671 return optionsFromFile['vmOptions'] as List<List<String>>; | 1675 return optionsFromFile['vmOptions'] as List<List<String>>; |
1672 } | 1676 } |
1673 | 1677 |
1674 /** | 1678 /** |
1675 * Read options from a co19 test file. | 1679 * Read options from a co19 test file. |
1676 * | 1680 * |
1677 * The reason this is different from [readOptionsFromFile] is that | 1681 * The reason this is different from [readOptionsFromFile] is that |
1678 * co19 is developed based on a contract which defines certain test | 1682 * co19 is developed based on a contract which defines certain test |
1679 * tags. These tags may appear unused, but should not be removed | 1683 * tags. These tags may appear unused, but should not be removed |
1680 * without consulting with the co19 team. | 1684 * without consulting with the co19 team. |
1681 * | 1685 * |
1682 * Also, [readOptionsFromFile] recognizes a number of additional | 1686 * Also, [readOptionsFromFile] recognizes a number of additional |
1683 * tags that are not appropriate for use in general tests of | 1687 * tags that are not appropriate for use in general tests of |
1684 * conformance to the Dart language. Any Dart implementation must | 1688 * conformance to the Dart language. Any Dart implementation must |
1685 * pass the co19 test suite as is, and not require extra flags, | 1689 * pass the co19 test suite as is, and not require extra flags, |
1686 * environment variables, configuration files, etc. | 1690 * environment variables, configuration files, etc. |
1687 */ | 1691 */ |
1688 Map<String, dynamic> readOptionsFromCo19File(Path filePath) { | 1692 Map readOptionsFromCo19File(Path filePath) { |
1689 String contents = | 1693 String contents = |
1690 decodeUtf8(new File(filePath.toNativePath()).readAsBytesSync()); | 1694 decodeUtf8(new File(filePath.toNativePath()).readAsBytesSync()); |
1691 | 1695 |
1692 bool hasCompileError = contents.contains("@compile-error"); | 1696 bool hasCompileError = contents.contains("@compile-error"); |
1693 bool hasRuntimeError = contents.contains("@runtime-error"); | 1697 bool hasRuntimeError = contents.contains("@runtime-error"); |
1694 bool hasStaticWarning = contents.contains("@static-warning"); | 1698 bool hasStaticWarning = contents.contains("@static-warning"); |
1695 bool isMultitest = multiTestRegExp.hasMatch(contents); | 1699 bool isMultitest = multiTestRegExp.hasMatch(contents); |
1696 | 1700 |
1697 return { | 1701 return { |
1698 "vmOptions": <List>[[]], | 1702 "vmOptions": <List>[[]], |
(...skipping 10 matching lines...) Expand all Loading... |
1709 "subtestNames": <String>[], | 1713 "subtestNames": <String>[], |
1710 "isolateStubs": '', | 1714 "isolateStubs": '', |
1711 "containsDomImport": false, | 1715 "containsDomImport": false, |
1712 }; | 1716 }; |
1713 } | 1717 } |
1714 } | 1718 } |
1715 | 1719 |
1716 /// Used for testing packages in on off settings, i.e., we pass in the actual | 1720 /// Used for testing packages in on off settings, i.e., we pass in the actual |
1717 /// directory that we want to test. | 1721 /// directory that we want to test. |
1718 class PKGTestSuite extends StandardTestSuite { | 1722 class PKGTestSuite extends StandardTestSuite { |
1719 PKGTestSuite(Configuration configuration, Path directoryPath) | 1723 PKGTestSuite(Map<String, dynamic> configuration, Path directoryPath) |
1720 : super(configuration, directoryPath.filename, directoryPath, | 1724 : super(configuration, directoryPath.filename, directoryPath, |
1721 ["$directoryPath/.status"], | 1725 ["$directoryPath/.status"], |
1722 isTestFilePredicate: (f) => f.endsWith('_test.dart'), | 1726 isTestFilePredicate: (f) => f.endsWith('_test.dart'), |
1723 recursive: true); | 1727 recursive: true); |
1724 | 1728 |
1725 void enqueueBrowserTest( | 1729 void enqueueBrowserTest( |
1726 List<Command> baseCommands, | 1730 List<Command> baseCommands, |
1727 Path packageRoot, | 1731 Path packageRoot, |
1728 packages, | 1732 packages, |
1729 TestInformation info, | 1733 TestInformation info, |
1730 String testName, | 1734 String testName, |
1731 /* Set<Expectation> | Map<String, Set<Expectation>> */ dynamic | 1735 /* Set<Expectation> | Map<String, Set<Expectation>> */ dynamic |
1732 expectations) { | 1736 expectations) { |
| 1737 var runtime = configuration['runtime'] as String; |
1733 var filePath = info.filePath; | 1738 var filePath = info.filePath; |
1734 var dir = filePath.directoryPath; | 1739 var dir = filePath.directoryPath; |
1735 var nameNoExt = filePath.filenameWithoutExtension; | 1740 var nameNoExt = filePath.filenameWithoutExtension; |
1736 var customHtmlPath = dir.append('$nameNoExt.html'); | 1741 var customHtmlPath = dir.append('$nameNoExt.html'); |
1737 var customHtml = new File(customHtmlPath.toNativePath()); | 1742 var customHtml = new File(customHtmlPath.toNativePath()); |
1738 if (!customHtml.existsSync()) { | 1743 if (!customHtml.existsSync()) { |
1739 super.enqueueBrowserTest( | 1744 super.enqueueBrowserTest( |
1740 baseCommands, packageRoot, packages, info, testName, expectations); | 1745 baseCommands, packageRoot, packages, info, testName, expectations); |
1741 } else { | 1746 } else { |
1742 var relativeHtml = customHtmlPath.relativeTo(TestUtils.dartDir); | 1747 var relativeHtml = customHtmlPath.relativeTo(TestUtils.dartDir); |
1743 var commands = baseCommands.toList(); | 1748 var commands = baseCommands.toList(); |
1744 var fullPath = _createUrlPathFromFile(customHtmlPath); | 1749 var fullPath = _createUrlPathFromFile(customHtmlPath); |
1745 | 1750 |
1746 commands.add(CommandBuilder.instance | 1751 commands.add(CommandBuilder.instance.getBrowserTestCommand( |
1747 .getBrowserTestCommand(fullPath, configuration, !isNegative(info))); | 1752 runtime, fullPath, configuration, !isNegative(info))); |
1748 var testDisplayName = '$suiteName/$testName'; | 1753 var testDisplayName = '$suiteName/$testName'; |
1749 enqueueNewTestCase(new BrowserTestCase( | 1754 enqueueNewTestCase(new BrowserTestCase( |
1750 testDisplayName, | 1755 testDisplayName, |
1751 commands, | 1756 commands, |
1752 configuration, | 1757 configuration, |
1753 expectations as Set<Expectation>, | 1758 expectations as Set<Expectation>, |
1754 info, | 1759 info, |
1755 isNegative(info), | 1760 isNegative(info), |
1756 relativeHtml.toNativePath())); | 1761 relativeHtml.toNativePath())); |
1757 } | 1762 } |
1758 } | 1763 } |
1759 } | 1764 } |
1760 | 1765 |
1761 /// A DartcCompilationTestSuite will run dartc on all of the tests. | 1766 /// A DartcCompilationTestSuite will run dartc on all of the tests. |
1762 /// | 1767 /// |
1763 /// Usually, the result of a dartc run is determined by the output of | 1768 /// Usually, the result of a dartc run is determined by the output of |
1764 /// dartc in connection with annotations in the test file. | 1769 /// dartc in connection with annotations in the test file. |
1765 class DartcCompilationTestSuite extends StandardTestSuite { | 1770 class DartcCompilationTestSuite extends StandardTestSuite { |
1766 List<String> _testDirs; | 1771 List<String> _testDirs; |
1767 | 1772 |
1768 DartcCompilationTestSuite( | 1773 DartcCompilationTestSuite( |
1769 Configuration configuration, | 1774 Map<String, dynamic> configuration, |
1770 String suiteName, | 1775 String suiteName, |
1771 String directoryPath, | 1776 String directoryPath, |
1772 List<String> this._testDirs, | 1777 List<String> this._testDirs, |
1773 List<String> expectations) | 1778 List<String> expectations) |
1774 : super(configuration, suiteName, new Path(directoryPath), expectations); | 1779 : super(configuration, suiteName, new Path(directoryPath), expectations); |
1775 | 1780 |
1776 List<String> additionalOptions(Path filePath) { | 1781 List<String> additionalOptions(Path filePath) { |
1777 return ['--fatal-warnings', '--fatal-type-errors']; | 1782 return ['--fatal-warnings', '--fatal-type-errors']; |
1778 } | 1783 } |
1779 | 1784 |
1780 Future enqueueTests() { | 1785 Future enqueueTests() { |
1781 var group = new FutureGroup(); | 1786 var group = new FutureGroup(); |
1782 | 1787 |
1783 for (String testDir in _testDirs) { | 1788 for (String testDir in _testDirs) { |
1784 Directory dir = new Directory(suiteDir.append(testDir).toNativePath()); | 1789 Directory dir = new Directory(suiteDir.append(testDir).toNativePath()); |
1785 if (dir.existsSync()) { | 1790 if (dir.existsSync()) { |
1786 enqueueDirectory(dir, group); | 1791 enqueueDirectory(dir, group); |
1787 } | 1792 } |
1788 } | 1793 } |
1789 | 1794 |
1790 return group.future; | 1795 return group.future; |
1791 } | 1796 } |
1792 } | 1797 } |
1793 | 1798 |
1794 class AnalyzeLibraryTestSuite extends DartcCompilationTestSuite { | 1799 class AnalyzeLibraryTestSuite extends DartcCompilationTestSuite { |
1795 static String libraryPath(Configuration configuration) => | 1800 static String libraryPath(Map<String, dynamic> configuration) => |
1796 configuration.useSdk ? '${configuration.buildDirectory}/dart-sdk' : 'sdk'; | 1801 configuration['use_sdk'] as bool |
| 1802 ? '${TestUtils.buildDir(configuration)}/dart-sdk' |
| 1803 : 'sdk'; |
1797 | 1804 |
1798 AnalyzeLibraryTestSuite(Configuration configuration) | 1805 AnalyzeLibraryTestSuite(Map<String, dynamic> configuration) |
1799 : super(configuration, 'analyze_library', libraryPath(configuration), | 1806 : super(configuration, 'analyze_library', libraryPath(configuration), |
1800 ['lib'], ['tests/lib/analyzer/analyze_library.status']); | 1807 ['lib'], ['tests/lib/analyzer/analyze_library.status']); |
1801 | 1808 |
1802 List<String> additionalOptions(Path filePath, {bool showSdkWarnings}) { | 1809 List<String> additionalOptions(Path filePath, {bool showSdkWarnings}) { |
1803 var options = super.additionalOptions(filePath); | 1810 var options = super.additionalOptions(filePath); |
1804 options.add('--sdk-warnings'); | 1811 options.add('--sdk-warnings'); |
1805 return options; | 1812 return options; |
1806 } | 1813 } |
1807 | 1814 |
1808 bool isTestFile(String filename) { | 1815 bool isTestFile(String filename) { |
(...skipping 142 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1951 throw new Exception('Can\'t delete path $native_path. ' | 1958 throw new Exception('Can\'t delete path $native_path. ' |
1952 'This path might be too long'); | 1959 'This path might be too long'); |
1953 } | 1960 } |
1954 }); | 1961 }); |
1955 } else { | 1962 } else { |
1956 var dir = new Directory(path); | 1963 var dir = new Directory(path); |
1957 return dir.delete(recursive: true); | 1964 return dir.delete(recursive: true); |
1958 } | 1965 } |
1959 } | 1966 } |
1960 | 1967 |
1961 static void deleteTempSnapshotDirectory(Configuration configuration) { | 1968 static void deleteTempSnapshotDirectory(Map configuration) { |
1962 if (configuration.compiler == Compiler.appJit || | 1969 if (configuration['compiler'] == 'dart2app' || |
1963 configuration.compiler == Compiler.precompiler) { | 1970 configuration['compiler'] == 'dart2appjit' || |
1964 var checked = configuration.isChecked ? '-checked' : ''; | 1971 configuration['compiler'] == 'precompiler') { |
1965 var strong = configuration.isStrong ? '-strong' : ''; | 1972 var checked = (configuration['checked'] as bool) ? '-checked' : ''; |
1966 var minified = configuration.isMinified ? '-minified' : ''; | 1973 var strong = (configuration['strong'] as bool) ? '-strong' : ''; |
1967 var csp = configuration.isCsp ? '-csp' : ''; | 1974 var minified = (configuration['minified'] as bool) ? '-minified' : ''; |
1968 var sdk = configuration.useSdk ? '-sdk' : ''; | 1975 var csp = (configuration['csp'] as bool) ? '-csp' : ''; |
1969 var dirName = "${configuration.compiler.name}" | 1976 var sdk = (configuration['use_sdk'] as bool) ? '-sdk' : ''; |
| 1977 var dirName = "${configuration['compiler']}" |
1970 "$checked$strong$minified$csp$sdk"; | 1978 "$checked$strong$minified$csp$sdk"; |
1971 var generatedPath = | 1979 String generatedPath = "${TestUtils.buildDir(configuration)}" |
1972 configuration.buildDirectory + "/generated_compilations/$dirName"; | 1980 "/generated_compilations/$dirName"; |
1973 TestUtils.deleteDirectory(generatedPath); | 1981 TestUtils.deleteDirectory(generatedPath); |
1974 } | 1982 } |
1975 } | 1983 } |
1976 | 1984 |
1977 static final debugLogFilePath = new Path(".debug.log"); | 1985 static final debugLogFilePath = new Path(".debug.log"); |
1978 | 1986 |
1979 /// If a flaky test did fail, infos about it (i.e. test name, stdin, stdout) | 1987 /// If a flaky test did fail, infos about it (i.e. test name, stdin, stdout) |
1980 /// will be written to this file. | 1988 /// will be written to this file. |
1981 /// | 1989 /// |
1982 /// This is useful for debugging flaky tests. When running on a buildbot, the | 1990 /// This is useful for debugging flaky tests. When running on a buildbot, the |
1983 /// file can be made visible in the waterfall UI. | 1991 /// file can be made visible in the waterfall UI. |
1984 static const flakyFileName = ".flaky.log"; | 1992 static const flakyFileName = ".flaky.log"; |
1985 | 1993 |
1986 /// If test.py was invoked with '--write-test-outcome-log it will write | 1994 /// If test.py was invoked with '--write-test-outcome-log it will write |
1987 /// test outcomes to this file. | 1995 /// test outcomes to this file. |
1988 static const testOutcomeFileName = ".test-outcome.log"; | 1996 static const testOutcomeFileName = ".test-outcome.log"; |
1989 | 1997 |
1990 static void ensureExists(String filename, Configuration configuration) { | 1998 static void ensureExists(String filename, Map configuration) { |
1991 if (!configuration.listTests && !existsCache.doesFileExist(filename)) { | 1999 if (!(configuration['list'] as bool) && |
| 2000 !existsCache.doesFileExist(filename)) { |
1992 throw "'$filename' does not exist"; | 2001 throw "'$filename' does not exist"; |
1993 } | 2002 } |
1994 } | 2003 } |
1995 | 2004 |
1996 static Path absolutePath(Path path) { | 2005 static Path absolutePath(Path path) { |
1997 if (!path.isAbsolute) { | 2006 if (!path.isAbsolute) { |
1998 return currentWorkingDirectory.join(path); | 2007 return currentWorkingDirectory.join(path); |
1999 } | 2008 } |
2000 return path; | 2009 return path; |
2001 } | 2010 } |
2002 | 2011 |
| 2012 static String outputDir(Map configuration) { |
| 2013 var result = ''; |
| 2014 var system = configuration['system'] as String; |
| 2015 if (system == 'fuchsia' || |
| 2016 system == 'linux' || |
| 2017 system == 'android' || |
| 2018 system == 'windows') { |
| 2019 result = 'out/'; |
| 2020 } else if (system == 'macos') { |
| 2021 result = 'xcodebuild/'; |
| 2022 } else { |
| 2023 throw new Exception('Unknown operating system: "$system"'); |
| 2024 } |
| 2025 return result; |
| 2026 } |
| 2027 |
| 2028 static List<String> standardOptions(Map configuration) { |
| 2029 var args = ["--ignore-unrecognized-flags"]; |
| 2030 var compiler = configuration["compiler"] as String; |
| 2031 if (compiler == "dart2js") { |
| 2032 args = ['--generate-code-with-compile-time-errors', '--test-mode']; |
| 2033 if (configuration["checked"] as bool) { |
| 2034 args.add('--enable-checked-mode'); |
| 2035 } |
| 2036 // args.add("--verbose"); |
| 2037 if (!isBrowserRuntime(configuration['runtime'] as String)) { |
| 2038 args.add("--allow-mock-compilation"); |
| 2039 args.add("--categories=all"); |
| 2040 } |
| 2041 } |
| 2042 if ((compiler == "dart2js") && (configuration["minified"] as bool)) { |
| 2043 args.add("--minify"); |
| 2044 } |
| 2045 if (compiler == "dart2js" && (configuration["csp"] as bool)) { |
| 2046 args.add("--csp"); |
| 2047 } |
| 2048 if (compiler == "dart2js" && (configuration["fast_startup"] as bool)) { |
| 2049 args.add("--fast-startup"); |
| 2050 } |
| 2051 if (compiler == "dart2js" && |
| 2052 (configuration["dart2js_with_kernel"] as bool)) { |
| 2053 args.add("--use-kernel"); |
| 2054 } |
| 2055 return args; |
| 2056 } |
| 2057 |
| 2058 static bool isBrowserRuntime(String runtime) { |
| 2059 const BROWSERS = const [ |
| 2060 'drt', |
| 2061 'dartium', |
| 2062 'ie9', |
| 2063 'ie10', |
| 2064 'ie11', |
| 2065 'safari', |
| 2066 'opera', |
| 2067 'chrome', |
| 2068 'ff', |
| 2069 'chromeOnAndroid', |
| 2070 'safarimobilesim', |
| 2071 'ContentShellOnAndroid', |
| 2072 'DartiumOnAndroid' |
| 2073 ]; |
| 2074 return BROWSERS.contains(runtime); |
| 2075 } |
| 2076 |
| 2077 static bool isJsCommandLineRuntime(String runtime) => |
| 2078 const ['d8', 'jsshell'].contains(runtime); |
| 2079 |
| 2080 static bool isCommandLineAnalyzer(String compiler) => |
| 2081 compiler == 'dart2analyzer'; |
| 2082 |
| 2083 static String buildDir(Map configuration) { |
| 2084 // FIXME(kustermann,ricow): Our code assumes that the returned 'buildDir' |
| 2085 // is relative to the current working directory. |
| 2086 // Thus, if we pass in an absolute path (e.g. '--build-directory=/tmp/out') |
| 2087 // we get into trouble. |
| 2088 if (configuration['build_directory'] == '') { |
| 2089 configuration['configuration_directory'] = |
| 2090 configurationDir(configuration); |
| 2091 configuration['build_directory'] = outputDir(configuration) + |
| 2092 (configuration['configuration_directory'] as String); |
| 2093 } |
| 2094 return configuration['build_directory'] as String; |
| 2095 } |
| 2096 |
| 2097 static String configurationDir(Map configuration) { |
| 2098 // This returns the correct configuration directory (the last component |
| 2099 // of the output directory path) for regular dart checkouts. |
| 2100 // Dartium checkouts use the --build-directory option to pass in the |
| 2101 // correct build directory explicitly. |
| 2102 // We allow our code to have been cross compiled, i.e., that there |
| 2103 // is an X in front of the arch. We don't allow both a cross compiled |
| 2104 // and a normal version to be present (except if you specifically pass |
| 2105 // in the build_directory). |
| 2106 String mode; |
| 2107 switch (configuration['mode'] as String) { |
| 2108 case 'debug': |
| 2109 mode = 'Debug'; |
| 2110 break; |
| 2111 case 'release': |
| 2112 mode = 'Release'; |
| 2113 break; |
| 2114 case 'product': |
| 2115 mode = 'Product'; |
| 2116 break; |
| 2117 default: |
| 2118 throw 'Unrecognized mode configuration: ${configuration['mode']}'; |
| 2119 } |
| 2120 String os; |
| 2121 switch (configuration['system'] as String) { |
| 2122 case 'android': |
| 2123 os = 'Android'; |
| 2124 break; |
| 2125 case 'fuchsia': |
| 2126 case 'linux': |
| 2127 case 'macos': |
| 2128 case 'windows': |
| 2129 os = ''; |
| 2130 break; |
| 2131 default: |
| 2132 throw 'Unrecognized operating system: ${configuration['system']}'; |
| 2133 } |
| 2134 var arch = (configuration['arch'] as String).toUpperCase(); |
| 2135 var normal = '$mode$os$arch'; |
| 2136 var cross = '$mode${os}X$arch'; |
| 2137 var outDir = outputDir(configuration); |
| 2138 var normalDir = new Directory(new Path('$outDir$normal').toNativePath()); |
| 2139 var crossDir = new Directory(new Path('$outDir$cross').toNativePath()); |
| 2140 if (normalDir.existsSync() && crossDir.existsSync()) { |
| 2141 throw "You can't have both $normalDir and $crossDir, we don't know which" |
| 2142 " binary to use"; |
| 2143 } |
| 2144 if (crossDir.existsSync()) { |
| 2145 return cross; |
| 2146 } |
| 2147 return normal; |
| 2148 } |
| 2149 |
| 2150 /** |
| 2151 * Gets extra options under [key] passed to the testing script. |
| 2152 */ |
| 2153 static List<String> getExtraOptions(Map configuration, String key) { |
| 2154 if (configuration[key] == null) return <String>[]; |
| 2155 return (configuration[key] as String) |
| 2156 .split(" ") |
| 2157 .map((s) => s.trim()) |
| 2158 .where((s) => s.isNotEmpty) |
| 2159 .toList(); |
| 2160 } |
| 2161 |
| 2162 /** |
| 2163 * Gets extra vm options passed to the testing script. |
| 2164 */ |
| 2165 static List<String> getExtraVmOptions(Map configuration) => |
| 2166 getExtraOptions(configuration, 'vm_options'); |
| 2167 |
2003 static int shortNameCounter = 0; // Make unique short file names on Windows. | 2168 static int shortNameCounter = 0; // Make unique short file names on Windows. |
2004 | 2169 |
2005 static String getShortName(String path) { | 2170 static String getShortName(String path) { |
2006 final PATH_REPLACEMENTS = const { | 2171 final PATH_REPLACEMENTS = const { |
2007 "pkg_polymer_e2e_test_bad_import_test": "polymer_bi", | 2172 "pkg_polymer_e2e_test_bad_import_test": "polymer_bi", |
2008 "pkg_polymer_e2e_test_canonicalization_test": "polymer_c16n", | 2173 "pkg_polymer_e2e_test_canonicalization_test": "polymer_c16n", |
2009 "pkg_polymer_e2e_test_experimental_boot_test": "polymer_boot", | 2174 "pkg_polymer_e2e_test_experimental_boot_test": "polymer_boot", |
2010 "pkg_polymer_e2e_test_good_import_test": "polymer_gi", | 2175 "pkg_polymer_e2e_test_good_import_test": "polymer_gi", |
2011 "tests_co19_src_Language_12_Expressions_14_Function_Invocation_": | 2176 "tests_co19_src_Language_12_Expressions_14_Function_Invocation_": |
2012 "co19_fn_invoke_", | 2177 "co19_fn_invoke_", |
(...skipping 63 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2076 } | 2241 } |
2077 if (path.length > WINDOWS_SHORTEN_PATH_LIMIT) { | 2242 if (path.length > WINDOWS_SHORTEN_PATH_LIMIT) { |
2078 ++shortNameCounter; | 2243 ++shortNameCounter; |
2079 var pathEnd = path.substring(path.length - WINDOWS_PATH_END_LENGTH); | 2244 var pathEnd = path.substring(path.length - WINDOWS_PATH_END_LENGTH); |
2080 path = "short${shortNameCounter}_$pathEnd"; | 2245 path = "short${shortNameCounter}_$pathEnd"; |
2081 } | 2246 } |
2082 } | 2247 } |
2083 return path; | 2248 return path; |
2084 } | 2249 } |
2085 } | 2250 } |
OLD | NEW |