OLD | NEW |
1 // Copyright (c) 2015, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2015, the Dart project authors. Please see the AUTHORS file |
2 // for details. All rights reserved. Use of this source code is governed by a | 2 // for details. All rights reserved. Use of this source code is governed by a |
3 // BSD-style license that can be found in the LICENSE file. | 3 // BSD-style license that can be found in the LICENSE file. |
4 | 4 |
5 library test.backend.declarer; | 5 library test.backend.declarer; |
6 | 6 |
7 import 'dart:collection'; | 7 import 'dart:collection'; |
8 | 8 |
9 import '../frontend/timeout.dart'; | 9 import '../frontend/timeout.dart'; |
10 import 'group.dart'; | 10 import 'group.dart'; |
11 import 'invoker.dart'; | 11 import 'invoker.dart'; |
12 import 'metadata.dart'; | 12 import 'metadata.dart'; |
13 import 'test.dart'; | 13 import 'test.dart'; |
14 | 14 |
15 /// A class that manages the state of tests as they're declared. | 15 /// A class that manages the state of tests as they're declared. |
16 /// | 16 /// |
17 /// This is in charge of tracking the current group, set-up, and tear-down | 17 /// This is in charge of tracking the current group, set-up, and tear-down |
18 /// functions. It produces a list of runnable [tests]. | 18 /// functions. It produces a list of runnable [tests]. |
19 class Declarer { | 19 class Declarer { |
20 /// The current group. | 20 /// The current group. |
21 var _group = new Group.root(); | 21 var _group = new Group.root(); |
22 | 22 |
23 /// The list of tests that have been defined. | 23 /// The list of tests that have been defined. |
24 List<Test> get tests => new UnmodifiableListView<Test>(_tests); | 24 List<Test> get tests => new UnmodifiableListView<Test>(_tests); |
25 final _tests = new List<Test>(); | 25 final _tests = new List<Test>(); |
26 | 26 |
27 Declarer(); | 27 Declarer(); |
28 | 28 |
29 /// Defines a test case with the given description and body. | 29 /// Defines a test case with the given description and body. |
30 /// | |
31 /// The description will be added to the descriptions of any surrounding | |
32 /// [group]s. | |
33 /// | |
34 /// If [testOn] is passed, it's parsed as a [PlatformSelector], and the test | |
35 /// will only be run on matching platforms. | |
36 /// | |
37 /// If [timeout] is passed, it's used to modify or replace the default timeout | |
38 /// of 30 seconds. Timeout modifications take precedence in suite-group-test | |
39 /// order, so [timeout] will also modify any timeouts set on the group or | |
40 /// suite. | |
41 /// | |
42 /// If [skip] is a String or `true`, the test is skipped. If it's a String, it | |
43 /// should explain why the test is skipped; this reason will be printed | |
44 /// instead of running the test. | |
45 void test(String description, body(), {String testOn, Timeout timeout, | 30 void test(String description, body(), {String testOn, Timeout timeout, |
46 skip}) { | 31 skip, Map<String, dynamic> onPlatform}) { |
47 // TODO(nweiz): Once tests have begun running, throw an error if [test] is | 32 // TODO(nweiz): Once tests have begun running, throw an error if [test] is |
48 // called. | 33 // called. |
49 var prefix = _group.description; | 34 var prefix = _group.description; |
50 if (prefix != null) description = "$prefix $description"; | 35 if (prefix != null) description = "$prefix $description"; |
51 | 36 |
52 var metadata = _group.metadata.merge( | 37 var metadata = _group.metadata.merge(new Metadata.parse( |
53 new Metadata.parse(testOn: testOn, timeout: timeout, skip: skip)); | 38 testOn: testOn, timeout: timeout, skip: skip, onPlatform: onPlatform)); |
| 39 |
54 var group = _group; | 40 var group = _group; |
55 _tests.add(new LocalTest(description, metadata, () { | 41 _tests.add(new LocalTest(description, metadata, () { |
56 // TODO(nweiz): It might be useful to throw an error here if a test starts | 42 // TODO(nweiz): It might be useful to throw an error here if a test starts |
57 // running while other tests from the same declarer are also running, | 43 // running while other tests from the same declarer are also running, |
58 // since they might share closurized state. | 44 // since they might share closurized state. |
59 return group.runSetUp().then((_) => body()); | 45 return group.runSetUp().then((_) => body()); |
60 }, tearDown: group.runTearDown)); | 46 }, tearDown: group.runTearDown)); |
61 } | 47 } |
62 | 48 |
63 /// Creates a group of tests. | 49 /// Creates a group of tests. |
64 /// | |
65 /// A group's description is included in the descriptions of any tests or | |
66 /// sub-groups it contains. [setUp] and [tearDown] are also scoped to the | |
67 /// containing group. | |
68 /// | |
69 /// If [testOn] is passed, it's parsed as a [PlatformSelector], and any tests | |
70 /// in the group will only be run on matching platforms. | |
71 /// | |
72 /// If [timeout] is passed, it's used to modify or replace the default timeout | |
73 /// of 30 seconds. Timeout modifications take precedence in suite-group-test | |
74 /// order, so [timeout] will also modify any timeouts set on the group or | |
75 /// suite. | |
76 /// | |
77 /// If [skip] is a String or `true`, the group is skipped. If it's a String, | |
78 /// it should explain why the group is skipped; this reason will be printed | |
79 /// instead of running the group's tests. | |
80 void group(String description, void body(), {String testOn, | 50 void group(String description, void body(), {String testOn, |
81 Timeout timeout, skip}) { | 51 Timeout timeout, skip, Map<String, dynamic> onPlatform}) { |
82 var oldGroup = _group; | 52 var oldGroup = _group; |
83 | 53 |
84 var metadata = new Metadata.parse( | 54 var metadata = new Metadata.parse( |
85 testOn: testOn, timeout: timeout, skip: skip); | 55 testOn: testOn, timeout: timeout, skip: skip, onPlatform: onPlatform); |
86 | 56 |
87 // Don' load the tests for a skipped group. | 57 // Don' load the tests for a skipped group. |
88 if (metadata.skip) { | 58 if (metadata.skip) { |
89 _tests.add(new LocalTest(description, metadata, () {})); | 59 _tests.add(new LocalTest(description, metadata, () {})); |
90 return; | 60 return; |
91 } | 61 } |
92 | 62 |
93 _group = new Group(oldGroup, description, metadata); | 63 _group = new Group(oldGroup, description, metadata); |
94 try { | 64 try { |
95 body(); | 65 body(); |
96 } finally { | 66 } finally { |
97 _group = oldGroup; | 67 _group = oldGroup; |
98 } | 68 } |
99 } | 69 } |
100 | 70 |
101 /// Registers a function to be run before tests. | 71 /// Registers a function to be run before tests. |
102 /// | |
103 /// This function will be called before each test is run. [callback] may be | |
104 /// asynchronous; if so, it must return a [Future]. | |
105 /// | |
106 /// If this is called within a [group], it applies only to tests in that | |
107 /// group. [callback] will be run after any set-up callbacks in parent groups | |
108 /// or at the top level. | |
109 void setUp(callback()) { | 72 void setUp(callback()) { |
110 if (_group.setUp != null) { | 73 if (_group.setUp != null) { |
111 throw new StateError("setUp() may not be called multiple times for the " | 74 throw new StateError("setUp() may not be called multiple times for the " |
112 "same group."); | 75 "same group."); |
113 } | 76 } |
114 | 77 |
115 _group.setUp = callback; | 78 _group.setUp = callback; |
116 } | 79 } |
117 | 80 |
118 /// Registers a function to be run after tests. | 81 /// Registers a function to be run after tests. |
119 /// | |
120 /// This function will be called after each test is run. [callback] may be | |
121 /// asynchronous; if so, it must return a [Future]. | |
122 /// | |
123 /// If this is called within a [group], it applies only to tests in that | |
124 /// group. [callback] will be run before any tear-down callbacks in parent | |
125 /// groups or at the top level. | |
126 void tearDown(callback()) { | 82 void tearDown(callback()) { |
127 if (_group.tearDown != null) { | 83 if (_group.tearDown != null) { |
128 throw new StateError("tearDown() may not be called multiple times for " | 84 throw new StateError("tearDown() may not be called multiple times for " |
129 "the same group."); | 85 "the same group."); |
130 } | 86 } |
131 | 87 |
132 _group.tearDown = callback; | 88 _group.tearDown = callback; |
133 } | 89 } |
134 } | 90 } |
OLD | NEW |