OLD | NEW |
1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2013, 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 library browser; | 4 library browser; |
5 | 5 |
6 import "dart:async"; | 6 import "dart:async"; |
7 import "dart:convert" show UTF8, JSON; | 7 import "dart:convert" show UTF8, JSON; |
8 import "dart:core"; | 8 import "dart:core"; |
9 import "dart:io"; | 9 import "dart:io"; |
10 import "dart:math" show min; | 10 import "dart:math" show min; |
11 | 11 |
12 import 'android.dart'; | 12 import 'android.dart'; |
13 import 'http_server.dart'; | 13 import 'http_server.dart'; |
14 import 'path.dart'; | 14 import 'path.dart'; |
15 import 'utils.dart'; | 15 import 'utils.dart'; |
16 | 16 |
17 import 'reset_safari.dart' show killAndResetSafari; | 17 import 'reset_safari.dart' show killAndResetSafari; |
18 | 18 |
| 19 typedef void BrowserDoneCallback(BrowserTestOutput output); |
| 20 typedef void TestChangedCallback(String browserId, String output, int testId); |
| 21 typedef BrowserTest NextTestCallback(String browserId); |
| 22 |
19 class BrowserOutput { | 23 class BrowserOutput { |
20 final StringBuffer stdout = new StringBuffer(); | 24 final StringBuffer stdout = new StringBuffer(); |
21 final StringBuffer stderr = new StringBuffer(); | 25 final StringBuffer stderr = new StringBuffer(); |
22 final StringBuffer eventLog = new StringBuffer(); | 26 final StringBuffer eventLog = new StringBuffer(); |
23 } | 27 } |
24 | 28 |
25 /** Class describing the interface for communicating with browsers. */ | 29 /** Class describing the interface for communicating with browsers. */ |
26 abstract class Browser { | 30 abstract class Browser { |
27 BrowserOutput _allBrowserOutput = new BrowserOutput(); | 31 BrowserOutput _allBrowserOutput = new BrowserOutput(); |
28 BrowserOutput _testBrowserOutput = new BrowserOutput(); | 32 BrowserOutput _testBrowserOutput = new BrowserOutput(); |
(...skipping 35 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
64 bool debugPrint = false; | 68 bool debugPrint = false; |
65 | 69 |
66 // This future returns when the process exits. It is also the return value | 70 // This future returns when the process exits. It is also the return value |
67 // of close() | 71 // of close() |
68 Future done; | 72 Future done; |
69 | 73 |
70 Browser(); | 74 Browser(); |
71 | 75 |
72 factory Browser.byName(String name, String executablePath, | 76 factory Browser.byName(String name, String executablePath, |
73 [bool checkedMode = false]) { | 77 [bool checkedMode = false]) { |
74 var browser; | 78 Browser browser; |
75 if (name == 'firefox') { | 79 if (name == 'firefox') { |
76 browser = new Firefox(); | 80 browser = new Firefox(); |
77 } else if (name == 'chrome') { | 81 } else if (name == 'chrome') { |
78 browser = new Chrome(); | 82 browser = new Chrome(); |
79 } else if (name == 'dartium') { | 83 } else if (name == 'dartium') { |
80 browser = new Dartium(checkedMode); | 84 browser = new Dartium(checkedMode); |
81 } else if (name == 'safari') { | 85 } else if (name == 'safari') { |
82 browser = new Safari(); | 86 browser = new Safari(); |
83 } else if (name == 'safarimobilesim') { | 87 } else if (name == 'safarimobilesim') { |
84 browser = new SafariMobileSimulator(); | 88 browser = new SafariMobileSimulator(); |
(...skipping 80 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
165 */ | 169 */ |
166 Future<bool> startBrowserProcess(String command, List<String> arguments, | 170 Future<bool> startBrowserProcess(String command, List<String> arguments, |
167 {Map<String, String> environment}) { | 171 {Map<String, String> environment}) { |
168 return Process | 172 return Process |
169 .start(command, arguments, environment: environment) | 173 .start(command, arguments, environment: environment) |
170 .then((startedProcess) { | 174 .then((startedProcess) { |
171 _logEvent("Started browser using $command ${arguments.join(' ')}"); | 175 _logEvent("Started browser using $command ${arguments.join(' ')}"); |
172 process = startedProcess; | 176 process = startedProcess; |
173 // Used to notify when exiting, and as a return value on calls to | 177 // Used to notify when exiting, and as a return value on calls to |
174 // close(). | 178 // close(). |
175 var doneCompleter = new Completer(); | 179 var doneCompleter = new Completer<bool>(); |
176 done = doneCompleter.future; | 180 done = doneCompleter.future; |
177 | 181 |
178 Completer stdoutDone = new Completer(); | 182 Completer stdoutDone = new Completer<Null>(); |
179 Completer stderrDone = new Completer(); | 183 Completer stderrDone = new Completer<Null>(); |
180 | 184 |
181 bool stdoutIsDone = false; | 185 bool stdoutIsDone = false; |
182 bool stderrIsDone = false; | 186 bool stderrIsDone = false; |
183 StreamSubscription stdoutSubscription; | 187 StreamSubscription stdoutSubscription; |
184 StreamSubscription stderrSubscription; | 188 StreamSubscription stderrSubscription; |
185 | 189 |
186 // This timer is used to close stdio to the subprocess once we got | 190 // This timer is used to close stdio to the subprocess once we got |
187 // the exitCode. Sometimes descendants of the subprocess keep stdio | 191 // the exitCode. Sometimes descendants of the subprocess keep stdio |
188 // handles alive even though the direct subprocess is dead. | 192 // handles alive even though the direct subprocess is dead. |
189 Timer watchdogTimer; | 193 Timer watchdogTimer; |
(...skipping 106 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
296 static const String versionFile = | 300 static const String versionFile = |
297 "/Applications/Safari.app/Contents/version.plist"; | 301 "/Applications/Safari.app/Contents/version.plist"; |
298 | 302 |
299 static const String safariBundleLocation = "/Applications/Safari.app/"; | 303 static const String safariBundleLocation = "/Applications/Safari.app/"; |
300 | 304 |
301 // Clears the cache if the static resetBrowserConfiguration flag is set. | 305 // Clears the cache if the static resetBrowserConfiguration flag is set. |
302 // Returns false if the command to actually clear the cache did not complete. | 306 // Returns false if the command to actually clear the cache did not complete. |
303 Future<bool> resetConfiguration() async { | 307 Future<bool> resetConfiguration() async { |
304 if (!Browser.resetBrowserConfiguration) return true; | 308 if (!Browser.resetBrowserConfiguration) return true; |
305 | 309 |
306 Completer completer = new Completer(); | 310 var completer = new Completer<Null>(); |
307 handleUncaughtError(error, StackTrace stackTrace) { | 311 handleUncaughtError(error, StackTrace stackTrace) { |
308 if (!completer.isCompleted) { | 312 if (!completer.isCompleted) { |
309 completer.completeError(error, stackTrace); | 313 completer.completeError(error, stackTrace); |
310 } else { | 314 } else { |
311 throw new AsyncError(error, stackTrace); | 315 throw new AsyncError(error, stackTrace); |
312 } | 316 } |
313 } | 317 } |
314 | 318 |
315 Zone parent = Zone.current; | 319 Zone parent = Zone.current; |
316 ZoneSpecification specification = new ZoneSpecification( | 320 ZoneSpecification specification = new ZoneSpecification( |
(...skipping 49 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
366 for (var line in content) { | 370 for (var line in content) { |
367 if (versionOnNextLine) return line; | 371 if (versionOnNextLine) return line; |
368 if (line.contains("CFBundleShortVersionString")) { | 372 if (line.contains("CFBundleShortVersionString")) { |
369 versionOnNextLine = true; | 373 versionOnNextLine = true; |
370 } | 374 } |
371 } | 375 } |
372 return null; | 376 return null; |
373 }); | 377 }); |
374 } | 378 } |
375 | 379 |
376 Future<Null> _createLaunchHTML(var path, var url) async { | 380 Future<Null> _createLaunchHTML(String path, String url) async { |
377 var file = new File("${path}/launch.html"); | 381 var file = new File("$path/launch.html"); |
378 var randomFile = await file.open(mode: FileMode.WRITE); | 382 var randomFile = await file.open(mode: FileMode.WRITE); |
379 var content = '<script language="JavaScript">location = "$url"</script>'; | 383 var content = '<script language="JavaScript">location = "$url"</script>'; |
380 await randomFile.writeString(content); | 384 await randomFile.writeString(content); |
381 await randomFile.close(); | 385 await randomFile.close(); |
382 } | 386 } |
383 | 387 |
384 Future<bool> start(String url) async { | 388 Future<bool> start(String url) async { |
385 _logEvent("Starting Safari browser on: $url"); | 389 _logEvent("Starting Safari browser on: $url"); |
386 if (!await resetConfiguration()) { | 390 if (!await resetConfiguration()) { |
387 _logEvent("Could not clear cache"); | 391 _logEvent("Could not clear cache"); |
(...skipping 274 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
662 'android.intent.action.VIEW'); | 666 'android.intent.action.VIEW'); |
663 | 667 |
664 final dartiumOnAndroidConfig = new AndroidBrowserConfig('DartiumOnAndroid', | 668 final dartiumOnAndroidConfig = new AndroidBrowserConfig('DartiumOnAndroid', |
665 'com.google.android.apps.chrome', '.Main', 'android.intent.action.VIEW'); | 669 'com.google.android.apps.chrome', '.Main', 'android.intent.action.VIEW'); |
666 | 670 |
667 class AndroidBrowser extends Browser { | 671 class AndroidBrowser extends Browser { |
668 final bool checkedMode; | 672 final bool checkedMode; |
669 AdbDevice _adbDevice; | 673 AdbDevice _adbDevice; |
670 AndroidBrowserConfig _config; | 674 AndroidBrowserConfig _config; |
671 | 675 |
672 AndroidBrowser(this._adbDevice, this._config, this.checkedMode, apkPath) { | 676 AndroidBrowser( |
| 677 this._adbDevice, this._config, this.checkedMode, String apkPath) { |
673 _binary = apkPath; | 678 _binary = apkPath; |
674 } | 679 } |
675 | 680 |
676 Future<bool> start(String url) { | 681 Future<bool> start(String url) { |
677 var intent = | 682 var intent = |
678 new Intent(_config.action, _config.package, _config.activity, url); | 683 new Intent(_config.action, _config.package, _config.activity, url); |
679 return _adbDevice.waitForBootCompleted().then((_) { | 684 return _adbDevice.waitForBootCompleted().then((_) { |
680 return _adbDevice.forceStop(_config.package); | 685 return _adbDevice.forceStop(_config.package); |
681 }).then((_) { | 686 }).then((_) { |
682 return _adbDevice.killAll(); | 687 return _adbDevice.killAll(); |
(...skipping 104 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
787 } | 792 } |
788 | 793 |
789 class Firefox extends Browser { | 794 class Firefox extends Browser { |
790 static const String enablePopUp = | 795 static const String enablePopUp = |
791 'user_pref("dom.disable_open_during_load", false);'; | 796 'user_pref("dom.disable_open_during_load", false);'; |
792 static const String disableDefaultCheck = | 797 static const String disableDefaultCheck = |
793 'user_pref("browser.shell.checkDefaultBrowser", false);'; | 798 'user_pref("browser.shell.checkDefaultBrowser", false);'; |
794 static const String disableScriptTimeLimit = | 799 static const String disableScriptTimeLimit = |
795 'user_pref("dom.max_script_run_time", 0);'; | 800 'user_pref("dom.max_script_run_time", 0);'; |
796 | 801 |
797 void _createPreferenceFile(var path) { | 802 void _createPreferenceFile(String path) { |
798 var file = new File("${path.toString()}/user.js"); | 803 var file = new File("$path/user.js"); |
799 var randomFile = file.openSync(mode: FileMode.WRITE); | 804 var randomFile = file.openSync(mode: FileMode.WRITE); |
800 randomFile.writeStringSync(enablePopUp); | 805 randomFile.writeStringSync(enablePopUp); |
801 randomFile.writeStringSync(disableDefaultCheck); | 806 randomFile.writeStringSync(disableDefaultCheck); |
802 randomFile.writeStringSync(disableScriptTimeLimit); | 807 randomFile.writeStringSync(disableScriptTimeLimit); |
803 randomFile.close(); | 808 randomFile.close(); |
804 } | 809 } |
805 | 810 |
806 Future<bool> start(String url) { | 811 Future<bool> start(String url) { |
807 _logEvent("Starting firefox browser on: $url"); | 812 _logEvent("Starting firefox browser on: $url"); |
808 // Get the version and log that. | 813 // Get the version and log that. |
(...skipping 47 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
856 Stopwatch timeSinceRestart = new Stopwatch()..start(); | 861 Stopwatch timeSinceRestart = new Stopwatch()..start(); |
857 | 862 |
858 BrowserStatus(Browser this.browser); | 863 BrowserStatus(Browser this.browser); |
859 } | 864 } |
860 | 865 |
861 /** | 866 /** |
862 * Describes a single test to be run in the browser. | 867 * Describes a single test to be run in the browser. |
863 */ | 868 */ |
864 class BrowserTest { | 869 class BrowserTest { |
865 // TODO(ricow): Add timeout callback instead of the string passing hack. | 870 // TODO(ricow): Add timeout callback instead of the string passing hack. |
866 Function doneCallback; | 871 BrowserDoneCallback doneCallback; |
867 String url; | 872 String url; |
868 int timeout; | 873 int timeout; |
869 String lastKnownMessage = ''; | 874 String lastKnownMessage = ''; |
870 Stopwatch stopwatch; | 875 Stopwatch stopwatch; |
871 | 876 |
872 // This might be null | 877 // This might be null |
873 Duration delayUntilTestStarted; | 878 Duration delayUntilTestStarted; |
874 | 879 |
875 // We store this here for easy access when tests time out (instead of | 880 // We store this here for easy access when tests time out (instead of |
876 // capturing this in a closure) | 881 // capturing this in a closure) |
(...skipping 10 matching lines...) Expand all Loading... |
887 | 892 |
888 String toJSON() => JSON.encode({'url': url, 'id': id, 'isHtmlTest': false}); | 893 String toJSON() => JSON.encode({'url': url, 'id': id, 'isHtmlTest': false}); |
889 } | 894 } |
890 | 895 |
891 /** | 896 /** |
892 * Describes a test with a custom HTML page to be run in the browser. | 897 * Describes a test with a custom HTML page to be run in the browser. |
893 */ | 898 */ |
894 class HtmlTest extends BrowserTest { | 899 class HtmlTest extends BrowserTest { |
895 List<String> expectedMessages; | 900 List<String> expectedMessages; |
896 | 901 |
897 HtmlTest(url, doneCallback, timeout, this.expectedMessages) | 902 HtmlTest(String url, BrowserDoneCallback doneCallback, int timeout, |
| 903 this.expectedMessages) |
898 : super(url, doneCallback, timeout) {} | 904 : super(url, doneCallback, timeout) {} |
899 | 905 |
900 String toJSON() => JSON.encode({ | 906 String toJSON() => JSON.encode({ |
901 'url': url, | 907 'url': url, |
902 'id': id, | 908 'id': id, |
903 'isHtmlTest': true, | 909 'isHtmlTest': true, |
904 'expectedMessages': expectedMessages | 910 'expectedMessages': expectedMessages |
905 }); | 911 }); |
906 } | 912 } |
907 | 913 |
(...skipping 22 matching lines...) Expand all Loading... |
930 /// driver page to the browsers, serves tests, and receives results and | 936 /// driver page to the browsers, serves tests, and receives results and |
931 /// requests back from the browsers. | 937 /// requests back from the browsers. |
932 class BrowserTestRunner { | 938 class BrowserTestRunner { |
933 static const int MAX_NEXT_TEST_TIMEOUTS = 10; | 939 static const int MAX_NEXT_TEST_TIMEOUTS = 10; |
934 static const Duration NEXT_TEST_TIMEOUT = const Duration(seconds: 120); | 940 static const Duration NEXT_TEST_TIMEOUT = const Duration(seconds: 120); |
935 static const Duration RESTART_BROWSER_INTERVAL = const Duration(seconds: 60); | 941 static const Duration RESTART_BROWSER_INTERVAL = const Duration(seconds: 60); |
936 | 942 |
937 /// If the queue was recently empty, don't start another browser. | 943 /// If the queue was recently empty, don't start another browser. |
938 static const Duration MIN_NONEMPTY_QUEUE_TIME = const Duration(seconds: 1); | 944 static const Duration MIN_NONEMPTY_QUEUE_TIME = const Duration(seconds: 1); |
939 | 945 |
940 final Map configuration; | 946 final Map<String, String> configuration; |
941 final BrowserTestingServer testingServer; | 947 final BrowserTestingServer testingServer; |
942 | 948 |
943 final String localIp; | 949 final String localIp; |
944 final String browserName; | 950 final String browserName; |
945 int maxNumBrowsers; | 951 int maxNumBrowsers; |
946 final bool checkedMode; | 952 final bool checkedMode; |
947 int numBrowsers = 0; | 953 int numBrowsers = 0; |
948 // Used to send back logs from the browser (start, stop etc) | 954 // Used to send back logs from the browser (start, stop etc) |
949 Function logger; | 955 Function logger; |
950 | 956 |
(...skipping 309 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1260 } | 1266 } |
1261 | 1267 |
1262 /// Creates a timer that is active while no test is running on the | 1268 /// Creates a timer that is active while no test is running on the |
1263 /// browser. It has finished one test, and it has not requested a new test. | 1269 /// browser. It has finished one test, and it has not requested a new test. |
1264 Timer createNextTestTimer(BrowserStatus status) { | 1270 Timer createNextTestTimer(BrowserStatus status) { |
1265 return new Timer(BrowserTestRunner.NEXT_TEST_TIMEOUT, () { | 1271 return new Timer(BrowserTestRunner.NEXT_TEST_TIMEOUT, () { |
1266 handleNextTestTimeout(status); | 1272 handleNextTestTimeout(status); |
1267 }); | 1273 }); |
1268 } | 1274 } |
1269 | 1275 |
1270 void handleNextTestTimeout(status) { | 1276 void handleNextTestTimeout(BrowserStatus status) { |
1271 DebugLogger | 1277 DebugLogger |
1272 .warning("Browser timed out before getting next test. Restarting"); | 1278 .warning("Browser timed out before getting next test. Restarting"); |
1273 if (status.timeout) return; | 1279 if (status.timeout) return; |
1274 numBrowserGetTestTimeouts++; | 1280 numBrowserGetTestTimeouts++; |
1275 if (numBrowserGetTestTimeouts >= MAX_NEXT_TEST_TIMEOUTS) { | 1281 if (numBrowserGetTestTimeouts >= MAX_NEXT_TEST_TIMEOUTS) { |
1276 DebugLogger.error( | 1282 DebugLogger.error( |
1277 "Too many browser timeouts before getting next test. Terminating"); | 1283 "Too many browser timeouts before getting next test. Terminating"); |
1278 terminate().then((_) => exit(1)); | 1284 terminate().then((_) => exit(1)); |
1279 } else { | 1285 } else { |
1280 status.timeout = true; | 1286 status.timeout = true; |
(...skipping 25 matching lines...) Expand all Loading... |
1306 DebugLogger.warning("${testCache[id]}, output: "); | 1312 DebugLogger.warning("${testCache[id]}, output: "); |
1307 DebugLogger.warning("${doubleReportingOutputs[id]}"); | 1313 DebugLogger.warning("${doubleReportingOutputs[id]}"); |
1308 DebugLogger.warning(""); | 1314 DebugLogger.warning(""); |
1309 DebugLogger.warning(""); | 1315 DebugLogger.warning(""); |
1310 } | 1316 } |
1311 } | 1317 } |
1312 | 1318 |
1313 // TODO(26191): Call a unified fatalError(), that shuts down all subprocesses. | 1319 // TODO(26191): Call a unified fatalError(), that shuts down all subprocesses. |
1314 // This just kills the browsers in this BrowserTestRunner instance. | 1320 // This just kills the browsers in this BrowserTestRunner instance. |
1315 Future terminate() async { | 1321 Future terminate() async { |
1316 var browsers = []; | 1322 var browsers = <Browser>[]; |
1317 underTermination = true; | 1323 underTermination = true; |
1318 testingServer.underTermination = true; | 1324 testingServer.underTermination = true; |
1319 for (BrowserStatus status in browserStatus.values) { | 1325 for (BrowserStatus status in browserStatus.values) { |
1320 browsers.add(status.browser); | 1326 browsers.add(status.browser); |
1321 if (status.nextTestTimeout != null) { | 1327 if (status.nextTestTimeout != null) { |
1322 status.nextTestTimeout.cancel(); | 1328 status.nextTestTimeout.cancel(); |
1323 status.nextTestTimeout = null; | 1329 status.nextTestTimeout = null; |
1324 } | 1330 } |
1325 } | 1331 } |
1326 for (Browser b in browsers) { | 1332 |
1327 await b.close(); | 1333 for (var browser in browsers) { |
| 1334 await browser.close(); |
1328 } | 1335 } |
| 1336 |
1329 testingServer.errorReportingServer.close(); | 1337 testingServer.errorReportingServer.close(); |
1330 printDoubleReportingTests(); | 1338 printDoubleReportingTests(); |
1331 } | 1339 } |
1332 } | 1340 } |
1333 | 1341 |
1334 class BrowserTestingServer { | 1342 class BrowserTestingServer { |
1335 final Map configuration; | 1343 final Map configuration; |
1336 | 1344 |
1337 /// Interface of the testing server: | 1345 /// Interface of the testing server: |
1338 /// | 1346 /// |
(...skipping 14 matching lines...) Expand all Loading... |
1353 | 1361 |
1354 static const String driverPath = "/driver"; | 1362 static const String driverPath = "/driver"; |
1355 static const String nextTestPath = "/next_test"; | 1363 static const String nextTestPath = "/next_test"; |
1356 static const String reportPath = "/report"; | 1364 static const String reportPath = "/report"; |
1357 static const String statusUpdatePath = "/status_update"; | 1365 static const String statusUpdatePath = "/status_update"; |
1358 static const String startedPath = "/started"; | 1366 static const String startedPath = "/started"; |
1359 static const String waitSignal = "WAIT"; | 1367 static const String waitSignal = "WAIT"; |
1360 static const String terminateSignal = "TERMINATE"; | 1368 static const String terminateSignal = "TERMINATE"; |
1361 | 1369 |
1362 var testCount = 0; | 1370 var testCount = 0; |
1363 var errorReportingServer; | 1371 HttpServer errorReportingServer; |
1364 bool underTermination = false; | 1372 bool underTermination = false; |
1365 | 1373 |
1366 Function testDoneCallBack; | 1374 TestChangedCallback testDoneCallBack; |
1367 Function testStatusUpdateCallBack; | 1375 TestChangedCallback testStatusUpdateCallBack; |
1368 Function testStartedCallBack; | 1376 TestChangedCallback testStartedCallBack; |
1369 Function nextTestCallBack; | 1377 NextTestCallback nextTestCallBack; |
1370 | 1378 |
1371 BrowserTestingServer( | 1379 BrowserTestingServer( |
1372 this.configuration, this.localIp, this.useIframe, this.requiresFocus); | 1380 this.configuration, this.localIp, this.useIframe, this.requiresFocus); |
1373 | 1381 |
1374 Future start() { | 1382 Future start() { |
1375 var test_driver_error_port = configuration['test_driver_error_port']; | 1383 var testDriverErrorPort = configuration['test_driver_error_port']; |
1376 return HttpServer | 1384 return HttpServer |
1377 .bind(localIp, test_driver_error_port) | 1385 .bind(localIp, testDriverErrorPort) |
1378 .then(setupErrorServer) | 1386 .then(setupErrorServer) |
1379 .then(setupDispatchingServer); | 1387 .then(setupDispatchingServer); |
1380 } | 1388 } |
1381 | 1389 |
1382 void setupErrorServer(HttpServer server) { | 1390 void setupErrorServer(HttpServer server) { |
1383 errorReportingServer = server; | 1391 errorReportingServer = server; |
1384 void errorReportingHandler(HttpRequest request) { | 1392 void errorReportingHandler(HttpRequest request) { |
1385 StringBuffer buffer = new StringBuffer(); | 1393 StringBuffer buffer = new StringBuffer(); |
1386 request.transform(UTF8.decoder).listen((data) { | 1394 request.transform(UTF8.decoder).listen((data) { |
1387 buffer.write(data); | 1395 buffer.write(data); |
(...skipping 14 matching lines...) Expand all Loading... |
1402 | 1410 |
1403 void errorHandler(e) { | 1411 void errorHandler(e) { |
1404 if (!underTermination) print("Error occured in httpserver: $e"); | 1412 if (!underTermination) print("Error occured in httpserver: $e"); |
1405 } | 1413 } |
1406 | 1414 |
1407 errorReportingServer.listen(errorReportingHandler, onError: errorHandler); | 1415 errorReportingServer.listen(errorReportingHandler, onError: errorHandler); |
1408 } | 1416 } |
1409 | 1417 |
1410 void setupDispatchingServer(_) { | 1418 void setupDispatchingServer(_) { |
1411 DispatchingServer server = configuration['_servers_'].server; | 1419 DispatchingServer server = configuration['_servers_'].server; |
1412 void noCache(request) { | 1420 void noCache(HttpRequest request) { |
1413 request.response.headers | 1421 request.response.headers |
1414 .set("Cache-Control", "no-cache, no-store, must-revalidate"); | 1422 .set("Cache-Control", "no-cache, no-store, must-revalidate"); |
1415 } | 1423 } |
1416 | 1424 |
1417 int testId(request) => int.parse(request.uri.queryParameters["id"]); | 1425 int testId(HttpRequest request) => |
1418 String browserId(request, prefix) => | 1426 int.parse(request.uri.queryParameters["id"]); |
| 1427 String browserId(HttpRequest request, String prefix) => |
1419 request.uri.path.substring(prefix.length + 1); | 1428 request.uri.path.substring(prefix.length + 1); |
1420 | 1429 |
1421 server.addHandler(reportPath, (HttpRequest request) { | 1430 server.addHandler(reportPath, (HttpRequest request) { |
1422 noCache(request); | 1431 noCache(request); |
1423 handleReport(request, browserId(request, reportPath), testId(request), | 1432 handleReport(request, browserId(request, reportPath), testId(request), |
1424 isStatusUpdate: false); | 1433 isStatusUpdate: false); |
1425 }); | 1434 }); |
1426 server.addHandler(statusUpdatePath, (HttpRequest request) { | 1435 server.addHandler(statusUpdatePath, (HttpRequest request) { |
1427 noCache(request); | 1436 noCache(request); |
1428 handleReport( | 1437 handleReport( |
(...skipping 35 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1464 // Ignoring the returned closure as it returns the 'done' future | 1473 // Ignoring the returned closure as it returns the 'done' future |
1465 // which already has catchError installed above. | 1474 // which already has catchError installed above. |
1466 request.response.close(); | 1475 request.response.close(); |
1467 }); | 1476 }); |
1468 } | 1477 } |
1469 | 1478 |
1470 server.addHandler(driverPath, sendPageHandler); | 1479 server.addHandler(driverPath, sendPageHandler); |
1471 server.addHandler(nextTestPath, sendPageHandler); | 1480 server.addHandler(nextTestPath, sendPageHandler); |
1472 } | 1481 } |
1473 | 1482 |
1474 void handleReport(HttpRequest request, String browserId, var testId, | 1483 void handleReport(HttpRequest request, String browserId, int testId, |
1475 {bool isStatusUpdate}) { | 1484 {bool isStatusUpdate}) { |
1476 StringBuffer buffer = new StringBuffer(); | 1485 StringBuffer buffer = new StringBuffer(); |
1477 request.transform(UTF8.decoder).listen((data) { | 1486 request.transform(UTF8.decoder).listen((data) { |
1478 buffer.write(data); | 1487 buffer.write(data); |
1479 }, onDone: () { | 1488 }, onDone: () { |
1480 String back = buffer.toString(); | 1489 String back = buffer.toString(); |
1481 request.response.close(); | 1490 request.response.close(); |
1482 if (isStatusUpdate) { | 1491 if (isStatusUpdate) { |
1483 testStatusUpdateCallBack(browserId, back, testId); | 1492 testStatusUpdateCallBack(browserId, back, testId); |
1484 } else { | 1493 } else { |
1485 testDoneCallBack(browserId, back, testId); | 1494 testDoneCallBack(browserId, back, testId); |
1486 } | 1495 } |
1487 // TODO(ricow): We should do something smart if we get an error here. | 1496 // TODO(ricow): We should do something smart if we get an error here. |
1488 }, onError: (error) { | 1497 }, onError: (error) { |
1489 DebugLogger.error("$error"); | 1498 DebugLogger.error("$error"); |
1490 }); | 1499 }); |
1491 } | 1500 } |
1492 | 1501 |
1493 void handleStarted(HttpRequest request, String browserId, var testId) { | 1502 void handleStarted(HttpRequest request, String browserId, int testId) { |
1494 StringBuffer buffer = new StringBuffer(); | 1503 StringBuffer buffer = new StringBuffer(); |
1495 // If an error occurs while receiving the data from the request stream, | 1504 // If an error occurs while receiving the data from the request stream, |
1496 // we don't handle it specially. We can safely ignore it, since the started | 1505 // we don't handle it specially. We can safely ignore it, since the started |
1497 // events are not crucial. | 1506 // events are not crucial. |
1498 request.transform(UTF8.decoder).listen((data) { | 1507 request.transform(UTF8.decoder).listen((data) { |
1499 buffer.write(data); | 1508 buffer.write(data); |
1500 }, onDone: () { | 1509 }, onDone: () { |
1501 String back = buffer.toString(); | 1510 String back = buffer.toString(); |
1502 request.response.close(); | 1511 request.response.close(); |
1503 testStartedCallBack(browserId, back, testId); | 1512 testStartedCallBack(browserId, back, testId); |
(...skipping 433 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1937 'exit code: ${result.exitCode}\n' | 1946 'exit code: ${result.exitCode}\n' |
1938 'stdout: ${result.stdout}\n' | 1947 'stdout: ${result.stdout}\n' |
1939 'stderr: ${result.stderr}'); | 1948 'stderr: ${result.stderr}'); |
1940 } else { | 1949 } else { |
1941 print('[$message] Successfully uploaded screenshot to $storageUrl'); | 1950 print('[$message] Successfully uploaded screenshot to $storageUrl'); |
1942 } | 1951 } |
1943 new File(screenshotFile).deleteSync(); | 1952 new File(screenshotFile).deleteSync(); |
1944 } | 1953 } |
1945 print('--------------------------------------------------------------------'); | 1954 print('--------------------------------------------------------------------'); |
1946 } | 1955 } |
OLD | NEW |