source: other-projects/trunk/gs3-release-maker/apache-ant-1.6.5/src/main/org/apache/tools/ant/taskdefs/optional/junit/XMLJUnitResultFormatter.java@ 14627

Last change on this file since 14627 was 14627, checked in by oranfry, 17 years ago

initial import of the gs3-release-maker

File size: 8.1 KB
Line 
1/*
2 * Copyright 2000-2005 The Apache Software Foundation
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 *
16 */
17
18package org.apache.tools.ant.taskdefs.optional.junit;
19
20import java.io.BufferedWriter;
21import java.io.IOException;
22import java.io.OutputStream;
23import java.io.OutputStreamWriter;
24import java.io.Writer;
25import java.util.Enumeration;
26import java.util.Hashtable;
27import java.util.Properties;
28import javax.xml.parsers.DocumentBuilder;
29import javax.xml.parsers.DocumentBuilderFactory;
30import junit.framework.AssertionFailedError;
31import junit.framework.Test;
32import org.apache.tools.ant.BuildException;
33import org.apache.tools.ant.util.DOMElementWriter;
34import org.w3c.dom.Document;
35import org.w3c.dom.Element;
36import org.w3c.dom.Text;
37
38
39/**
40 * Prints XML output of the test to a specified Writer.
41 *
42 *
43 * @see FormatterElement
44 */
45
46public class XMLJUnitResultFormatter implements JUnitResultFormatter, XMLConstants {
47
48 /** constant for unnnamed testsuites/cases */
49 private static final String UNKNOWN = "unknown";
50
51 private static DocumentBuilder getDocumentBuilder() {
52 try {
53 return DocumentBuilderFactory.newInstance().newDocumentBuilder();
54 } catch (Exception exc) {
55 throw new ExceptionInInitializerError(exc);
56 }
57 }
58
59 /**
60 * The XML document.
61 */
62 private Document doc;
63 /**
64 * The wrapper for the whole testsuite.
65 */
66 private Element rootElement;
67 /**
68 * Element for the current test.
69 */
70 private Hashtable testElements = new Hashtable();
71 /**
72 * tests that failed.
73 */
74 private Hashtable failedTests = new Hashtable();
75 /**
76 * Timing helper.
77 */
78 private Hashtable testStarts = new Hashtable();
79 /**
80 * Where to write the log to.
81 */
82 private OutputStream out;
83
84 public XMLJUnitResultFormatter() {
85 }
86
87 public void setOutput(OutputStream out) {
88 this.out = out;
89 }
90
91 public void setSystemOutput(String out) {
92 formatOutput(SYSTEM_OUT, out);
93 }
94
95 public void setSystemError(String out) {
96 formatOutput(SYSTEM_ERR, out);
97 }
98
99 /**
100 * The whole testsuite started.
101 */
102 public void startTestSuite(JUnitTest suite) {
103 doc = getDocumentBuilder().newDocument();
104 rootElement = doc.createElement(TESTSUITE);
105 String n = suite.getName();
106 rootElement.setAttribute(ATTR_NAME, n == null ? UNKNOWN : n);
107
108 // Output properties
109 Element propsElement = doc.createElement(PROPERTIES);
110 rootElement.appendChild(propsElement);
111 Properties props = suite.getProperties();
112 if (props != null) {
113 Enumeration e = props.propertyNames();
114 while (e.hasMoreElements()) {
115 String name = (String) e.nextElement();
116 Element propElement = doc.createElement(PROPERTY);
117 propElement.setAttribute(ATTR_NAME, name);
118 propElement.setAttribute(ATTR_VALUE, props.getProperty(name));
119 propsElement.appendChild(propElement);
120 }
121 }
122 }
123
124 /**
125 * The whole testsuite ended.
126 */
127 public void endTestSuite(JUnitTest suite) throws BuildException {
128 rootElement.setAttribute(ATTR_TESTS, "" + suite.runCount());
129 rootElement.setAttribute(ATTR_FAILURES, "" + suite.failureCount());
130 rootElement.setAttribute(ATTR_ERRORS, "" + suite.errorCount());
131 rootElement.setAttribute(ATTR_TIME, "" + (suite.getRunTime() / 1000.0));
132 if (out != null) {
133 Writer wri = null;
134 try {
135 wri = new BufferedWriter(new OutputStreamWriter(out, "UTF8"));
136 wri.write("<?xml version=\"1.0\" encoding=\"UTF-8\" ?>\n");
137 (new DOMElementWriter()).write(rootElement, wri, 0, " ");
138 wri.flush();
139 } catch (IOException exc) {
140 throw new BuildException("Unable to write log file", exc);
141 } finally {
142 if (out != System.out && out != System.err) {
143 if (wri != null) {
144 try {
145 wri.close();
146 } catch (IOException e) {
147 // ignore
148 }
149 }
150 }
151 }
152 }
153 }
154
155 /**
156 * Interface TestListener.
157 *
158 * <p>A new Test is started.
159 */
160 public void startTest(Test t) {
161 testStarts.put(t, new Long(System.currentTimeMillis()));
162 }
163
164 /**
165 * Interface TestListener.
166 *
167 * <p>A Test is finished.
168 */
169 public void endTest(Test test) {
170 // Fix for bug #5637 - if a junit.extensions.TestSetup is
171 // used and throws an exception during setUp then startTest
172 // would never have been called
173 if (!testStarts.containsKey(test)) {
174 startTest(test);
175 }
176
177 Element currentTest = null;
178 if (!failedTests.containsKey(test)) {
179 currentTest = doc.createElement(TESTCASE);
180 String n = JUnitVersionHelper.getTestCaseName(test);
181 currentTest.setAttribute(ATTR_NAME,
182 n == null ? UNKNOWN : n);
183 // a TestSuite can contain Tests from multiple classes,
184 // even tests with the same name - disambiguate them.
185 currentTest.setAttribute(ATTR_CLASSNAME,
186 test.getClass().getName());
187 rootElement.appendChild(currentTest);
188 testElements.put(test, currentTest);
189 } else {
190 currentTest = (Element) testElements.get(test);
191 }
192
193 Long l = (Long) testStarts.get(test);
194 currentTest.setAttribute(ATTR_TIME,
195 "" + ((System.currentTimeMillis() - l.longValue()) / 1000.0));
196 }
197
198 /**
199 * Interface TestListener for JUnit &lt;= 3.4.
200 *
201 * <p>A Test failed.
202 */
203 public void addFailure(Test test, Throwable t) {
204 formatError(FAILURE, test, t);
205 }
206
207 /**
208 * Interface TestListener for JUnit &gt; 3.4.
209 *
210 * <p>A Test failed.
211 */
212 public void addFailure(Test test, AssertionFailedError t) {
213 addFailure(test, (Throwable) t);
214 }
215
216 /**
217 * Interface TestListener.
218 *
219 * <p>An error occurred while running the test.
220 */
221 public void addError(Test test, Throwable t) {
222 formatError(ERROR, test, t);
223 }
224
225 private void formatError(String type, Test test, Throwable t) {
226 if (test != null) {
227 endTest(test);
228 failedTests.put(test, test);
229 }
230
231 Element nested = doc.createElement(type);
232 Element currentTest = null;
233 if (test != null) {
234 currentTest = (Element) testElements.get(test);
235 } else {
236 currentTest = rootElement;
237 }
238
239 currentTest.appendChild(nested);
240
241 String message = t.getMessage();
242 if (message != null && message.length() > 0) {
243 nested.setAttribute(ATTR_MESSAGE, t.getMessage());
244 }
245 nested.setAttribute(ATTR_TYPE, t.getClass().getName());
246
247 String strace = JUnitTestRunner.getFilteredTrace(t);
248 Text trace = doc.createTextNode(strace);
249 nested.appendChild(trace);
250 }
251
252 private void formatOutput(String type, String output) {
253 Element nested = doc.createElement(type);
254 rootElement.appendChild(nested);
255 nested.appendChild(doc.createCDATASection(output));
256 }
257
258} // XMLJUnitResultFormatter
Note: See TracBrowser for help on using the repository browser.