Index: tests/standalone/packages_file_test.dart |
diff --git a/tests/standalone/packages_file_test.dart b/tests/standalone/packages_file_test.dart |
index 4d695eae5283ac4768547a75595358dcbbd799a0..c0c5d3980786f90eaa85afa1f7716a5d3036dc45 100644 |
--- a/tests/standalone/packages_file_test.dart |
+++ b/tests/standalone/packages_file_test.dart |
@@ -11,197 +11,202 @@ import "package:async_helper/async_helper.dart"; |
main() async { |
asyncStart(); |
- // The `test` function can generate file or http resources. |
- // It replaces "%file/" with URI of the root directory of generated files and |
- // "%http/" with the URI of the HTTP server's root in appropriate contexts |
- // (all file contents and parameters). |
- |
- // With no specified resolutiuon and no implicit .packages or packages/ |
- // available, nothing can be resolved and the package can't be imported. |
- await test("file: no resolution", |
- "%file/main.dart", |
- file: {"main": testMain}, |
- expect: {"foo.x": null}); |
- |
- // An HTTP script with no ".packages" file assumes a "packages" dir. |
- // All packages are resolved relative to that dir, whether it exists or not. |
- await test("http: no resolution", "%http/main.dart", |
- http: {"main": testMain}, |
- expect: { |
- "iroot": "%http/packages/", |
- // "foo": null, |
- "foo/": "%http/packages/foo/", |
- "foo/bar": "%http/packages/foo/bar", |
- "foo.x": null, |
- }); |
+ Future runTests(test) async { |
floitsch
2016/05/27 14:26:50
Move that function out. Should make the diff bette
|
+ // The `test` function can generate file or http resources. |
+ // It replaces "%file/" with URI of the root directory of generated files and |
floitsch
2016/05/27 14:26:50
Long line.
|
+ // "%http/" with the URI of the HTTP server's root in appropriate contexts |
+ // (all file contents and parameters). |
+ |
+ // With no specified resolutiuon and no implicit .packages or packages/ |
+ // available, nothing can be resolved and the package can't be imported. |
+ await test("file: no resolution", |
+ "%file/main.dart", |
+ file: {"main": testMain}, |
+ expect: {"foo.x": null}); |
+ |
+ // An HTTP script with no ".packages" file assumes a "packages" dir. |
+ // All packages are resolved relative to that dir, whether it exists or not. |
+ await test("http: no resolution", "%http/main.dart", |
+ http: {"main": testMain}, |
+ expect: { |
+ "iroot": "%http/packages/", |
+ // "foo": null, |
+ "foo/": "%http/packages/foo/", |
+ "foo/bar": "%http/packages/foo/bar", |
+ "foo.x": null, |
+ }); |
- // A number of tests which behave similarly whether run as local files or |
- // over HTTP. |
- for (var scheme in ["file", "http"]) { |
- |
- /// Run a test in the current scheme. |
- /// |
- /// The files are served either through HTTP or in a local directory. |
- /// Use "%$scheme/" to refer to the root of the served files. |
- testScheme(name, main, {expect, files, args, root, config}) { |
- return test("$scheme: $name", main, expect: expect, |
- root: root, config: config, args: args, |
- file: scheme == "file" ? files : null, |
- http: scheme == "http" ? files : null); |
- } |
+ // A number of tests which behave similarly whether run as local files or |
+ // over HTTP. |
+ for (var scheme in ["file", "http"]) { |
+ |
+ /// Run a test in the current scheme. |
+ /// |
+ /// The files are served either through HTTP or in a local directory. |
+ /// Use "%$scheme/" to refer to the root of the served files. |
+ testScheme(name, main, {expect, files, args, root, config}) { |
+ return test("$scheme: $name", main, expect: expect, |
+ root: root, config: config, args: args, |
+ file: scheme == "file" ? files : null, |
+ http: scheme == "http" ? files : null); |
+ } |
- { |
- var files = {"main": testMain, "packages": fooPackage}; |
- // Expect implicitly detected package dir. |
- await testScheme("implicit packages dir","%$scheme/main.dart", |
- files: files, |
- expect: { |
- "iroot": "%$scheme/packages/", |
- // "foo": null, |
- "foo/": "%$scheme/packages/foo/", |
- "foo/bar": "%$scheme/packages/foo/bar", |
- }); |
- } |
+ { |
+ var files = {"main": testMain, "packages": fooPackage}; |
+ // Expect implicitly detected package dir. |
+ await testScheme("implicit packages dir","%$scheme/main.dart", |
+ files: files, |
+ expect: { |
+ "iroot": "%$scheme/packages/", |
+ // "foo": null, |
+ "foo/": "%$scheme/packages/foo/", |
+ "foo/bar": "%$scheme/packages/foo/bar", |
+ }); |
+ } |
- { |
- var files = {"sub": {"main": testMain, "packages": fooPackage}, |
- ".packages": ""}; |
- // Expect implicitly detected package dir. |
- // Should not detect the .packages file in parent directory. |
- // That file is empty, so if it is used, the system cannot resolve "foo". |
- await testScheme("implicit packages dir 2", "%$scheme/sub/main.dart", |
- files: files, |
- expect: { |
- "iroot": "%$scheme/sub/packages/", |
- // "foo": null, |
- "foo/": "%$scheme/sub/packages/foo/", |
- "foo/bar": "%$scheme/sub/packages/foo/bar", |
- }); |
- } |
+ { |
+ var files = {"sub": {"main": testMain, "packages": fooPackage}, |
+ ".packages": ""}; |
+ // Expect implicitly detected package dir. |
+ // Should not detect the .packages file in parent directory. |
+ // That file is empty, so if it is used, the system cannot resolve "foo". |
+ await testScheme("implicit packages dir 2", "%$scheme/sub/main.dart", |
+ files: files, |
+ expect: { |
+ "iroot": "%$scheme/sub/packages/", |
+ // "foo": null, |
+ "foo/": "%$scheme/sub/packages/foo/", |
+ "foo/bar": "%$scheme/sub/packages/foo/bar", |
+ }); |
+ } |
- { |
- var files = {"main": testMain, |
- ".packages": "foo:pkgs/foo/", |
- "pkgs": fooPackage}; |
- await testScheme("implicit .packages file", "%$scheme/main.dart", |
- files: files, |
- expect: { |
- "iconf": "%$scheme/.packages", |
- // "foo": null, |
- "foo/": "%$scheme/pkgs/foo/", |
- "foo/bar": "%$scheme/pkgs/foo/bar", |
- }); |
- } |
+ { |
+ var files = {"main": testMain, |
+ ".packages": "foo:pkgs/foo/", |
+ "pkgs": fooPackage}; |
+ await testScheme("implicit .packages file", "%$scheme/main.dart", |
+ files: files, |
+ expect: { |
+ "iconf": "%$scheme/.packages", |
+ // "foo": null, |
+ "foo/": "%$scheme/pkgs/foo/", |
+ "foo/bar": "%$scheme/pkgs/foo/bar", |
+ }); |
+ } |
- { |
- var files = {"main": testMain, |
- ".packages": "foo:packages/foo/", |
- "packages": fooPackage, |
- "pkgs": fooPackage}; |
- await testScheme("explicit package root, no slash", "%$scheme/main.dart", |
- files: files, |
- root: "%$scheme/pkgs", |
- expect: { |
- "proot": "%$scheme/pkgs/", |
- "iroot": "%$scheme/pkgs/", |
- // "foo": null, |
- "foo/": "%$scheme/pkgs/foo/", |
- "foo/bar": "%$scheme/pkgs/foo/bar", |
- }); |
- } |
+ { |
+ var files = {"main": testMain, |
+ ".packages": "foo:packages/foo/", |
+ "packages": fooPackage, |
+ "pkgs": fooPackage}; |
+ await testScheme("explicit package root, no slash", "%$scheme/main.dart", |
+ files: files, |
+ root: "%$scheme/pkgs", |
+ expect: { |
+ "proot": "%$scheme/pkgs/", |
+ "iroot": "%$scheme/pkgs/", |
+ // "foo": null, |
+ "foo/": "%$scheme/pkgs/foo/", |
+ "foo/bar": "%$scheme/pkgs/foo/bar", |
+ }); |
+ } |
- { |
- var files = {"main": testMain, |
- ".packages": "foo:packages/foo/", |
- "packages": fooPackage, |
- "pkgs": fooPackage}; |
- await testScheme("explicit package root, slash", "%$scheme/main.dart", |
- files: files, |
- root: "%$scheme/pkgs", |
- expect: { |
- "proot": "%$scheme/pkgs/", |
- "iroot": "%$scheme/pkgs/", |
- // "foo": null, |
- "foo/": "%$scheme/pkgs/foo/", |
- "foo/bar": "%$scheme/pkgs/foo/bar", |
- }); |
+ { |
+ var files = {"main": testMain, |
+ ".packages": "foo:packages/foo/", |
+ "packages": fooPackage, |
+ "pkgs": fooPackage}; |
+ await testScheme("explicit package root, slash", "%$scheme/main.dart", |
+ files: files, |
+ root: "%$scheme/pkgs", |
+ expect: { |
+ "proot": "%$scheme/pkgs/", |
+ "iroot": "%$scheme/pkgs/", |
+ // "foo": null, |
+ "foo/": "%$scheme/pkgs/foo/", |
+ "foo/bar": "%$scheme/pkgs/foo/bar", |
+ }); |
+ } |
+ |
+ { |
+ var files = {"main": testMain, |
+ ".packages": "foo:packages/foo/", |
+ "packages": fooPackage, |
+ ".pkgs": "foo:pkgs/foo/", |
+ "pkgs": fooPackage}; |
+ await testScheme("explicit package config file", "%$scheme/main.dart", |
+ files: files, |
+ config: "%$scheme/.pkgs", |
+ expect: { |
+ "pconf": "%$scheme/.pkgs", |
+ "iconf": "%$scheme/.pkgs", |
+ // "foo": null, |
+ "foo/": "%$scheme/pkgs/foo/", |
+ "foo/bar": "%$scheme/pkgs/foo/bar", |
+ }); |
+ } |
+ |
+ { |
+ /// The package config can be specified as a data: URI. |
+ /// (In that case, relative URI references in the config file won't work). |
+ var files = {"main": testMain, |
+ ".packages": "foo:packages/foo/", |
+ "packages": fooPackage, |
+ "pkgs": fooPackage}; |
+ var dataUri = "data:,foo:%$scheme/pkgs/foo/\n"; |
+ await testScheme("explicit data: config file", "%$scheme/main.dart", |
+ files: files, |
+ config: dataUri, |
+ expect: { |
+ "pconf": dataUri, |
+ "iconf": dataUri, |
+ // "foo": null, |
+ "foo/": "%$scheme/pkgs/foo/", |
+ "foo/bar": "%$scheme/pkgs/foo/bar", |
+ }); |
+ } |
} |
{ |
- var files = {"main": testMain, |
- ".packages": "foo:packages/foo/", |
- "packages": fooPackage, |
- ".pkgs": "foo:pkgs/foo/", |
+ // With a file: URI, the lookup checks for a .packages file in superdirs |
+ // when it fails to find a ,packages file or packages/ directory next to |
+ // the entry point. |
+ var files = {"sub": { "main": testMain }, |
+ ".packages": "foo:pkgs/foo/", |
"pkgs": fooPackage}; |
- await testScheme("explicit package config file", "%$scheme/main.dart", |
- files: files, |
- config: "%$scheme/.pkgs", |
+ await test("file: implicit .packages file in ..", "%file/sub/main.dart", |
+ file: files, |
expect: { |
- "pconf": "%$scheme/.pkgs", |
- "iconf": "%$scheme/.pkgs", |
+ "iconf": "%file/.packages", |
// "foo": null, |
- "foo/": "%$scheme/pkgs/foo/", |
- "foo/bar": "%$scheme/pkgs/foo/bar", |
+ "foo/": "%file/pkgs/foo/", |
+ "foo/bar": "%file/pkgs/foo/bar", |
}); |
} |
{ |
- /// The package config can be specified as a data: URI. |
- /// (In that case, relative URI references in the config file won't work). |
- var files = {"main": testMain, |
- ".packages": "foo:packages/foo/", |
- "packages": fooPackage, |
+ // With a non-file: URI, the lookup assumes a packges/ dir. |
+ // The absence of a .packages file next to the entry point means |
+ // that the resolution assumes a packages directory, whether it exists or |
+ // not. It should not find the .packages file in the parent directory. |
+ var files = {"sub": { "main": testMain }, |
+ ".packages": "foo:pkgs/foo/", |
"pkgs": fooPackage}; |
- var dataUri = "data:,foo:%$scheme/pkgs/foo/\n"; |
- await testScheme("explicit data: config file", "%$scheme/main.dart", |
- files: files, |
- config: dataUri, |
+ await test("http: implicit packages dir", "%http/sub/main.dart", |
+ http: files, |
expect: { |
- "pconf": dataUri, |
- "iconf": dataUri, |
+ "iroot": "%http/sub/packages/", |
// "foo": null, |
- "foo/": "%$scheme/pkgs/foo/", |
- "foo/bar": "%$scheme/pkgs/foo/bar", |
+ "foo/": "%http/sub/packages/foo/", |
+ "foo/bar": "%http/sub/packages/foo/bar", |
+ "foo.x": null, |
}); |
} |
} |
- { |
- // With a file: URI, the lookup checks for a .packages file in superdirs |
- // when it fails to find a ,packages file or packages/ directory next to |
- // the entry point. |
- var files = {"sub": { "main": testMain }, |
- ".packages": "foo:pkgs/foo/", |
- "pkgs": fooPackage}; |
- await test("file: implicit .packages file in ..", "%file/sub/main.dart", |
- file: files, |
- expect: { |
- "iconf": "%file/.packages", |
- // "foo": null, |
- "foo/": "%file/pkgs/foo/", |
- "foo/bar": "%file/pkgs/foo/bar", |
- }); |
- } |
- |
- { |
- // With a non-file: URI, the lookup assumes a packges/ dir. |
- // The absence of a .packages file next to the entry point means |
- // that the resolution assumes a packages directory, whether it exists or |
- // not. It should not find the .packages file in the parent directory. |
- var files = {"sub": { "main": testMain }, |
- ".packages": "foo:pkgs/foo/", |
- "pkgs": fooPackage}; |
- await test("http: implicit packages dir", "%http/sub/main.dart", |
- http: files, |
- expect: { |
- "iroot": "%http/sub/packages/", |
- // "foo": null, |
- "foo/": "%http/sub/packages/foo/", |
- "foo/bar": "%http/sub/packages/foo/bar", |
- "foo.x": null, |
- }); |
- } |
- |
+ await runTests(test); |
+ await runTests(testSpawn(test)); |
+ await runTests(testSpawn(testSpawn(test))); |
if (failingTests.isNotEmpty) { |
print("Errors found in tests:\n ${failingTests.join("\n ")}\n"); |
@@ -217,6 +222,10 @@ var failingTests = new Set(); |
var fileHttpRegexp = new RegExp(r"%(?:file|http)/"); |
+typedef Future Test(String name, String main, |
+ {String root, String config, List<String> args, |
+ Map file, Map http, Map expect}); |
+ |
Future test(String name, String main, |
{String root, String config, List<String> args, |
Map file, Map http, Map expect}) async { |
@@ -285,6 +294,31 @@ Future test(String name, String main, |
} |
} |
+Test testSpawn(Test test) => |
+ (String name, String main, |
+ {String root, String config, List<String> args, |
+ Map file, Map http, Map expect}) { |
+ // Add spawnMain file next to main file. |
+ var spawnMainName = "_spawnMain${tmpNameCounter++}"; |
+ var parts = main.split('/').toList(); |
+ var files; |
+ if (parts[0] == "%file") { |
+ files = file; |
+ } else { |
+ assert(parts[0] == "%http"); |
+ files = http; |
+ } |
+ for (var i = 1; i < parts.length - 1; i++) { |
+ files = files[parts[i]]; |
+ } |
+ files[spawnMainName] = spawnMain.replaceAll("%main", main); |
+ parts[parts.length - 1] = "$spawnMainName.dart"; |
+ |
+ return test("spawn: $name", parts.join("/"), |
+ root: root, config: config, args: args, |
+ file: file, http: http, expect: expect); |
+ }; |
+ |
/// Test that the output of running testMain matches the expectations. |
/// |
@@ -359,23 +393,36 @@ main(args) async { |
var isolate = await Isolate.spawnUri(target, restArgs, |
packageRoot: root, packageConfig: conf, paused: true); |
// Wait for isolate to exit before exiting the main isolate. |
- var done = new RawReceivePort(); |
- done.handler = (_) { done.close(); }; |
- isolate.addExitHandler(done.sendPort); |
+ var port = new RawReceivePort(); |
+ port.handler = (res) async { |
+ port.close(); // Close on done or first error. |
+ if (res != null) { |
+ await new Future.error(res[0], new Stacktrace.fromString(res[1])); |
+ } |
+ }; |
+ isolate.addOnExitListener(port.sendPort); |
+ isolate.addErrorListener(port.sendPort); |
isolate.resume(isolate.pauseCapability); |
} |
"""; |
/// Script that spawns a new Isolate using Isolate.spawn. |
const String spawnMain = r""" |
+import "dart:async"; |
import "dart:isolate"; |
-import "testmain.dart" as test; |
-main() async { |
+import "%main" as test; |
+main([_]) async { |
var isolate = await Isolate.spawn(test.main, [], paused: true); |
// Wait for isolate to exit before exiting the main isolate. |
- var done = new RawReceivePort(); |
- done.handler = (_) { done.close(); }; |
- isolate.addExitHandler(done.sendPort); |
+ var port = new RawReceivePort(); |
+ port.handler = (res) async { |
+ port.close(); // Close on port or first error. |
+ if (res != null) { |
+ await new Future.error(res[0], new Stacktrace.fromString(res[1])); |
+ } |
+ }; |
+ isolate.addOnExitListener(port.sendPort); |
+ isolate.addErrorListener(port.sendPort); |
isolate.resume(isolate.pauseCapability); |
} |
"""; |
@@ -389,11 +436,14 @@ const Map fooPackage = const { "foo": const { "foo": "var x = 'qux';" }}; |
Future<String> runDart(String script, |
{String root, String config, |
Iterable<String> scriptArgs}) async { |
+ var checked = false; |
+ assert((checked = true)); |
floitsch
2016/05/27 14:26:50
Add a comment.
|
// TODO: Find a way to change CWD before running script. |
var executable = Platform.executable; |
var args = []; |
- if (root != null) args..add("-p")..add(root); |
- if (config != null) args..add("--packages=$config"); |
+ if (checked) args.add("--checked"); |
+ if (root != null) args.add("--package-root=$root"); |
+ if (config != null) args.add("--packages=$config"); |
args.add(script); |
if (scriptArgs != null) { |
args.addAll(scriptArgs); |
@@ -491,8 +541,8 @@ Future<HttpServer> startServer(Map files, String fixPaths(String text)) async { |
// Counter used to avoid reusing temporary directory names. |
// Some platforms are timer based, and creating two temp-dirs withing a short |
// duration may cause a collision. |
-int tmpDirCounter = 0; |
+int tmpNameCounter = 0; |
Directory createTempDir() { |
- return Directory.systemTemp.createTempSync("pftest-${tmpDirCounter++}-"); |
+ return Directory.systemTemp.createTempSync("pftest-${tmpNameCounter++}-"); |
} |