PR: 30798 While fixing this, I noticed that printsummary="withOutAndErr" didn't work with fork="true". git-svn-id: https://svn.apache.org/repos/asf/ant/core/trunk@276916 13f79535-47bb-0310-9956-ffa450edef68master
| @@ -7,6 +7,10 @@ | |||||
| <pathelement location="../../../../../build/testcases" /> | <pathelement location="../../../../../build/testcases" /> | ||||
| </path> | </path> | ||||
| <target name="cleanup"> | |||||
| <delete file="testlog.txt"/> | |||||
| </target> | |||||
| <target name="testForkedOutput"> | <target name="testForkedOutput"> | ||||
| <junit fork="yes" haltonerror="true" haltonfailure="true" | <junit fork="yes" haltonerror="true" haltonfailure="true" | ||||
| showoutput="${showoutput}"> | showoutput="${showoutput}"> | ||||
| @@ -69,4 +73,23 @@ | |||||
| <classpath refid="test" /> | <classpath refid="test" /> | ||||
| </junit> | </junit> | ||||
| </target> | </target> | ||||
| <target name="capture"> | |||||
| <property name="fork" value="false"/> | |||||
| <junit fork="${fork}"> | |||||
| <test | |||||
| name="org.apache.tools.ant.taskdefs.optional.junit.Printer" | |||||
| outfile="testlog"/> | |||||
| <formatter type="plain"/> | |||||
| <classpath refid="test"/> | |||||
| </junit> | |||||
| </target> | |||||
| <target name="captureToSummary"> | |||||
| <property name="fork" value="true"/> | |||||
| <junit fork="${fork}" printSummary="withOutAndErr"> | |||||
| <test name="org.apache.tools.ant.taskdefs.optional.junit.Printer"/> | |||||
| <classpath refid="test"/> | |||||
| </junit> | |||||
| </target> | |||||
| </project> | </project> | ||||
| @@ -805,9 +805,14 @@ public class JUnitTask extends Task { | |||||
| if (summary) { | if (summary) { | ||||
| log("Running " + test.getName(), Project.MSG_INFO); | log("Running " + test.getName(), Project.MSG_INFO); | ||||
| String prefix = ""; | |||||
| if ("withoutanderr".equalsIgnoreCase(summaryValue)) { | |||||
| prefix = "OutErr"; | |||||
| } | |||||
| cmd.createArgument() | cmd.createArgument() | ||||
| .setValue("formatter" | .setValue("formatter" | ||||
| + "=org.apache.tools.ant.taskdefs.optional.junit.SummaryJUnitResultFormatter"); | |||||
| + "=org.apache.tools.ant.taskdefs.optional.junit." | |||||
| + prefix + "SummaryJUnitResultFormatter"); | |||||
| } | } | ||||
| cmd.createArgument().setValue("showoutput=" | cmd.createArgument().setValue("showoutput=" | ||||
| @@ -126,16 +126,6 @@ public class JUnitTestRunner implements TestListener { | |||||
| */ | */ | ||||
| private boolean haltOnFailure = false; | private boolean haltOnFailure = false; | ||||
| /** | |||||
| * The corresponding testsuite. | |||||
| */ | |||||
| private Test suite = null; | |||||
| /** | |||||
| * Exception caught in constructor. | |||||
| */ | |||||
| private Exception exception; | |||||
| /** | /** | ||||
| * Returncode | * Returncode | ||||
| */ | */ | ||||
| @@ -158,6 +148,9 @@ public class JUnitTestRunner implements TestListener { | |||||
| /** Running more than one test suite? */ | /** Running more than one test suite? */ | ||||
| private static boolean multipleTests = false; | private static boolean multipleTests = false; | ||||
| /** ClassLoader passed in in non-forked mode. */ | |||||
| private ClassLoader loader; | |||||
| /** | /** | ||||
| * Constructor for fork=true or when the user hasn't specified a | * Constructor for fork=true or when the user hasn't specified a | ||||
| * classpath. | * classpath. | ||||
| @@ -197,38 +190,7 @@ public class JUnitTestRunner implements TestListener { | |||||
| this.haltOnError = haltOnError; | this.haltOnError = haltOnError; | ||||
| this.haltOnFailure = haltOnFailure; | this.haltOnFailure = haltOnFailure; | ||||
| this.showOutput = showOutput; | this.showOutput = showOutput; | ||||
| try { | |||||
| Class testClass = null; | |||||
| if (loader == null) { | |||||
| testClass = Class.forName(test.getName()); | |||||
| } else { | |||||
| testClass = Class.forName(test.getName(), true, loader); | |||||
| } | |||||
| Method suiteMethod = null; | |||||
| try { | |||||
| // check if there is a suite method | |||||
| suiteMethod = testClass.getMethod("suite", new Class[0]); | |||||
| } catch (NoSuchMethodException e) { | |||||
| // no appropriate suite method found. We don't report any | |||||
| // error here since it might be perfectly normal. | |||||
| } | |||||
| if (suiteMethod != null) { | |||||
| // if there is a suite method available, then try | |||||
| // to extract the suite from it. If there is an error | |||||
| // here it will be caught below and reported. | |||||
| suite = (Test) suiteMethod.invoke(null, new Class[0]); | |||||
| } else { | |||||
| // try to extract a test suite automatically | |||||
| // this will generate warnings if the class is no suitable Test | |||||
| suite = new TestSuite(testClass); | |||||
| } | |||||
| } catch (Exception e) { | |||||
| retCode = ERRORS; | |||||
| exception = e; | |||||
| } | |||||
| this.loader = loader; | |||||
| } | } | ||||
| public void run() { | public void run() { | ||||
| @@ -238,77 +200,114 @@ public class JUnitTestRunner implements TestListener { | |||||
| res.addListener((TestListener) formatters.elementAt(i)); | res.addListener((TestListener) formatters.elementAt(i)); | ||||
| } | } | ||||
| long start = System.currentTimeMillis(); | |||||
| ByteArrayOutputStream errStrm = new ByteArrayOutputStream(); | |||||
| systemError = new PrintStream(errStrm); | |||||
| fireStartTestSuite(); | |||||
| if (exception != null) { // had an exception in the constructor | |||||
| for (int i = 0; i < formatters.size(); i++) { | |||||
| ((TestListener) formatters.elementAt(i)).addError(null, | |||||
| exception); | |||||
| } | |||||
| junitTest.setCounts(1, 0, 1); | |||||
| junitTest.setRunTime(0); | |||||
| } else { | |||||
| ByteArrayOutputStream outStrm = new ByteArrayOutputStream(); | |||||
| systemOut = new PrintStream(outStrm); | |||||
| PrintStream savedOut = null; | |||||
| PrintStream savedErr = null; | |||||
| ByteArrayOutputStream errStrm = new ByteArrayOutputStream(); | |||||
| systemError = new PrintStream(errStrm); | |||||
| if (forked) { | |||||
| savedOut = System.out; | |||||
| savedErr = System.err; | |||||
| if (!showOutput) { | |||||
| System.setOut(systemOut); | |||||
| System.setErr(systemError); | |||||
| } else { | |||||
| System.setOut(new PrintStream( | |||||
| new TeeOutputStream(savedOut, systemOut) | |||||
| ) | |||||
| ); | |||||
| System.setErr(new PrintStream( | |||||
| new TeeOutputStream(savedErr, | |||||
| systemError) | |||||
| ) | |||||
| ); | |||||
| } | |||||
| perm = null; | |||||
| } else { | |||||
| if (perm != null) { | |||||
| perm.setSecurityManager(); | |||||
| } | |||||
| } | |||||
| ByteArrayOutputStream outStrm = new ByteArrayOutputStream(); | |||||
| systemOut = new PrintStream(outStrm); | |||||
| Test suite = null; | |||||
| Exception exception = null; | |||||
| PrintStream savedOut = null; | |||||
| PrintStream savedErr = null; | |||||
| try { | |||||
| if (forked) { | |||||
| savedOut = System.out; | |||||
| savedErr = System.err; | |||||
| if (!showOutput) { | |||||
| System.setOut(systemOut); | |||||
| System.setErr(systemError); | |||||
| try { | |||||
| Class testClass = null; | |||||
| if (loader == null) { | |||||
| testClass = Class.forName(junitTest.getName()); | |||||
| } else { | } else { | ||||
| System.setOut(new PrintStream( | |||||
| new TeeOutputStream(savedOut, systemOut) | |||||
| ) | |||||
| ); | |||||
| System.setErr(new PrintStream( | |||||
| new TeeOutputStream(savedErr, | |||||
| systemError) | |||||
| ) | |||||
| ); | |||||
| testClass = Class.forName(junitTest.getName(), true, | |||||
| loader); | |||||
| } | } | ||||
| perm = null; | |||||
| } else { | |||||
| if (perm != null) { | |||||
| perm.setSecurityManager(); | |||||
| Method suiteMethod = null; | |||||
| try { | |||||
| // check if there is a suite method | |||||
| suiteMethod = testClass.getMethod("suite", new Class[0]); | |||||
| } catch (NoSuchMethodException e) { | |||||
| // no appropriate suite method found. We don't report any | |||||
| // error here since it might be perfectly normal. | |||||
| } | |||||
| if (suiteMethod != null) { | |||||
| // if there is a suite method available, then try | |||||
| // to extract the suite from it. If there is an error | |||||
| // here it will be caught below and reported. | |||||
| suite = (Test) suiteMethod.invoke(null, new Class[0]); | |||||
| } else { | |||||
| // try to extract a test suite automatically this | |||||
| // will generate warnings if the class is no | |||||
| // suitable Test | |||||
| suite = new TestSuite(testClass); | |||||
| } | } | ||||
| } catch (Exception e) { | |||||
| retCode = ERRORS; | |||||
| exception = e; | |||||
| } | } | ||||
| long start = System.currentTimeMillis(); | |||||
| try { | |||||
| suite.run(res); | |||||
| } finally { | |||||
| if (perm != null) { | |||||
| perm.restoreSecurityManager(); | |||||
| } | |||||
| if (savedOut != null) { | |||||
| System.setOut(savedOut); | |||||
| fireStartTestSuite(); | |||||
| if (exception != null) { // had an exception constructing suite | |||||
| for (int i = 0; i < formatters.size(); i++) { | |||||
| ((TestListener) formatters.elementAt(i)) | |||||
| .addError(null, exception); | |||||
| } | } | ||||
| if (savedErr != null) { | |||||
| System.setErr(savedErr); | |||||
| junitTest.setCounts(1, 0, 1); | |||||
| junitTest.setRunTime(0); | |||||
| } else { | |||||
| try { | |||||
| suite.run(res); | |||||
| } finally { | |||||
| junitTest.setCounts(res.runCount(), res.failureCount(), | |||||
| res.errorCount()); | |||||
| junitTest.setRunTime(System.currentTimeMillis() - start); | |||||
| } | } | ||||
| systemError.close(); | |||||
| systemError = null; | |||||
| systemOut.close(); | |||||
| systemOut = null; | |||||
| sendOutAndErr(new String(outStrm.toByteArray()), | |||||
| new String(errStrm.toByteArray())); | |||||
| junitTest.setCounts(res.runCount(), res.failureCount(), | |||||
| res.errorCount()); | |||||
| junitTest.setRunTime(System.currentTimeMillis() - start); | |||||
| } | } | ||||
| } finally { | |||||
| if (perm != null) { | |||||
| perm.restoreSecurityManager(); | |||||
| } | |||||
| if (savedOut != null) { | |||||
| System.setOut(savedOut); | |||||
| } | |||||
| if (savedErr != null) { | |||||
| System.setErr(savedErr); | |||||
| } | |||||
| systemError.close(); | |||||
| systemError = null; | |||||
| systemOut.close(); | |||||
| systemOut = null; | |||||
| sendOutAndErr(new String(outStrm.toByteArray()), | |||||
| new String(errStrm.toByteArray())); | |||||
| } | } | ||||
| fireEndTestSuite(); | fireEndTestSuite(); | ||||
| @@ -0,0 +1,35 @@ | |||||
| /* | |||||
| * Copyright 2004 The Apache Software Foundation | |||||
| * | |||||
| * Licensed under the Apache License, Version 2.0 (the "License"); | |||||
| * you may not use this file except in compliance with the License. | |||||
| * You may obtain a copy of the License at | |||||
| * | |||||
| * http://www.apache.org/licenses/LICENSE-2.0 | |||||
| * | |||||
| * Unless required by applicable law or agreed to in writing, software | |||||
| * distributed under the License is distributed on an "AS IS" BASIS, | |||||
| * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||||
| * See the License for the specific language governing permissions and | |||||
| * limitations under the License. | |||||
| * | |||||
| */ | |||||
| package org.apache.tools.ant.taskdefs.optional.junit; | |||||
| /** | |||||
| * Used instead of SummaryJUnitResultFormatter in forked tests if | |||||
| * withOutAndErr is requested. | |||||
| */ | |||||
| public class OutErrSummaryJUnitResultFormatter | |||||
| extends SummaryJUnitResultFormatter { | |||||
| /** | |||||
| * Empty | |||||
| */ | |||||
| public OutErrSummaryJUnitResultFormatter() { | |||||
| super(); | |||||
| setWithOutAndErr(true); | |||||
| } | |||||
| } | |||||
| @@ -1,5 +1,5 @@ | |||||
| /* | /* | ||||
| * Copyright 2002,2004 The Apache Software Foundation | |||||
| * Copyright 2004 The Apache Software Foundation | |||||
| * | * | ||||
| * Licensed under the Apache License, Version 2.0 (the "License"); | * Licensed under the Apache License, Version 2.0 (the "License"); | ||||
| * you may not use this file except in compliance with the License. | * you may not use this file except in compliance with the License. | ||||
| @@ -16,17 +16,15 @@ | |||||
| */ | */ | ||||
| package org.apache.tools.ant.taskdefs.optional.junit; | package org.apache.tools.ant.taskdefs.optional.junit; | ||||
| import org.apache.tools.ant.Project; | |||||
| import org.apache.tools.ant.BuildException; | |||||
| import org.apache.tools.ant.BuildFileTest; | import org.apache.tools.ant.BuildFileTest; | ||||
| import java.lang.reflect.InvocationTargetException; | |||||
| import java.io.BufferedReader; | |||||
| import java.io.FileReader; | |||||
| import java.io.IOException; | |||||
| public class JUnitTaskTest extends BuildFileTest { | public class JUnitTaskTest extends BuildFileTest { | ||||
| /** | /** | ||||
| * Constructor for the JUnitTaskTest object | * Constructor for the JUnitTaskTest object | ||||
| * | |||||
| * @param name we dont know | |||||
| */ | */ | ||||
| public JUnitTaskTest(String name) { | public JUnitTaskTest(String name) { | ||||
| super(name); | super(name); | ||||
| @@ -45,7 +43,7 @@ public class JUnitTaskTest extends BuildFileTest { | |||||
| * The teardown method for JUnit | * The teardown method for JUnit | ||||
| */ | */ | ||||
| public void tearDown() { | public void tearDown() { | ||||
| //executeTarget("cleanup"); | |||||
| executeTarget("cleanup"); | |||||
| } | } | ||||
| public void testCrash() { | public void testCrash() { | ||||
| @@ -64,5 +62,69 @@ public class JUnitTaskTest extends BuildFileTest { | |||||
| expectPropertyUnset("notimeout", "timeout"); | expectPropertyUnset("notimeout", "timeout"); | ||||
| } | } | ||||
| public void testNonForkedCapture() throws IOException { | |||||
| executeTarget("capture"); | |||||
| assertNoPrint(getLog(), "log"); | |||||
| assertNoPrint(getFullLog(), "debug log"); | |||||
| } | |||||
| public void testForkedCapture() throws IOException { | |||||
| getProject().setProperty("fork", "true"); | |||||
| testNonForkedCapture(); | |||||
| // those would fail because of the way BuildFileTest captures output | |||||
| assertNoPrint(getOutput(), "output"); | |||||
| assertNoPrint(getError(), "error output"); | |||||
| assertOutput(); | |||||
| } | |||||
| private void assertNoPrint(String result, String where) { | |||||
| assertTrue(where + " '" + result + "' must not contain print statement", | |||||
| result.indexOf("print to System.") == -1); | |||||
| } | |||||
| private void assertOutput() throws IOException { | |||||
| FileReader inner = new FileReader(getProject() | |||||
| .resolveFile("testlog.txt")); | |||||
| BufferedReader reader = new BufferedReader(inner); | |||||
| try { | |||||
| String line = reader.readLine(); | |||||
| assertEquals("Testsuite: org.apache.tools.ant.taskdefs.optional.junit.Printer", | |||||
| line); | |||||
| line = reader.readLine(); | |||||
| assertNotNull(line); | |||||
| assertTrue(line.startsWith("Tests run: 1, Failures: 0, Errors: 0, Time elapsed:")); | |||||
| line = reader.readLine(); | |||||
| assertEquals("------------- Standard Output ---------------", | |||||
| line); | |||||
| assertPrint(reader.readLine(), "static", "out"); | |||||
| assertPrint(reader.readLine(), "constructor", "out"); | |||||
| assertPrint(reader.readLine(), "method", "out"); | |||||
| line = reader.readLine(); | |||||
| assertEquals("------------- ---------------- ---------------", | |||||
| line); | |||||
| line = reader.readLine(); | |||||
| assertEquals("------------- Standard Error -----------------", | |||||
| line); | |||||
| assertPrint(reader.readLine(), "static", "err"); | |||||
| assertPrint(reader.readLine(), "constructor", "err"); | |||||
| assertPrint(reader.readLine(), "method", "err"); | |||||
| line = reader.readLine(); | |||||
| assertEquals("------------- ---------------- ---------------", | |||||
| line); | |||||
| line = reader.readLine(); | |||||
| assertEquals("", line); | |||||
| line = reader.readLine(); | |||||
| assertNotNull(line); | |||||
| assertTrue(line.startsWith("Testcase: testNoCrash took ")); | |||||
| } finally { | |||||
| inner.close(); | |||||
| } | |||||
| } | |||||
| private void assertPrint(String line, String from, String to) { | |||||
| String search = from + " print to System." + to; | |||||
| assertEquals(search, line); | |||||
| } | |||||
| } | } | ||||
| @@ -16,9 +16,7 @@ | |||||
| */ | */ | ||||
| package org.apache.tools.ant.taskdefs.optional.junit; | package org.apache.tools.ant.taskdefs.optional.junit; | ||||
| import junit.framework.Test; | |||||
| import junit.framework.TestCase; | import junit.framework.TestCase; | ||||
| import junit.framework.TestResult; | |||||
| /** | /** | ||||
| * @version $Revision$ | * @version $Revision$ | ||||
| @@ -0,0 +1,42 @@ | |||||
| /* | |||||
| * Copyright 2004 The Apache Software Foundation | |||||
| * | |||||
| * Licensed under the Apache License, Version 2.0 (the "License"); | |||||
| * you may not use this file except in compliance with the License. | |||||
| * You may obtain a copy of the License at | |||||
| * | |||||
| * http://www.apache.org/licenses/LICENSE-2.0 | |||||
| * | |||||
| * Unless required by applicable law or agreed to in writing, software | |||||
| * distributed under the License is distributed on an "AS IS" BASIS, | |||||
| * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||||
| * See the License for the specific language governing permissions and | |||||
| * limitations under the License. | |||||
| * | |||||
| */ | |||||
| package org.apache.tools.ant.taskdefs.optional.junit; | |||||
| import junit.framework.TestCase; | |||||
| /** | |||||
| * @version $Revision$ | |||||
| */ | |||||
| public class Printer extends TestCase { | |||||
| public Printer(String name) { | |||||
| super(name); | |||||
| System.err.println("constructor print to System.err"); | |||||
| System.out.println("constructor print to System.out"); | |||||
| } | |||||
| static { | |||||
| System.err.println("static print to System.err"); | |||||
| System.out.println("static print to System.out"); | |||||
| } | |||||
| public void testNoCrash() { | |||||
| System.err.println("method print to System.err"); | |||||
| System.out.println("method print to System.out"); | |||||
| } | |||||
| } | |||||
| @@ -16,9 +16,7 @@ | |||||
| */ | */ | ||||
| package org.apache.tools.ant.taskdefs.optional.junit; | package org.apache.tools.ant.taskdefs.optional.junit; | ||||
| import junit.framework.Test; | |||||
| import junit.framework.TestCase; | import junit.framework.TestCase; | ||||
| import junit.framework.TestResult; | |||||
| /** | /** | ||||
| * @version $Revision$ | * @version $Revision$ | ||||
| @@ -16,9 +16,7 @@ | |||||
| */ | */ | ||||
| package org.apache.tools.ant.taskdefs.optional.junit; | package org.apache.tools.ant.taskdefs.optional.junit; | ||||
| import junit.framework.Test; | |||||
| import junit.framework.TestCase; | import junit.framework.TestCase; | ||||
| import junit.framework.TestResult; | |||||
| /** | /** | ||||
| * @version $Revision$ | * @version $Revision$ | ||||