From cbf1a178e3f594dd79291e6de776141e55fc3eb7 Mon Sep 17 00:00:00 2001 From: Stephane Bailliez Date: Wed, 30 Jan 2002 21:06:49 +0000 Subject: [PATCH] Prepare for listener changes and event types. git-svn-id: https://svn.apache.org/repos/asf/ant/core/trunk@271010 13f79535-47bb-0310-9956-ffa450edef68 --- .../optional/junit/TestRunListener.java | 34 ++- .../junit/formatter/BaseFormatter.java | 34 ++- .../junit/formatter/BriefFormatter.java | 17 +- .../junit/formatter/FilterFormatter.java | 37 ++-- .../junit/formatter/FilterStackFormatter.java | 18 +- .../junit/formatter/PlainFormatter.java | 41 ++-- .../junit/formatter/XMLFormatter.java | 69 +++---- .../junit/remote/EventDispatcher.java | 195 ++++++++++++++++++ .../optional/junit/remote/MessageReader.java | 8 +- .../optional/junit/remote/Messenger.java | 116 +++++++++++ .../optional/junit/remote/Server.java | 31 ++- .../optional/junit/remote/TestRunEvent.java | 159 ++++++++++++++ .../junit/remote/TestRunListener.java | 76 +++++++ .../optional/junit/remote/TestRunner.java | 57 +++-- 14 files changed, 717 insertions(+), 175 deletions(-) create mode 100644 proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/remote/EventDispatcher.java create mode 100644 proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/remote/Messenger.java create mode 100644 proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/remote/TestRunEvent.java create mode 100644 proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/remote/TestRunListener.java diff --git a/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/TestRunListener.java b/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/TestRunListener.java index 55e5569cc..7f45b99f3 100644 --- a/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/TestRunListener.java +++ b/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/TestRunListener.java @@ -54,6 +54,9 @@ package org.apache.tools.ant.taskdefs.optional.junit; import java.util.Properties; +import java.util.EventListener; + +import org.apache.tools.ant.taskdefs.optional.junit.remote.TestRunEvent; /** @@ -67,27 +70,21 @@ import java.util.Properties; * * @author Stephane Bailliez */ -public interface TestRunListener { - - /** Some tests failed. */ - public final static int STATUS_FAILURE = 1; - - /** An error occured. */ - public final static int STATUS_ERROR = 2; +public interface TestRunListener extends EventListener{ /** * A test has started. * @param a testname made of the testname and testcase classname. * in the following format: <testname>(<testcase>) */ - public void onTestStarted(String testname); + public void onTestStarted(TestRunEvent evt); /** * A test ended. * @param a testname made of the testname and testcase classname. * in the following format: <testname>(<testcase>) */ - public void onTestEnded(String testname); + public void onTestEnded(TestRunEvent evt); /** * A test has failed. @@ -97,24 +94,19 @@ public interface TestRunListener { * @param trace the error/failure stacktrace. * @todo change this to a testFailure / testError ? */ - public void onTestFailed(int status, String testname, String trace); - - /** test logged this line on stdout */ - public void onTestStdOutLine(String testname, String line); - - /** test logged this line on sterr */ - public void onTestStdErrLine(String testname, String line); + public void onTestFailure(TestRunEvent evt); - /** these system properties are used on the remote client */ - public void onTestRunSystemProperties(Properties props); + public void onTestError(TestRunEvent evt); /** starting a sequence of testcount tests. */ - public void onTestRunStarted(int testcount); + public void onRunStarted(TestRunEvent evt); /** ending gracefully the sequence after elapsedtime ms. */ - public void onTestRunEnded(long elapsedtime); + public void onRunEnded(TestRunEvent evt); /** stopping the sequence after elapsedtime ms. */ - public void onTestRunStopped(long elapsedtime); + public void onRunStopped(TestRunEvent evt); + public void onSuiteStarted(TestRunEvent evt); + public void onSuiteEnded(TestRunEvent evt); } diff --git a/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/formatter/BaseFormatter.java b/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/formatter/BaseFormatter.java index 34593e8da..33e5a5923 100644 --- a/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/formatter/BaseFormatter.java +++ b/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/formatter/BaseFormatter.java @@ -56,6 +56,7 @@ package org.apache.tools.ant.taskdefs.optional.junit.formatter; import java.util.Properties; import org.apache.tools.ant.BuildException; +import org.apache.tools.ant.taskdefs.optional.junit.remote.TestRunEvent; /** * Provide a common set of attributes and methods to factorize @@ -81,42 +82,39 @@ public abstract class BaseFormatter implements Formatter { close(); } - public void onTestStdOutLine(String testname, String line) { + public void onTestStarted(TestRunEvent evt) { + runCount++; } - public void onTestStdErrLine(String testname, String line) { + public void onTestEnded(TestRunEvent evt) { } - public void onTestRunSystemProperties(Properties props) { + public void onTestFailure(TestRunEvent evt) { + failureCount++; } - public void onTestStarted(String testname) { + public void onTestError(TestRunEvent evt) { + errorCount++; } - public void onTestEnded(String testname) { + public void onSuiteStarted(TestRunEvent evt) { } - public void onTestFailed(int status, String testname, String trace) { - if (status == STATUS_ERROR) { - errorCount++; - } else if (status == STATUS_FAILURE) { - failureCount++; - } + public void onSuiteEnded(TestRunEvent evt) { } - public void onTestRunStarted(int testcount) { - runCount = testcount; + public void onRunStarted(TestRunEvent evt) { } - public void onTestRunEnded(long elapsedtime) { - finished(elapsedtime); + public void onRunEnded(TestRunEvent evt) { + finished(); } - public void onTestRunStopped(long elapsedtime) { - finished(elapsedtime); + public void onRunStopped(TestRunEvent evt) { + finished(); } - protected void finished(long elapsedtime) { + protected void finished() { close(); } diff --git a/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/formatter/BriefFormatter.java b/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/formatter/BriefFormatter.java index f66a079f9..98f8124f1 100644 --- a/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/formatter/BriefFormatter.java +++ b/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/formatter/BriefFormatter.java @@ -55,6 +55,7 @@ package org.apache.tools.ant.taskdefs.optional.junit.formatter; import org.apache.avalon.excalibur.i18n.ResourceManager; import org.apache.avalon.excalibur.i18n.Resources; +import org.apache.tools.ant.taskdefs.optional.junit.remote.TestRunEvent; /** * Display additional messages from a SummaryFormatter @@ -67,15 +68,15 @@ public class BriefFormatter extends SummaryFormatter { private final static Resources RES = ResourceManager.getPackageResources(BriefFormatter.class); - public void onTestFailed(int status, String testname, String trace) { - String msg = null; - if (status == STATUS_ERROR) { - msg = RES.getString("brief.status-error.msg", testname, trace); - } else { - msg = RES.getString("brief.status-failure.msg", testname, trace); - } + public void onTestFailure(TestRunEvent evt) { + String msg = RES.getString("brief.status-failure.msg", evt.getName(), evt.getStackTrace()); getWriter().println(msg); - super.onTestFailed(status, testname, trace); + super.onTestFailure(evt); } + public void onTestError(TestRunEvent evt) { + String msg = RES.getString("brief.status-error.msg", evt.getName(), evt.getStackTrace()); + getWriter().println(msg); + super.onTestError(evt); + } } diff --git a/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/formatter/FilterFormatter.java b/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/formatter/FilterFormatter.java index 5ac2afb9f..55ab0d93f 100644 --- a/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/formatter/FilterFormatter.java +++ b/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/formatter/FilterFormatter.java @@ -56,6 +56,7 @@ package org.apache.tools.ant.taskdefs.optional.junit.formatter; import java.util.Properties; import org.apache.tools.ant.BuildException; +import org.apache.tools.ant.taskdefs.optional.junit.remote.TestRunEvent; /** * A base class that can be used to filter data. @@ -75,40 +76,40 @@ public abstract class FilterFormatter implements Formatter { formatter.init(props); } - public void onTestStdOutLine(String testname, String line) { - formatter.onTestStdOutLine(testname, line); + public void onSuiteStarted(TestRunEvent evt) { + formatter.onSuiteStarted(evt); } - public void onTestStdErrLine(String testname, String line) { - formatter.onTestStdErrLine(testname, line); + public void onSuiteEnded(TestRunEvent evt) { + formatter.onSuiteEnded(evt); } - public void onTestStarted(String testname) { - formatter.onTestStarted(testname); + public void onTestStarted(TestRunEvent evt) { + formatter.onTestStarted(evt); } - public void onTestEnded(String testname) { - formatter.onTestEnded(testname); + public void onTestEnded(TestRunEvent evt) { + formatter.onTestEnded(evt); } - public void onTestFailed(int status, String testname, String trace) { - formatter.onTestFailed(status, testname, trace); + public void onTestFailure(TestRunEvent evt) { + formatter.onTestFailure(evt); } - public void onTestRunSystemProperties(Properties props) { - formatter.onTestRunSystemProperties(props); + public void onTestError(TestRunEvent evt) { + formatter.onTestError(evt); } - public void onTestRunStarted(int testcount) { - formatter.onTestRunStarted(testcount); + public void onRunStarted(TestRunEvent evt) { + formatter.onRunStarted(evt); } - public void onTestRunEnded(long elapsedtime) { - formatter.onTestRunEnded(elapsedtime); + public void onRunEnded(TestRunEvent evt) { + formatter.onRunEnded(evt); } - public void onTestRunStopped(long elapsedtime) { - formatter.onTestRunEnded(elapsedtime); + public void onRunStopped(TestRunEvent evt) { + formatter.onRunEnded(evt); } /** set the wrapped formatter */ diff --git a/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/formatter/FilterStackFormatter.java b/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/formatter/FilterStackFormatter.java index 729d6dbe2..16cbdd705 100644 --- a/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/formatter/FilterStackFormatter.java +++ b/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/formatter/FilterStackFormatter.java @@ -56,6 +56,7 @@ package org.apache.tools.ant.taskdefs.optional.junit.formatter; import java.util.StringTokenizer; import org.apache.tools.ant.util.StringUtils; +import org.apache.tools.ant.taskdefs.optional.junit.remote.TestRunEvent; /** * Filtered Formatter that strips out unwanted stack frames from the full @@ -99,7 +100,19 @@ public class FilterStackFormatter extends FilterFormatter { super(formatter); } - public void onTestFailed(int status, String testname, String trace) { + public void onTestFailure(TestRunEvent evt) { + String filteredTrace = filter(evt.getStackTrace()); + evt.setStackTrace(filteredTrace); + super.onTestFailure(evt); + } + + public void onTestError(TestRunEvent evt) { + String filteredTrace = filter(evt.getStackTrace()); + evt.setStackTrace(filteredTrace); + super.onTestFailure(evt); + } + + protected String filter(String trace){ StringTokenizer st = new StringTokenizer(trace, "\r\n"); StringBuffer buf = new StringBuffer(trace.length()); while (st.hasMoreTokens()) { @@ -108,9 +121,8 @@ public class FilterStackFormatter extends FilterFormatter { buf.append(line).append(StringUtils.LINE_SEP); } } - super.onTestFailed(status, testname, buf.toString()); + return buf.toString(); } - /** * Check whether or not the line should be accepted. * @param the line to be check for acceptance. diff --git a/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/formatter/PlainFormatter.java b/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/formatter/PlainFormatter.java index 3b299aa13..d0b1b9663 100644 --- a/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/formatter/PlainFormatter.java +++ b/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/formatter/PlainFormatter.java @@ -55,6 +55,8 @@ package org.apache.tools.ant.taskdefs.optional.junit.formatter; import java.util.Properties; +import org.apache.tools.ant.taskdefs.optional.junit.remote.TestRunEvent; + /** * Default formatter to text. * @@ -62,38 +64,39 @@ import java.util.Properties; */ public class PlainFormatter extends BaseStreamFormatter { - public void onTestStarted(String testname) { - getWriter().println("Started " + testname); - } - - public void onTestEnded(String testname) { - getWriter().println("Ended " + testname); + public void onSuiteStarted(TestRunEvent evt) { + getWriter().println(" suite: " + evt.getName()); + super.onSuiteStarted(evt); } - public void onTestFailed(int status, String testname, String trace) { - getWriter().println(testname + " failed with status " + status); - getWriter().println(trace); + public void onSuiteEnded(TestRunEvent evt) { + getWriter().println(" end suite"); + super.onSuiteEnded(evt); } - public void onTestRunSystemProperties(Properties props) { - getWriter().println("properties: " + props); + public void onTestStarted(TestRunEvent evt) { + getWriter().println(" running test: " + evt.getName()); } - public void onTestRunStarted(int testcount) { - getWriter().println("testsuite: " + testcount); + public void onTestEnded(TestRunEvent evt) { + getWriter().println(" success: " + evt.getName()); } - public void onTestStdOutLine(String testname, String line) { + public void onTestFailure(TestRunEvent evt) { + getWriter().println(" failure: " + evt.getName()); + getWriter().println(evt.getStackTrace()); } - public void onTestStdErrLine(String testname, String line) { + public void onTestError(TestRunEvent evt) { + getWriter().println(" error: " + evt.getName()); + getWriter().println(evt.getStackTrace()); } - public void onTestRunEnded(long elapsedtime) { - getWriter().println("testsuite ended after: " + elapsedtime); + public void onRunEnded(TestRunEvent evt) { + getWriter().println("run ended"); } - public void onTestRunStopped(long elapsedtime) { - getWriter().println("testsuite stopped after: " + elapsedtime); + public void onRunStopped(TestRunEvent evt) { + getWriter().println("run stopped"); } } diff --git a/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/formatter/XMLFormatter.java b/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/formatter/XMLFormatter.java index 23ceae218..36aa34b75 100644 --- a/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/formatter/XMLFormatter.java +++ b/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/formatter/XMLFormatter.java @@ -64,6 +64,7 @@ import org.w3c.dom.Text; import org.apache.tools.ant.util.DOMElementWriter; import org.apache.tools.ant.BuildException; +import org.apache.tools.ant.taskdefs.optional.junit.remote.TestRunEvent; /** * XML Formatter. Due to the nature of the XML we are forced to store @@ -140,67 +141,63 @@ public class XMLFormatter extends BaseStreamFormatter { /** Timing helper. */ private Hashtable testStarts = new Hashtable(); - public void onTestStarted(String testname) { + public void onTestStarted(TestRunEvent evt) { //@fixme, eh, a testname only can obviouslly be a duplicate... - testStarts.put(testname, new Long(System.currentTimeMillis())); + testStarts.put(evt.getName(), evt); Element currentTest = doc.createElement(TESTCASE); - currentTest.setAttribute(ATTR_NAME, testname); + currentTest.setAttribute(ATTR_NAME, evt.getName()); rootElement.appendChild(currentTest); - testElements.put(testname, currentTest); - super.onTestStarted(testname); + testElements.put(evt.getName(), currentTest); + super.onTestStarted(evt); + removeEvent(evt); } - public void onTestEnded(String testname) { - Element currentTest = (Element) testElements.get(testname); + public void onTestEnded(TestRunEvent evt) { + Element currentTest = (Element) testElements.get(evt); // with a TestSetup, startTest and endTest are not called. if (currentTest == null) { - onTestStarted(testname); - currentTest = (Element) testElements.get(testname); + onTestStarted(evt); + currentTest = (Element) testElements.get(evt.getName()); } - Long l = (Long) testStarts.get(testname); - float time = ((System.currentTimeMillis() - l.longValue()) / 1000.0f); + TestRunEvent start = (TestRunEvent)testStarts.get(evt); + float time = ((evt.getTimeStamp() - start.getTimeStamp()) / 1000.0f); currentTest.setAttribute(ATTR_TIME, Float.toString(time)); - super.onTestEnded(testname); - // remove the test objects - //testStarts.remove(testname); - //testElements.remove(testname); + super.onTestEnded(evt); + removeEvent(evt); } - public void onTestFailed(int status, String testname, String trace) { - if (testname != null) { - onTestEnded(testname); - } - String type = status == STATUS_FAILURE ? FAILURE : ERROR; + public void onTestFailure(TestRunEvent evt) { + String type = evt == evt.getType() == TestRunEvent.TEST_FAILURE ? FAILURE : ERROR; Element nested = doc.createElement(type); - Element currentTest = null; - if (testname != null) { - currentTest = (Element) testElements.get(testname); - } else { - currentTest = rootElement; - } - + Element currentTest = (Element) testElements.get(evt.getName()); currentTest.appendChild(nested); - String[] args = parseFirstLine(trace); + String[] args = parseFirstLine(evt.getStackTrace()); if (args[1] != null && args[1].length() > 0) { nested.setAttribute(ATTR_MESSAGE, args[1]); } nested.setAttribute(ATTR_TYPE, args[0]); - Text text = doc.createTextNode(trace); + Text text = doc.createTextNode(evt.getStackTrace()); nested.appendChild(text); - super.onTestFailed(status, testname, trace); + super.onTestFailure(evt); + removeEvent(evt); + } + + protected void removeEvent(TestRunEvent evt){ + testStarts.remove(evt.getName()); + testElements.remove(evt.getName()); } - public void onTestRunStarted(int testcount) { - super.onTestRunStarted(testcount); + public void onRunStarted(TestRunEvent evt) { + super.onRunStarted(evt); } - public void onTestRunEnded(long elapsedtime) { - super.onTestRunEnded(elapsedtime); + public void onRunEnded(TestRunEvent evt) { + super.onRunEnded(evt); } - public void onTestRunStopped(long elapsedtime) { - super.onTestRunStopped(elapsedtime); + public void onRunStopped(TestRunEvent evt) { + super.onRunStopped(evt); } protected void close() { diff --git a/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/remote/EventDispatcher.java b/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/remote/EventDispatcher.java new file mode 100644 index 000000000..32adcd011 --- /dev/null +++ b/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/remote/EventDispatcher.java @@ -0,0 +1,195 @@ +/* + * The Apache Software License, Version 1.1 + * + * Copyright (c) 2002 The Apache Software Foundation. All rights + * reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in + * the documentation and/or other materials provided with the + * distribution. + * + * 3. The end-user documentation included with the redistribution, if + * any, must include the following acknowlegement: + * "This product includes software developed by the + * Apache Software Foundation (http://www.apache.org/)." + * Alternately, this acknowlegement may appear in the software itself, + * if and wherever such third-party acknowlegements normally appear. + * + * 4. The names "The Jakarta Project", "Ant", and "Apache Software + * Foundation" must not be used to endorse or promote products derived + * from this software without prior written permission. For written + * permission, please contact apache@apache.org. + * + * 5. Products derived from this software may not be called "Apache" + * nor may "Apache" appear in their names without prior written + * permission of the Apache Group. + * + * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED + * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES + * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR + * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, + * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT + * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF + * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, + * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT + * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * ==================================================================== + * + * This software consists of voluntary contributions made by many + * individuals on behalf of the Apache Software Foundation. For more + * information on the Apache Software Foundation, please see + * . + */ +package org.apache.tools.ant.taskdefs.optional.junit.remote; + +import java.util.Vector; +import java.io.InputStream; +import java.io.IOException; +import java.io.BufferedReader; +import java.io.InputStreamReader; + +/** + * + * @author Stephane Bailliez + */ +public class EventDispatcher { + + /** the set of registered listeners */ + private Vector listeners = new Vector(); + + /** + * Add a new listener. + * @param listener a listener that will receive events from the client. + */ + public void addListener(TestRunListener listener) { + listeners.addElement(listener); + } + + public void removeListener(org.apache.tools.ant.taskdefs.optional.junit.remote.TestRunListener listener) { + listeners.removeElement(listener); + } + + /** + * Process a message from the client and dispatch the + * appropriate message to the listeners. + */ + public void dispatchEvent(TestRunEvent evt) { + // I hate switch/case but no need to design a complex + // system for limited events. + switch (evt.getType()){ + case TestRunEvent.RUN_STARTED: + fireRunStarted(evt); + break; + case TestRunEvent.RUN_ENDED: + fireRunEnded(evt); + break; + case TestRunEvent.RUN_STOPPED: + fireRunStopped(evt); + break; + case TestRunEvent.TEST_STARTED: + fireTestStarted(evt); + break; + case TestRunEvent.TEST_ERROR: + fireTestError(evt); + break; + case TestRunEvent.TEST_FAILURE: + fireTestFailure(evt); + break; + case TestRunEvent.TEST_ENDED: + fireTestEnded(evt); + break; + case TestRunEvent.TESTSUITE_ENDED: + fireSuiteEnded(evt); + break; + case TestRunEvent.TESTSUITE_STARTED: + fireSuiteStarted(evt); + break; + default: + // should not happen + } + } + + protected void fireRunStarted(TestRunEvent evt) { + synchronized (listeners) { + for (int i = 0; i < listeners.size(); i++) { + ((org.apache.tools.ant.taskdefs.optional.junit.remote.TestRunListener) listeners.elementAt(i)).onRunStarted(evt); + } + } + } + + protected void fireRunEnded(TestRunEvent evt) { + synchronized (listeners) { + for (int i = 0; i < listeners.size(); i++) { + ((org.apache.tools.ant.taskdefs.optional.junit.remote.TestRunListener) listeners.elementAt(i)).onRunEnded(evt); + } + } + } + + protected void fireTestStarted(TestRunEvent evt) { + synchronized (listeners) { + for (int i = 0; i < listeners.size(); i++) { + ((org.apache.tools.ant.taskdefs.optional.junit.remote.TestRunListener) listeners.elementAt(i)).onTestStarted(evt); + } + } + } + + protected void fireTestEnded(TestRunEvent evt) { + synchronized (listeners) { + for (int i = 0; i < listeners.size(); i++) { + ((org.apache.tools.ant.taskdefs.optional.junit.remote.TestRunListener) listeners.elementAt(i)).onTestEnded(evt); + } + } + } + + protected void fireTestFailure(TestRunEvent evt) { + synchronized (listeners) { + for (int i = 0; i < listeners.size(); i++) { + ((org.apache.tools.ant.taskdefs.optional.junit.remote.TestRunListener) listeners.elementAt(i)).onTestFailure(evt); + } + } + } + + protected void fireTestError(TestRunEvent evt) { + synchronized (listeners) { + for (int i = 0; i < listeners.size(); i++) { + ((org.apache.tools.ant.taskdefs.optional.junit.remote.TestRunListener) listeners.elementAt(i)).onTestError(evt); + } + } + } + + protected void fireSuiteStarted(TestRunEvent evt) { + synchronized (listeners) { + for (int i = 0; i < listeners.size(); i++) { + ((org.apache.tools.ant.taskdefs.optional.junit.remote.TestRunListener) listeners.elementAt(i)).onSuiteStarted(evt); + } + } + } + + protected void fireSuiteEnded(TestRunEvent evt) { + synchronized (listeners) { + for (int i = 0; i < listeners.size(); i++) { + ((org.apache.tools.ant.taskdefs.optional.junit.remote.TestRunListener) listeners.elementAt(i)).onSuiteEnded(evt); + } + } + } + + protected void fireRunStopped(TestRunEvent evt) { + synchronized (listeners) { + for (int i = 0; i < listeners.size(); i++) { + ((org.apache.tools.ant.taskdefs.optional.junit.remote.TestRunListener) listeners.elementAt(i)).onRunStopped(evt); + } + } + } + +} diff --git a/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/remote/MessageReader.java b/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/remote/MessageReader.java index 6f247aa6c..8f24f4732 100644 --- a/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/remote/MessageReader.java +++ b/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/remote/MessageReader.java @@ -203,7 +203,7 @@ public class MessageReader { protected void notifyTestFailed(int kind, String testname, String trace) { synchronized (listeners) { for (int i = 0; i < listeners.size(); i++) { - ((TestRunListener) listeners.elementAt(i)).onTestFailed(kind, testname, trace); + ((TestRunListener) listeners.elementAt(i)).onTestFailure(kind); } } } @@ -211,7 +211,7 @@ public class MessageReader { protected void notifyTestSuiteStarted(int count) { synchronized (listeners) { for (int i = 0; i < listeners.size(); i++) { - ((TestRunListener) listeners.elementAt(i)).onTestRunStarted(count); + ((TestRunListener) listeners.elementAt(i)).onRunStarted(count); } } } @@ -219,7 +219,7 @@ public class MessageReader { protected void notifyTestSuiteEnded(long elapsedtime) { synchronized (listeners) { for (int i = 0; i < listeners.size(); i++) { - ((TestRunListener) listeners.elementAt(i)).onTestRunEnded(elapsedtime); + ((TestRunListener) listeners.elementAt(i)).onRunEnded(elapsedtime); } } } @@ -227,7 +227,7 @@ public class MessageReader { protected void notifyTestSuiteStopped(long elapsedtime) { synchronized (listeners) { for (int i = 0; i < listeners.size(); i++) { - ((TestRunListener) listeners.elementAt(i)).onTestRunStopped(elapsedtime); + ((TestRunListener) listeners.elementAt(i)).onRunStopped(elapsedtime); } } } diff --git a/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/remote/Messenger.java b/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/remote/Messenger.java new file mode 100644 index 000000000..d6daad0d3 --- /dev/null +++ b/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/remote/Messenger.java @@ -0,0 +1,116 @@ +/* + * The Apache Software License, Version 1.1 + * + * Copyright (c) 2002 The Apache Software Foundation. All rights + * reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in + * the documentation and/or other materials provided with the + * distribution. + * + * 3. The end-user documentation included with the redistribution, if + * any, must include the following acknowlegement: + * "This product includes software developed by the + * Apache Software Foundation (http://www.apache.org/)." + * Alternately, this acknowlegement may appear in the software itself, + * if and wherever such third-party acknowlegements normally appear. + * + * 4. The names "The Jakarta Project", "Ant", and "Apache Software + * Foundation" must not be used to endorse or promote products derived + * from this software without prior written permission. For written + * permission, please contact apache@apache.org. + * + * 5. Products derived from this software may not be called "Apache" + * nor may "Apache" appear in their names without prior written + * permission of the Apache Group. + * + * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED + * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES + * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR + * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, + * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT + * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF + * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, + * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT + * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * ==================================================================== + * + * This software consists of voluntary contributions made by many + * individuals on behalf of the Apache Software Foundation. For more + * information on the Apache Software Foundation, please see + * . + */ +package org.apache.tools.ant.taskdefs.optional.junit.remote; + +import java.io.OutputStream; +import java.io.InputStream; +import java.io.IOException; +import java.io.ObjectInputStream; +import java.io.ObjectOutputStream; + +/** + * + * @author Stephane Bailliez + */ +public class Messenger { + + private InputStream in; + + private OutputStream out; + + public Messenger(InputStream in, OutputStream out) throws IOException { + setOutputStream( new ObjectOutputStream(out) ); + setInputStream( new ObjectInputStream(in) ); + } + + protected void finalize() throws Throwable { + close(); + } + + public void close() throws IOException { + if (in != null) { + in.close(); + in = null; + } + if (out != null) { + out.flush(); + out.close(); + out = null; + } + } + + public TestRunEvent read() throws IOException { + return (TestRunEvent)((ObjectInputStream)in).readObject(); + } + + public void writeEvent(TestRunEvent evt) throws IOException { + ((ObjectOutputStream)out).writeObject(evt); + } + + protected OutputStream getOutputStream(){ + return out; + } + + protected InputStream getInputStream(){ + return in; + } + + protected void setOutputStream(OutputStream out){ + this.out = out; + } + + protected void setInputStream(InputStream in){ + this.in = in; + } +} diff --git a/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/remote/Server.java b/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/remote/Server.java index e6ccb9021..72b9fb6e4 100644 --- a/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/remote/Server.java +++ b/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/remote/Server.java @@ -57,8 +57,6 @@ import java.io.IOException; import java.net.ServerSocket; import java.net.Socket; -import org.apache.tools.ant.taskdefs.optional.junit.TestRunListener; - /** * The server that will receive events from a remote client. * @@ -83,10 +81,9 @@ public class Server { private Socket client; /** the reader in charge of interpreting messages from the client */ - private MessageReader reader = new MessageReader(); + private Messenger messenger; - /** writer used to send message to clients */ - private MessageWriter writer; + private EventDispatcher dispatcher = new EventDispatcher(); public Server(int port) { this.port = port; @@ -102,7 +99,7 @@ public class Server { * @param listener a instance of a listener. */ public void addListener(TestRunListener listener) { - reader.addListener(listener); + dispatcher.addListener(listener); } /** @@ -110,7 +107,7 @@ public class Server { * @param listener a instance of a listener. */ public void removeListener(TestRunListener listener) { - reader.removeListener(listener); + dispatcher.removeListener(listener); } /** return whether there is a client running or not */ @@ -127,19 +124,16 @@ public class Server { /** cancel the connection to the client */ public void cancel() { if (isRunning()) { - writer.sendMessage(MessageIds.TEST_STOP); + TestRunEvent evt = new TestRunEvent(new Integer(-1), TestRunEvent.RUN_STOP); + messenger.writeEvent(evt); } } /** shutdown the server and any running client */ public void shutdown() { - if (writer != null) { - writer.close(); - writer = null; - } - if (reader != null) { - //@fixme what about the stream ? - reader = null; + if (messenger != null) { + messenger.close(); + messenger = null; } try { if (client != null) { @@ -166,8 +160,11 @@ public class Server { try { server = new ServerSocket(port); client = server.accept(); - writer = new MessageWriter(client.getOutputStream()); - reader.process(client.getInputStream()); + messenger = new Messenger(client.getInputStream(), client.getOutputStream()); + TestRunEvent evt = null; + while ( (evt = messenger.read()) != null ) { + dispatcher.dispatchEvent(evt); + } } catch (IOException e) { //@fixme this stacktrace might be normal when closing // the socket. So decompose the above in distinct steps diff --git a/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/remote/TestRunEvent.java b/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/remote/TestRunEvent.java new file mode 100644 index 000000000..df9b491fa --- /dev/null +++ b/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/remote/TestRunEvent.java @@ -0,0 +1,159 @@ +/* + * The Apache Software License, Version 1.1 + * + * Copyright (c) 2002 The Apache Software Foundation. All rights + * reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in + * the documentation and/or other materials provided with the + * distribution. + * + * 3. The end-user documentation included with the redistribution, if + * any, must include the following acknowlegement: + * "This product includes software developed by the + * Apache Software Foundation (http://www.apache.org/)." + * Alternately, this acknowlegement may appear in the software itself, + * if and wherever such third-party acknowlegements normally appear. + * + * 4. The names "The Jakarta Project", "Ant", and "Apache Software + * Foundation" must not be used to endorse or promote products derived + * from this software without prior written permission. For written + * permission, please contact apache@apache.org. + * + * 5. Products derived from this software may not be called "Apache" + * nor may "Apache" appear in their names without prior written + * permission of the Apache Group. + * + * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED + * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES + * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR + * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, + * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT + * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF + * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, + * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT + * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * ==================================================================== + * + * This software consists of voluntary contributions made by many + * individuals on behalf of the Apache Software Foundation. For more + * information on the Apache Software Foundation, please see + * . + */ +package org.apache.tools.ant.taskdefs.optional.junit.remote; + +import java.util.EventObject; +import java.util.Properties; + +import org.apache.tools.ant.util.StringUtils; + +/** + * + * @author Stephane Bailliez + */ +public class TestRunEvent extends EventObject { + + // received from clients + public final static int RUN_STARTED = 0; + public final static int RUN_ENDED = 1; + public final static int RUN_STOPPED = 2; + public final static int TEST_STARTED = 3; + public final static int TEST_FAILURE = 4; + public final static int TEST_ERROR = 5; + public final static int TEST_ENDED = 6; + public final static int SUITE_STARTED = 7; + public final static int SUITE_ENDED = 8; + + // received from server + public final static int RUN_STOP = 9; + + /** the type of event */ + private int type = -1; + + /** timestamp for all tests */ + private long timestamp = System.currentTimeMillis(); + + /** name of testcase(method name) or testsuite (classname) */ + private String name; + + /** stacktrace for error or failure */ + private String stacktrace; + + /** properties for end of testrun */ + private Properties props; + + public TestRunEvent(Integer id, int type){ + super(id); + this.type = type; + } + + public TestRunEvent(Integer id, int type, String name){ + this(id, type); + this.name = name; + } + + public TestRunEvent(Integer id, int type, Properties props){ + this(id, type); + this.props = props; + } + + public TestRunEvent(Integer id, int type, String name, Throwable t){ + this(id, type, name); + this.stacktrace = StringUtils.getStackTrace(t); + } + + public void setType(int type) { + this.type = type; + } + + public void setTimeStamp(long timestamp) { + this.timestamp = timestamp; + } + + public void setStackTrace(String stacktrace) { + this.stacktrace = stacktrace; + } + + public void setName(String name) { + this.name = name; + } + + public void setProperties(Properties props) { + this.props = props; + } + + public int getType(){ + return type; + } + + public long getTimeStamp(){ + return timestamp; + } + + public String getName(){ + return name; + } + + public String getStackTrace(){ + return stacktrace; + } + + public Properties getProperties(){ + return props; + } + + public String toString(){ + return "Id: " + source + ", Type: " + type; + } +} diff --git a/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/remote/TestRunListener.java b/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/remote/TestRunListener.java new file mode 100644 index 000000000..4476a8c5a --- /dev/null +++ b/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/remote/TestRunListener.java @@ -0,0 +1,76 @@ +/* + * The Apache Software License, Version 1.1 + * + * Copyright (c) 2002 The Apache Software Foundation. All rights + * reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in + * the documentation and/or other materials provided with the + * distribution. + * + * 3. The end-user documentation included with the redistribution, if + * any, must include the following acknowlegement: + * "This product includes software developed by the + * Apache Software Foundation (http://www.apache.org/)." + * Alternately, this acknowlegement may appear in the software itself, + * if and wherever such third-party acknowlegements normally appear. + * + * 4. The names "The Jakarta Project", "Ant", and "Apache Software + * Foundation" must not be used to endorse or promote products derived + * from this software without prior written permission. For written + * permission, please contact apache@apache.org. + * + * 5. Products derived from this software may not be called "Apache" + * nor may "Apache" appear in their names without prior written + * permission of the Apache Group. + * + * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED + * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES + * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR + * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, + * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT + * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF + * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, + * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT + * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * ==================================================================== + * + * This software consists of voluntary contributions made by many + * individuals on behalf of the Apache Software Foundation. For more + * information on the Apache Software Foundation, please see + * . + */ +package org.apache.tools.ant.taskdefs.optional.junit.remote; + +import java.util.EventListener; + + +/** + * + * @author Stephane Bailliez + */ +public interface TestRunListener extends EventListener { + + void onRunStarted(TestRunEvent evt); + void onRunEnded(TestRunEvent evt); + void onRunStopped(TestRunEvent evt); + + void onSuiteStarted(TestRunEvent evt); + void onSuiteEnded(TestRunEvent evt); + + void onTestStarted(TestRunEvent evt); + void onTestError(TestRunEvent evt); + void onTestFailure(TestRunEvent evt); + void onTestEnded(TestRunEvent evt); +} diff --git a/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/remote/TestRunner.java b/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/remote/TestRunner.java index 96a26bff2..8759c2ca8 100644 --- a/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/remote/TestRunner.java +++ b/proposal/sandbox/junit/src/main/org/apache/tools/ant/taskdefs/optional/junit/remote/TestRunner.java @@ -61,6 +61,7 @@ import java.net.Socket; import java.util.Properties; import java.util.StringTokenizer; import java.util.Vector; +import java.util.Random; import junit.framework.AssertionFailedError; import junit.framework.Test; @@ -86,6 +87,9 @@ import org.apache.tools.ant.util.StringUtils; */ public class TestRunner implements TestListener { + /** unique identifier for the runner */ + private final Integer id = new Integer( (new Random()).nextInt() ); + /** host to connect to */ private String host = "127.0.0.1"; @@ -104,10 +108,7 @@ public class TestRunner implements TestListener { private Socket clientSocket; /** writer to send message to the server */ - private MessageWriter writer; - - /** reader to listen for a shutdown from the server */ - private BufferedReader reader; + private Messenger messenger; /** bean constructor */ public TestRunner() { @@ -152,9 +153,9 @@ public class TestRunner implements TestListener { private class StopThread extends Thread { public void run() { try { - String line = null; - if ((line = reader.readLine()) != null) { - if (line.startsWith(MessageIds.TEST_STOP)) { + TestRunEvent evt = null; + if ((evt = messenger.read()) != null) { + if (evt.getType() == TestRunEvent.RUN_STOP) { TestRunner.this.stop(); } } @@ -298,26 +299,26 @@ public class TestRunner implements TestListener { // count all testMethods and inform TestRunListeners int count = countTests(suites); log("Total tests to run: " + count); - writer.notifyTestRunStarted(count); - - // send system properties to know for the JVM status - writer.notifySystemProperties(); + fireEvent(new TestRunEvent(id, TestRunEvent.RUN_STARTED)); long startTime = System.currentTimeMillis(); for (int i = 0; i < suites.length; i++) { + String name = suites[i].getClass().getName(); if (suites[i] instanceof TestCase) { - suites[i] = new TestSuite(suites[i].getClass().getName()); + suites[i] = new TestSuite(name); } log("running suite: " + suites[i]); + fireEvent(new TestRunEvent(id, TestRunEvent.SUITE_STARTED, name)); suites[i].run(testResult); + fireEvent(new TestRunEvent(id, TestRunEvent.SUITE_ENDED, name)); } // inform TestRunListeners of test end long elapsedTime = System.currentTimeMillis() - startTime; if (testResult == null || testResult.shouldStop()) { - writer.notifyTestRunStopped(elapsedTime); + fireEvent(new TestRunEvent(id, TestRunEvent.RUN_STOPPED, System.getProperties())); } else { - writer.notifyTestRunEnded(elapsedTime); + fireEvent(new TestRunEvent(id, TestRunEvent.RUN_ENDED, System.getProperties())); } log("Finished after " + elapsedTime + "ms"); shutDown(); @@ -345,23 +346,16 @@ public class TestRunner implements TestListener { protected void connect() throws IOException { log("Connecting to " + host + " on port " + port + "..."); clientSocket = new Socket(host, port); - writer = new MessageWriter(clientSocket.getOutputStream()); - reader = new BufferedReader(new InputStreamReader(clientSocket.getInputStream())); + messenger = new Messenger(clientSocket.getInputStream(), clientSocket.getOutputStream()); new StopThread().start(); } protected void shutDown() { - - if (writer != null) { - writer.close(); - writer = null; - } - try { - if (reader != null) { - reader.close(); - reader = null; + if (messenger != null) { + messenger.close(); + messenger = null; } } catch (IOException e) { log(e); @@ -377,6 +371,9 @@ public class TestRunner implements TestListener { } } + protected void fireEvent(TestRunEvent evt){ + messenger.writeEvent(evt); + } // -------- JUnit TestListener implementation @@ -384,14 +381,13 @@ public class TestRunner implements TestListener { public void startTest(Test test) { String testName = test.toString(); log("starting test: " + test); - writer.notifyTestStarted(testName); + fireEvent(new TestRunEvent(id, TestRunEvent.TEST_STARTED, testName)); } public void addError(Test test, Throwable t) { log("Adding error for test: " + test); String testName = test.toString(); - String trace = StringUtils.getStackTrace(t); - writer.notifyTestFailed(TestRunListener.STATUS_ERROR, testName, trace); + fireEvent(new TestRunEvent(id, TestRunEvent.TEST_ERROR, testName, t)); } /** @@ -409,14 +405,13 @@ public class TestRunner implements TestListener { public void addFailure(Test test, Throwable t) { log("Adding failure for test: " + test); String testName = test.toString(); - String trace = StringUtils.getStackTrace(t); - writer.notifyTestFailed(TestRunListener.STATUS_FAILURE, testName, trace); + fireEvent(new TestRunEvent(id, TestRunEvent.TEST_FAILURE, testName, t)); } public void endTest(Test test) { log("Ending test: " + test); String testName = test.toString(); - writer.notifyTestEnded(testName); + fireEvent(new TestRunEvent(id, TestRunEvent.TEST_ENDED, testName)); } public void log(String msg) {