Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(32)

Side by Side Diff: utils/testrunner/dart_wrap_task.dart

Issue 10897016: Testrunner for 3rd parties. (Closed) Base URL: http://dart.googlecode.com/svn/branches/bleeding_edge/dart/
Patch Set: Created 8 years, 3 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
(Empty)
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
3 // BSD-style license that can be found in the LICENSE file.
4
5 class DartWrapTask extends PipelineTask {
Siggi Cherem (dart-lang) 2012/08/29 01:05:54 docs?
gram 2012/08/29 20:12:26 Done.
6 String sourceFileTemplate;
7 String tempDartFileTemplate;
8
9 DartWrapTask(this.sourceFileTemplate, this.tempDartFileTemplate);
10
11 void execute(Path testfile, List stdout, List stderr, bool verboseLogging,
12 Function exitHandler) {
13 // Get the source test file and canonicalize the path.
14 var sourceName = makePathAbsolute(concretize(sourceFileTemplate, testfile));
15 // Get the destination file.
16 var destFile = concretize(tempDartFileTemplate, testfile);
17
18 StringBuffer sbuf = new StringBuffer();
19
20 // Add the common header stuff.
21 var p = new Path(sourceName);
22 var u = new Path(configuration['unittest']);
23 sbuf.add(directives(p.filenameWithoutExtension, u.toString(), sourceName));
24
25 // Add the test configuration and the action function.
26 var action;
27 if (configuration['list-tests']) {
28 action = 'listTests';
29 sbuf.add(barebonesConfig());
30 sbuf.add(listTests(sourceName));
31 } else if (configuration['list-groups']) {
32 sbuf.add(barebonesConfig());
33 sbuf.add(listGroups(sourceName));
34 action = 'listGroups';
35 } else {
36 var runIsolated = configuration['isolate'];
37 var runInBrowser =
38 configuration['runtime'] != 'vm' &&
39 configuration['runtime'] != 'd8';
40 sbuf.add(testPrint(runInBrowser));
41 sbuf.add(testConfig(sourceName, runInBrowser, runIsolated,
42 configuration['time'],
43 configuration['summary']));
44 // Add the isolate stuff, if applicable. This overrides
45 if (runIsolated) {
46 action = 'runIsolateTests';
47 sbuf.add(isolateTests());
48 } else {
49 action = 'runTests';
50 sbuf.add("runTests() { unittest.runTests(); }\n");
51 }
52 }
53 sbuf.add(formatMessage(configuration['format']));
54
55 // Add the filter, if applicable.
56 var include = configuration['include'];
57 var filter = false;
58 if (include.length > 0) {
59 sbuf.add(filterTests(include, 'true'));
60 filter = true;
61 } else {
62 var exclude = configuration['exclude'];
63 if (exclude.length > 0) {
64 sbuf.add(filterTests(exclude, 'false'));
65 filter = true;
66 }
67 }
68
69 // Add the common trailer stuff.
70 sbuf.add(dartMain(action, filter));
71
72 // Save the Dart file.
73 createFile(destFile, sbuf.toString());
74 exitHandler(0);
75 }
76
77 String directives(String library, String unittest, String sourceName) {
78 return """
79 #library('$library');
80 #import('dart:isolate');
81 #import('$unittest', prefix:'unittest');
82 #import('$sourceName', prefix: 'test');
83 """;
84 }
85
86 String testPrint(bool runInBrowser) {
87 if (runInBrowser) {
88 return """
89 #import('dart:html');
90 void tprint(msg) {
91 var pre = query('#console');
92 pre.elements.add(new Text('###\$msg\\n'));
93 }
94 """;
95 } else {
96 return """
97 void tprint(msg) {
98 print('###\$msg');
99 }
100 """;
101 }
102 }
103
104 String config(String body) {
105 return """
106 class TestRunnerConfiguration extends unittest.Configuration {
107 get name => 'Test runner configuration';
108 get autoStart => false;
109 $body
110 }
111 """;
112 }
113
114 String barebonesConfig() {
115 return config('');
116 }
117
118 String testConfig(String sourceName, bool runInBrowser, bool runIsolated,
119 bool showTime, bool summary) {
120 StringBuffer sbuf = new StringBuffer();
121 if (runIsolated) {
122 sbuf.add("var port;\nTestRunnerConfiguration(this.port);\n");
123 }
124 sbuf.add("""
125 String resultName(result) {
Siggi Cherem (dart-lang) 2012/08/29 01:05:54 the mix of quoted code and normal code makes this
gram 2012/08/29 20:12:26 I've refactored this quite a bit; hopefully it wil
Siggi Cherem (dart-lang) 2012/08/29 20:47:35 it is easier to see with syntax highlighting, but
126 if (result == 'pass') return '${configuration['pass-text']}';
127 if (result == 'fail') return '${configuration['fail-text']}';
128 return '${configuration['error-text']}';
129 }
130 void onTestStart(TestCase testCase) {}
131 void onDone(int passed, int failed, int errors, List<TestCase> results,
132 String uncaughtError) {
133 // Print each result.
134 for (final t in results) {
135 var groupName = '', testName = '';
136 var idx = t.description.lastIndexOf('###');
137 if (idx >= 0) {
138 groupName = t.description.substring(0, idx).replaceAll('###', ' ');
139 testName = t.description.substring(idx+3);
140 } else {
141 testName = t.description;
142 }
143 var stack = (t.stackTrace == null) ? '' : '\${t.stackTrace} ';
144 var message = (t.message.length > 0) ? '\$t.message ' : '';
145 var elapsed = '';
146 """);
147 if (showTime) {
148 sbuf.add("""
149 double duration = t.runningTime.inMilliseconds;
150 duration /= 1000;
151 elapsed = '\${duration.toStringAsFixed(3)}s ';
152 """);
153 }
154 sbuf.add("""
155 tprint(formatMessage('${sourceName} ', '\$groupName ', '\$testName ',
156 elapsed, '\${resultName(t.result)} ', message, stack));
157 }
158 """);
159 if (summary) {
160 sbuf.add("""
161 tprint('');
162 var success = false;
163 if (passed == 0 && failed == 0 && errors == 0) {
164 tprint('$sourceName: No tests found.');
165 // This is considered a failure too.
166 } else if (failed == 0 && errors == 0 && uncaughtError == null) {
167 tprint('$sourceName: All \$passed tests passed.');
168 success = true;
169 } else {
170 if (uncaughtError != null) {
171 tprint('$sourceName: Top-level uncaught error: \$uncaughtError');
172 }
173 tprint('$sourceName: \$passed PASSED, \$failed FAILED, \$errors ERRORS');
174 }
175 """);
176 }
177 if (runIsolated) {
178 sbuf.add("var success = (passed > 0 && failed == 0 && errors == 0 "
179 "&& uncaughtError == null);\n");
180 sbuf.add("port.send(success);\n}\n");
181 } else if (runInBrowser) {
182 sbuf.add("window.postMessage('done', '*');\n}\n");
183 } else {
184 sbuf.add("}\n");
185 }
186 return config(sbuf.toString());
187 }
188
189 String formatMessage(String format) {
190 return """
191 String formatMessage(filename, groupname,
192 [ testname = '', testTime = '', result = '',
193 message = '', stack = '' ]) {
194 return '${format}'.
195 replaceAll('${Meta.testResult}', result).
196 replaceAll('${Meta.testTime}', testTime).
197 replaceAll('${Meta.testfile}', filename).
198 replaceAll('${Meta.testGroup}', groupname).
199 replaceAll('${Meta.testDescription}', testname).
200 replaceAll('${Meta.testMessage}', message).
201 replaceAll('${Meta.testStacktrace}', stack);
202 }
203 """;
204 }
205
206 String listGroups(String sourceName) {
207 return """
208 listGroups() {
209 List tests = unittest.testCases;
210 Map groups = {};
211 for (var t in tests) {
212 var groupName, testName = '';
213 var idx = t.description.lastIndexOf('###');
214 if (idx >= 0) {
215 groupName = t.description.substring(0, idx).replaceAll('###', ' ');
216 if (!groups.containsKey(groupName)) {
217 groups[groupName] = '';
218 }
219 }
220 }
221 for (var g in groups.getKeys()) {
222 var msg = formatMessage('${sourceName} ', '\$g ');
223 print('###\$msg');
224 }
225 }
226 """;
227 }
228
229 String listTests(String sourceName) {
230 return """
231 listTests() {
232 List tests = unittest.testCases;
233 for (var t in tests) {
234 var groupName, testName = '';
235 var idx = t.description.lastIndexOf('###');
236 if (idx >= 0) {
237 groupName = t.description.substring(0, idx).replaceAll('###', ' ');
238 testName = t.description.substring(idx+3);
239 } else {
240 groupName = '';
241 testName = t.description;
242 }
243 var msg = formatMessage('${sourceName} ', '\$groupName ',
244 '\$testName ');
245 print('###\$msg');
246 }
247 }
248 """;
249 }
250
251 String filterTests(List filters, String filterReturnValue) {
252 StringBuffer sbuf = new StringBuffer();
253 sbuf.add('filterTest(t) {\n');
254 if (filters != null) {
255 sbuf.add(' var name = t.description.replaceAll("###", " ");\n');
256 for (var f in filters) {
257 sbuf.add(' if (name.indexOf("$f")>=0) return $filterReturnValue;\n');
258 }
259 sbuf.add(' return !$filterReturnValue;\n');
260 } else {
261 // TODO - is this right? Should it be filterReturnValue?
262 sbuf.add(' return true;\n');
263 }
264 sbuf.add('}\n');
265 return sbuf.toString();
266 }
267
268 String isolateTests() {
269 return """
270 runSlaveTest() {
271 port.receive((testName, sendport) {
272 unittest.configure(new TestRunnerConfiguration(sendport));
273 unittest.group('', test.main);
274 unittest.filterTests(testName);
275 unittest.runTests();
276 });
277 }
278
279 var testNum;
280 var failed;
281
282 runMasterTest() {
283 var tests = unittest.testCases;
284 SendPort sport = spawnFunction(runSlaveTest);
285 sport.call(tests[testNum].description).then((result) {
286 if (!result) failed = true;
287 ++testNum;
288 if (testNum < tests.length) {
289 runMasterTest();
290 } else if (failed) {
291 throw new Exception("Some tests failed.");
292 }
293 });
294 }
295
296 runIsolateTests() {
297 testNum = 0;
298 failed = false;
299 runMasterTest();
300 }
301 """;
302 }
303
304 String dartMain(String action, bool filter) {
305 return """
306 main() {
307 unittest.groupSep = '###';
308 unittest.configure(new TestRunnerConfiguration());
309 unittest.group('', test.main);
310 ${filter?'unittest.filterTests(filterTest);':''}
311 $action();
312 }
313 """;
314 }
315
316 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698