You are viewing a plain text version of this content. The canonical link for it is here.
Posted to dev@ant.apache.org by jg...@apache.org on 2006/02/28 22:07:18 UTC

svn commit: r381780 - in /ant/core/trunk: WHATSNEW docs/manual/OptionalTasks/junit.html src/main/org/apache/tools/ant/taskdefs/optional/junit/JUnitTestRunner.java src/main/org/apache/tools/ant/taskdefs/optional/junit/JUnitVersionHelper.java

Author: jglick
Date: Tue Feb 28 13:07:15 2006
New Revision: 381780

URL: http://svn.apache.org/viewcvs?rev=381780&view=rev
Log:
#38811: support for JUnit 4.0.

Modified:
    ant/core/trunk/WHATSNEW
    ant/core/trunk/docs/manual/OptionalTasks/junit.html
    ant/core/trunk/src/main/org/apache/tools/ant/taskdefs/optional/junit/JUnitTestRunner.java
    ant/core/trunk/src/main/org/apache/tools/ant/taskdefs/optional/junit/JUnitVersionHelper.java

Modified: ant/core/trunk/WHATSNEW
URL: http://svn.apache.org/viewcvs/ant/core/trunk/WHATSNEW?rev=381780&r1=381779&r2=381780&view=diff
==============================================================================
--- ant/core/trunk/WHATSNEW (original)
+++ ant/core/trunk/WHATSNEW Tue Feb 28 13:07:15 2006
@@ -77,6 +77,8 @@
 Fixed bugs:
 -----------
 
+* <junit> now supports JUnit 4. Bugzilla Report 38811.
+
 * <junit> can now work with junit.jar in its <classpath>. Bugzilla Report 38799.
 
 * Some potential NullPointerExceptions, Bugzilla Reports 37765 and 38056

Modified: ant/core/trunk/docs/manual/OptionalTasks/junit.html
URL: http://svn.apache.org/viewcvs/ant/core/trunk/docs/manual/OptionalTasks/junit.html?rev=381780&r1=381779&r2=381780&view=diff
==============================================================================
--- ant/core/trunk/docs/manual/OptionalTasks/junit.html (original)
+++ ant/core/trunk/docs/manual/OptionalTasks/junit.html Tue Feb 28 13:07:15 2006
@@ -12,7 +12,8 @@
 version of the framework can be found at
 <a href="http://www.junit.org">http://www.junit.org</a>.
 This task has been tested with JUnit 3.0 up to JUnit 3.8.1; it won't
-work with versions prior to JUnit 3.0.</p>
+work with versions prior to JUnit 3.0. It also works with JUnit 4.0, including
+"pure" JUnit 4 tests using only annotations and no <code>JUnit4TestAdapter</code>.</p>
 <p><strong>Note:</strong> This task depends on external libraries not included
 in the Ant distribution.  See <a href="../install.html#librarydependencies">
 Library Dependencies</a> for more information.

Modified: ant/core/trunk/src/main/org/apache/tools/ant/taskdefs/optional/junit/JUnitTestRunner.java
URL: http://svn.apache.org/viewcvs/ant/core/trunk/src/main/org/apache/tools/ant/taskdefs/optional/junit/JUnitTestRunner.java?rev=381780&r1=381779&r2=381780&view=diff
==============================================================================
--- ant/core/trunk/src/main/org/apache/tools/ant/taskdefs/optional/junit/JUnitTestRunner.java (original)
+++ ant/core/trunk/src/main/org/apache/tools/ant/taskdefs/optional/junit/JUnitTestRunner.java Tue Feb 28 13:07:15 2006
@@ -35,6 +35,7 @@
 import java.util.Vector;
 import junit.framework.AssertionFailedError;
 import junit.framework.Test;
+import junit.framework.TestFailure;
 import junit.framework.TestListener;
 import junit.framework.TestResult;
 import junit.framework.TestSuite;
@@ -99,7 +100,13 @@
                 "junit.textui.TestRunner",
                 "java.lang.reflect.Method.invoke(",
                 "sun.reflect.",
-                "org.apache.tools.ant."
+                "org.apache.tools.ant.",
+                // JUnit 4 support:
+                "org.junit.",
+                "junit.framework.JUnit4TestAdapter",
+                // See wrapListener for reason:
+                "Caused by: java.lang.AssertionError",
+                " more",
         };
 
 
@@ -141,6 +148,9 @@
     /** Do we print TestListener events? */
     private boolean logTestListenerEvents = false;
 
+    /** Turned on if we are using JUnit 4 for this test suite. see #38811 */
+    private boolean junit4;
+
     /**
      * Constructor for fork=true or when the user hasn't specified a
      * classpath.
@@ -212,9 +222,9 @@
     
     public void run() {
         res = new TestResult();
-        res.addListener(this);
+        res.addListener(wrapListener(this));
         for (int i = 0; i < formatters.size(); i++) {
-            res.addListener((TestListener) formatters.elementAt(i));
+            res.addListener(wrapListener((TestListener) formatters.elementAt(i)));
         }
 
         ByteArrayOutputStream errStrm = new ByteArrayOutputStream();
@@ -255,6 +265,19 @@
         try {
 
             try {
+                Class junit4TestAdapterClass = null;
+                // Note that checking for JDK 5 directly won't work; under JDK 4, this will already have failed.
+                try {
+                    if (loader == null) {
+                        junit4TestAdapterClass = Class.forName("junit.framework.JUnit4TestAdapter");
+                    } else {
+                        junit4TestAdapterClass = Class.forName("junit.framework.JUnit4TestAdapter", true, loader);
+                    }
+                } catch (ClassNotFoundException e) {
+                    // OK, fall back to JUnit 3.
+                }
+                junit4 = junit4TestAdapterClass != null;
+
                 Class testClass = null;
                 if (loader == null) {
                     testClass = Class.forName(junitTest.getName());
@@ -263,24 +286,33 @@
                                               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]);
+                if (junit4) {
+                    // Let's use it!
+                    suite = (Test) junit4TestAdapterClass.getConstructor(new Class[] {Class.class}).
+                            newInstance(new Object[] {testClass});
                 } else {
-                    // try to extract a test suite automatically this
-                    // will generate warnings if the class is no
-                    // suitable Test
-                    suite = new TestSuite(testClass);
+                    // Use JUnit 3.
+
+                    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 (Throwable e) {
@@ -303,8 +335,13 @@
                     logTestListenerEvent("tests to run: " + suite.countTestCases());
                     suite.run(res);
                 } finally {
-                    junitTest.setCounts(res.runCount(), res.failureCount(),
-                                        res.errorCount());
+                    if (junit4) {
+                        int[] cnts = findJUnit4FailureErrorCount(res);
+                        junitTest.setCounts(res.runCount(), cnts[0], cnts[1]);
+                    } else {
+                        junitTest.setCounts(res.runCount(), res.failureCount(),
+                                res.errorCount());
+                    }
                     junitTest.setRunTime(System.currentTimeMillis() - start);
                 }
             }
@@ -692,7 +729,7 @@
 
     private static boolean filterLine(String line) {
         for (int i = 0; i < DEFAULT_TRACE_FILTERS.length; i++) {
-            if (line.indexOf(DEFAULT_TRACE_FILTERS[i]) > 0) {
+            if (line.indexOf(DEFAULT_TRACE_FILTERS[i]) != -1) {
                 return true;
             }
         }
@@ -733,4 +770,83 @@
             }
         }
     }
+
+    /**
+     * Modifies a TestListener when running JUnit 4:
+     * treats AssertionFailedError as a failure not an error.
+     * @since Ant 1.7
+     */
+    private TestListener wrapListener(final TestListener testListener) {
+        return new TestListener() {
+            public void addError(Test test, Throwable t) {
+                if (junit4 && t instanceof AssertionFailedError) {
+                    // JUnit 4 does not distinguish between errors and failures even in the JUnit 3 adapter.
+                    // So we need to help it a bit to retain compatibility for JUnit 3 tests.
+                    testListener.addFailure(test, (AssertionFailedError) t);
+                } else if (junit4 && t.getClass().getName().equals("java.lang.AssertionError")) {
+                    // Not strictly necessary but probably desirable.
+                    // JUnit 4-specific test GUIs will show just "failures".
+                    // But Ant's output shows "failures" vs. "errors".
+                    // We would prefer to show "failure" for things that logically are.
+                    try {
+                        String msg = t.getMessage();
+                        AssertionFailedError failure = msg != null ?
+                            new AssertionFailedError(msg) : new AssertionFailedError();
+                        // To compile on pre-JDK 4 (even though this should always succeed):
+                        Method initCause = Throwable.class.getMethod("initCause", new Class[] {Throwable.class});
+                        initCause.invoke(failure, new Object[] {t});
+                        testListener.addFailure(test, failure);
+                    } catch (Exception e) {
+                        // Rats.
+                        e.printStackTrace(); // should not happen
+                        testListener.addError(test, t);
+                    }
+                } else {
+                    testListener.addError(test, t);
+                }
+            }
+            public void addFailure(Test test, AssertionFailedError t) {
+                testListener.addFailure(test, t);
+            }
+            public void addFailure(Test test, Throwable t) { // pre-3.4
+                if (t instanceof AssertionFailedError) {
+                    testListener.addFailure(test, (AssertionFailedError) t);
+                } else {
+                    testListener.addError(test, t);
+                }
+            }
+            public void endTest(Test test) {
+                testListener.endTest(test);
+            }
+            public void startTest(Test test) {
+                testListener.startTest(test);
+            }
+        };
+    }
+
+    /**
+     * Use instead of TestResult.get{Failure,Error}Count on JUnit 4,
+     * since the adapter claims that all failures are errors.
+     * @since Ant 1.7
+     */
+    private int[] findJUnit4FailureErrorCount(TestResult res) {
+        int failures = 0;
+        int errors = 0;
+        Enumeration e = res.failures();
+        while (e.hasMoreElements()) {
+            e.nextElement();
+            failures++;
+        }
+        e = res.errors();
+        while (e.hasMoreElements()) {
+            Throwable t = ((TestFailure) e.nextElement()).thrownException();
+            if (t instanceof AssertionFailedError || t.getClass().getName().equals("java.lang.AssertionError")) {
+                failures++;
+            } else {
+                errors++;
+            }
+        }
+        return new int[] {failures, errors};
+    }
+
 } // JUnitTestRunner

Modified: ant/core/trunk/src/main/org/apache/tools/ant/taskdefs/optional/junit/JUnitVersionHelper.java
URL: http://svn.apache.org/viewcvs/ant/core/trunk/src/main/org/apache/tools/ant/taskdefs/optional/junit/JUnitVersionHelper.java?rev=381780&r1=381779&r2=381780&view=diff
==============================================================================
--- ant/core/trunk/src/main/org/apache/tools/ant/taskdefs/optional/junit/JUnitVersionHelper.java (original)
+++ ant/core/trunk/src/main/org/apache/tools/ant/taskdefs/optional/junit/JUnitVersionHelper.java Tue Feb 28 13:07:15 2006
@@ -1,5 +1,5 @@
 /*
- * Copyright  2001-2002,2004-2005 The Apache Software Foundation
+ * Copyright  2001-2002,2004-2006 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.
@@ -51,8 +51,21 @@
      * <p>since Ant 1.5.1 this method will invoke &quot;<code>public
      * String getName()</code>&quot; on any implementation of Test if
      * it exists.</p>
+     *
+     * <p>Since Ant 1.7 also checks for JUnit4TestCaseFacade explicitly.
+     * This is used by junit.framework.JUnit4TestAdapter.</p>
      */
     public static String getTestCaseName(Test t) {
+        if (t != null && t.getClass().getName().equals("junit.framework.JUnit4TestCaseFacade")) {
+            // Self-describing as of JUnit 4 (#38811). But trim "(ClassName)".
+            String name = t.toString();
+            if (name.endsWith(")")) {
+                int paren = name.lastIndexOf('(');
+                return name.substring(0, paren);
+            } else {
+                return name;
+            }
+        }
         if (t instanceof TestCase && testCaseName != null) {
             try {
                 return (String) testCaseName.invoke(t, new Object[0]);



---------------------------------------------------------------------
To unsubscribe, e-mail: dev-unsubscribe@ant.apache.org
For additional commands, e-mail: dev-help@ant.apache.org


Re: Junut4

Posted by Stefan Bodewig <bo...@apache.org>.
On Wed, 01 Mar 2006, Steve Loughran <st...@apache.org> wrote:
> Martijn Kruithof wrote:

>> Furthermore I thought junit 4 would get rid of the distinction
>> between failure and error, wouldn't we want to remain in-line with
>> this new junit behaviour when running junit 4 testcases in an junit
>> 4 environment?
> 
> Just because junit4 wants that behaviour does not mean we need to
> follow.

Agreed.  To me there is a difference between a failed assertion and a
NullPointerException.

What our formatters should support in some way is a number of ignored
tests.

Stefan

---------------------------------------------------------------------
To unsubscribe, e-mail: dev-unsubscribe@ant.apache.org
For additional commands, e-mail: dev-help@ant.apache.org


Re: Junut4 (was Re: svn commit: r381780 - in /ant/core/trunk: WHATSNEW docs/manual/OptionalTasks/junit.html src/main/org/apache/tools/ant/taskdefs/optional/junit/JUnitTestRunner.java src/main/org/apache/tools/ant/taskdefs/optional/junit/JUnitVersionHelper.java)

Posted by Steve Loughran <st...@apache.org>.
Jesse Glick wrote:
> Steve Loughran wrote:
>> There was some discussion of junit4 implications in the ant-user mail 
>> list,
> 
> Ah, thanks for the pointer, missed that before. Some things I can 
> extract from that thread:
> 
> - ignored tests ought to be reported (currently they are just silently 
> skipped)

...this would impact the style sheets, of course; maybe we'd need a 
junit4 set.

> 
> - <junit> should support specifying categories of tests
> 
> Not really clear to me at this point whether the significant features of 
> JUnit 4 can be accommodated comfortably inside <junit> or whether a 
> separate task would be better. Making a separate task may however 
> discourage migration. With the current patch you can at least put 
> junit-4.0.jar on your classpath and migrate a couple of tests to it, 
> without touching other tests and without touching your build script.

Before your last patch, I was in favour of a new antlib. now I'm not so 
sure. After all, junit is as important as javac.

>> What does Ant's junit task [...] does badly
>>  -installation. <junit> is the first time most people encounter ant 
>> lib setup grief.
> 
> I guess this was fixed by my other <junit> patch a couple days ago?

yes indeed!

> 
>> exceptions don't serialize
> 
> Throwable implements Serializable, BTW.

yes, but some of the things that extend it dont deserialize at the far 
end unless you have a shared classloader, jini style. My 
throwable-for-the-log class has to extract the common info from the 
entire chain of exceptions before sending it down the wire:
http://cvs.sourceforge.net/viewcvs.py/smartfrog/core/components/junit/src/org/smartfrog/services/junit/ThrowableTraceInfo.java?view=markup

---------------------------------------------------------------------
To unsubscribe, e-mail: dev-unsubscribe@ant.apache.org
For additional commands, e-mail: dev-help@ant.apache.org


Re: Junut4

Posted by Steve Loughran <st...@apache.org>.
Kev Jackson wrote:
> 
>> +1 for a separate task, packaged in an Ant library.  This one could be
>> release before Ant 1.7.0 which would give people using JUnit4 more
>> support sooner.
>>
>> Personally I'd even prefer the JUnit team to provide that Ant library
>> so they have to keep up with their API changes themselves 8-)
>>  
>>
> That would certainly be optimal.  (+1 for seperate task)
> 
> With this addition to Ant 1.7 code base, we now have code that relies on 
> jdk1.5 to build correctly (or will it build on <1.4?). 

We already do, in the <isReachable> component, but I think it reflects.

I just got "inconvenienced" at work by compareTo suddenly becoming 
generic, there is a risk that code compiled on java1.5 that uses, say 
Long.compareTo() wont work on java1.4, where the argument is an Object 
not a Long. There was a fair bit of casting needed to keep 
Long.compareTo() to take an object without a complaint.

> If this is the 
> case, is there perhaps a case for moving some of the codebase forward 
> from pre 1.2?  I know that these changes are only in one of the tasks 
> (and an optional one at that), but I think it's time to look at 
> deprecating 1.1.8 support and at least move the core up to 1.2 standard 
> (with Collections etc).

There is no need to run on Java1.1, as long as we can cross compile; 
nothing to stop you using collections. Its just the effort of patching 
things and of increasing the difference between SVN_HEAD and the 
shipping branch that has made people reluctant.

-steve

---------------------------------------------------------------------
To unsubscribe, e-mail: dev-unsubscribe@ant.apache.org
For additional commands, e-mail: dev-help@ant.apache.org


Re: Junut4

Posted by Stefan Bodewig <bo...@apache.org>.
On Fri, 03 Mar 2006, Jesse Glick <je...@sun.com> wrote:
> Stefan Bodewig wrote:
>> putting even more modifications into the current task (adding a new
>> JUnitResultFormatter subclass for ignored tests, for example) will
>> make it even more convoluted than it currently is.
> 
> Of course. The question is how this additional complexity balances
> against the duplication of code and resulting maintenance problems
> if we have two tasks.

I here you, and I agree to a certain extent.

> I could try to draft a standalone <junit4> if there is general
> agreement that that is the way to go. I guess that would be in
> 
> https://svn.apache.org/repos/asf/ant/antlibs/junit4/trunk/
> 
> or something?

https://svn.apache.org/repos/asf/ant/sandbox/antlibs/junit4/trunk/

> The twist in this case is that we are dealing with an upgrade to a
> library for which we already provide support in the Ant distro; no
> clear precedent for that, beyond the customary support for tools in
> new JDK releases.

"no clear precedent" is very true.  There are tasks like javacc that
try to adapt to three different versions and there is jspc which only
supports Tomcat 4 since Tomcat 5 now provides a task of its own.  I
vaguely recall the ANTLR project wanted to ship an improved antlr task
as well.

Stefan

---------------------------------------------------------------------
To unsubscribe, e-mail: dev-unsubscribe@ant.apache.org
For additional commands, e-mail: dev-help@ant.apache.org


RE: Junut4

Posted by Stephen McConnell <mc...@dpml.net>.
 

> -----Original Message-----
> From: news [mailto:news@sea.gmane.org] On Behalf Of Jesse Glick
> Sent: Saturday, 4 March 2006 5:50 AM
> To: dev@ant.apache.org
> Subject: Re: Junut4
> 
> Stefan Bodewig wrote:
> > putting even more modifications into the current task (adding a new 
> > JUnitResultFormatter subclass for ignored tests, for example) will 
> > make it even more convoluted than it currently is.
> 
> Of course. The question is how this additional complexity 
> balances against the duplication of code and resulting 
> maintenance problems if we have two tasks. Although there are 
> clearly semantic differences between
> 3 and 4, there are also many similarities that can be 
> implemented in one place in one task vs. two places in two 
> tasks; forking isn't free.
> 
> Any other takes on this? I could try to draft a standalone 
> <junit4> if there is general agreement that that is the way 
> to go. 

Jesse:

For what it's worth I would be *very* much in favour of a move to separate
task.  In the process you may want to consider constraints that such an
external tasks could (hypothetically) declare within an antlib that would
ensure meaningful error messages from ant if the new task is referenced
without the prerequisites resources.

Cheers, Steve.

 


---------------------------------------------------------------------
To unsubscribe, e-mail: dev-unsubscribe@ant.apache.org
For additional commands, e-mail: dev-help@ant.apache.org


Re: Junut4

Posted by Jesse Glick <je...@sun.com>.
Stefan Bodewig wrote:
> putting even more modifications into the current task (adding a new
> JUnitResultFormatter subclass for ignored tests, for example) will
> make it even more convoluted than it currently is.

Of course. The question is how this additional complexity balances 
against the duplication of code and resulting maintenance problems if we 
have two tasks. Although there are clearly semantic differences between 
3 and 4, there are also many similarities that can be implemented in one 
place in one task vs. two places in two tasks; forking isn't free.

Any other takes on this? I could try to draft a standalone <junit4> if 
there is general agreement that that is the way to go. I guess that 
would be in

https://svn.apache.org/repos/asf/ant/antlibs/junit4/trunk/

or something?

>> I do think that whatever form the support takes, it should be in the
>> standard Ant distro.
> 
> The drawback here is that it is tied to Ant's release schedule.  It
> will take months for your latest cahnges to become available to a
> wider audience.  A separate Ant library would allow a much shorter
> release cycle.

True indeed, although you lose the benefit of ubiquity. Means people 
effectively have to ship the <junit4> antlib with their projects in 
order to ensure that it is available. I guess this is a more general 
trade-off. The twist in this case is that we are dealing with an upgrade 
to a library for which we already provide support in the Ant distro; no 
clear precedent for that, beyond the customary support for tools in new 
JDK releases.

>> 6. Sorting of tests (e.g. by last fail time) - not clear to me if
>> this is something an Ant task should address.
> 
> Is this something JUnit4 offers or something that users would like to
> see?

Looking more closely, I think it is just something offered by the new 
API, in Request.sortWith. (In 3 this is not available since new 
TestSuite(Class) just enumerates all test methods in declaration order.) 
The task does not need to make use of it to be compliant.

-J.

-- 
jesse.glick@sun.com  x22801  netbeans.org  ant.apache.org
         http://google.com/search?q=e%5E(pi*i)%2B1


---------------------------------------------------------------------
To unsubscribe, e-mail: dev-unsubscribe@ant.apache.org
For additional commands, e-mail: dev-help@ant.apache.org


Re: Junut4

Posted by Stefan Bodewig <bo...@apache.org>.
On Thu, 02 Mar 2006, Jesse Glick <je...@sun.com> wrote:
> Kev Jackson wrote:
>> That would certainly be optimal.  (+1 for seperate task)
> 
> If others agree, should the existing 4 support in <junit> be
> reverted?

I feel that the changes between JUnit3 and JUnit4 warrant a new task,
putting even more modifications into the current task (adding a new
JUnitResultFormatter subclass for ignored tests, for example) will
make it even more convoluted than it currently is.

> My main concern is that making it a separate task would require
> people to change their build scripts gratuitously.

True.

> I do think that whatever form the support takes, it should be in the
> standard Ant distro.

The drawback here is that it is tied to Ant's release schedule.  It
will take months for your latest cahnges to become available to a
wider audience.  A separate Ant library would allow a much shorter
release cycle.

> 2. Timeout failures; similar to #1, though this could probably be
> skipped (just treat as a general failure with appropriate
> message).

I'd expect this to be an error like any other error.

> 3. Test failed to throw expected exception; similar to #2.

A failure.

> 4. Display only a "failure" count and no "error" count (if this is
> in fact desirable - does not appear to be consensus)

8-)

> 6. Sorting of tests (e.g. by last fail time) - not clear to me if
> this is something an Ant task should address.

Is this something JUnit4 offers or something that users would like to
see?

> Don't we already presume at least 1.2 to compile (and run) for Ant
> 1.6+ generally?

We do.

Stefan

---------------------------------------------------------------------
To unsubscribe, e-mail: dev-unsubscribe@ant.apache.org
For additional commands, e-mail: dev-help@ant.apache.org


Re: Junut4

Posted by Jesse Glick <je...@sun.com>.
Kev Jackson wrote:
> That would certainly be optimal.  (+1 for seperate task)

If others agree, should the existing 4 support in <junit> be reverted? 
It can be considered a proof of concept in its current state. My main 
concern is that making it a separate task would require people to change 
their build scripts gratuitously. I do think that whatever form the 
support takes, it should be in the standard Ant distro.

I believe the changes which might require a change to the <junit> task 
signature, associated interfaces, or result XML format are:

1. Reporting of ignored tests, which would require an optional extension 
to, or alternative to, the JUnitResultFormatter interface for custom 
formatters, as well as impl of that extension / alternative in the 
shipped formatters. Assuming most people use the standard formatters, 
they don't need to touch their script. The XML format for test results 
(and its default stylesheet) might also need extensions.

2. Timeout failures; similar to #1, though this could probably be 
skipped (just treat as a general failure with appropriate message). 
Seems that 4's RunListener anyway doesn't report it specially?

3. Test failed to throw expected exception; similar to #2.

4. Display only a "failure" count and no "error" count (if this is in 
fact desirable - does not appear to be consensus); similar to #1.

5. I thought there was support for named "categories" of tests in 4, but 
I can't now find it - maybe it was dropped for 4.0, or maybe I was 
thinking of TestNG?

6. Sorting of tests (e.g. by last fail time) - not clear to me if this 
is something an Ant task should address.

7. Use of Filter, e.g. to run one test method only. But this is 
desirable for JUnit 3 anyway (see Bugzilla).

Other changes which probably don't imply any signature change:

1. Handling of StoppedByUserException (not sure when this is thrown).

> With this addition to Ant 1.7 code base, we now have code that relies on 
> jdk1.5 to build correctly (or will it build on <1.4?).

It shouldn't require anything above 1.2 to build; everything in 
junit-4.0.jar (not much) is accessed via reflection. JDK 1.5 is only 
required to run if you actually have junit-4.0.jar in your test's CP 
(and not junit-3.8.1.jar first); or you want to run 4-based tests.

> If this is the 
> case, is there perhaps a case for moving some of the codebase forward 
> from pre 1.2?  I know that these changes are only in one of the tasks 
> (and an optional one at that), but I think it's time to look at 
> deprecating 1.1.8 support and at least move the core up to 1.2 standard 
> (with Collections etc).

Don't we already presume at least 1.2 to compile (and run) for Ant 1.6+ 
generally? There's no reason not to use Collections in Ant today, except 
for places where we have a historical API mentioning Vector or Hashtable 
that can't be changed compatibly.

-J.

-- 
jesse.glick@sun.com  x22801  netbeans.org  ant.apache.org
         http://google.com/search?q=e%5E(pi*i)%2B1


---------------------------------------------------------------------
To unsubscribe, e-mail: dev-unsubscribe@ant.apache.org
For additional commands, e-mail: dev-help@ant.apache.org


Re: Junut4

Posted by Kev Jackson <ke...@it.fts-vn.com>.
>+1 for a separate task, packaged in an Ant library.  This one could be
>release before Ant 1.7.0 which would give people using JUnit4 more
>support sooner.
>
>Personally I'd even prefer the JUnit team to provide that Ant library
>so they have to keep up with their API changes themselves 8-)
>  
>
That would certainly be optimal.  (+1 for seperate task)

With this addition to Ant 1.7 code base, we now have code that relies on 
jdk1.5 to build correctly (or will it build on <1.4?).  If this is the 
case, is there perhaps a case for moving some of the codebase forward 
from pre 1.2?  I know that these changes are only in one of the tasks 
(and an optional one at that), but I think it's time to look at 
deprecating 1.1.8 support and at least move the core up to 1.2 standard 
(with Collections etc).

Thoughts?

Also - it'd be good to have <junit> as the old task and <junut> as the 
new task ;) [see subject...]

Kev

---------------------------------------------------------------------
To unsubscribe, e-mail: dev-unsubscribe@ant.apache.org
For additional commands, e-mail: dev-help@ant.apache.org


Re: Junut4

Posted by Stefan Bodewig <bo...@apache.org>.
On Wed, 01 Mar 2006, Jesse Glick <je...@sun.com> wrote:

> Not really clear to me at this point whether the significant
> features of JUnit 4 can be accommodated comfortably inside <junit>
> or whether a separate task would be better.

+1 for a separate task, packaged in an Ant library.  This one could be
release before Ant 1.7.0 which would give people using JUnit4 more
support sooner.

Personally I'd even prefer the JUnit team to provide that Ant library
so they have to keep up with their API changes themselves 8-)

Stefan

---------------------------------------------------------------------
To unsubscribe, e-mail: dev-unsubscribe@ant.apache.org
For additional commands, e-mail: dev-help@ant.apache.org


Re: Junut4 (was Re: svn commit: r381780 - in /ant/core/trunk: WHATSNEW docs/manual/OptionalTasks/junit.html src/main/org/apache/tools/ant/taskdefs/optional/junit/JUnitTestRunner.java src/main/org/apache/tools/ant/taskdefs/optional/junit/JUnitVersionHelper.java)

Posted by Jesse Glick <je...@sun.com>.
Steve Loughran wrote:
> There was some discussion of junit4 implications in the ant-user mail 
> list,

Ah, thanks for the pointer, missed that before. Some things I can 
extract from that thread:

- ignored tests ought to be reported (currently they are just silently 
skipped)

- <junit> should support specifying categories of tests

Not really clear to me at this point whether the significant features of 
JUnit 4 can be accommodated comfortably inside <junit> or whether a 
separate task would be better. Making a separate task may however 
discourage migration. With the current patch you can at least put 
junit-4.0.jar on your classpath and migrate a couple of tests to it, 
without touching other tests and without touching your build script.

> What does Ant's junit task [...] does badly
>  -installation. <junit> is the first time most people encounter ant lib 
> setup grief.

I guess this was fixed by my other <junit> patch a couple days ago?

> exceptions don't serialize

Throwable implements Serializable, BTW.

-J.

-- 
jesse.glick@sun.com  x22801  netbeans.org  ant.apache.org
         http://google.com/search?q=e%5E(pi*i)%2B1


---------------------------------------------------------------------
To unsubscribe, e-mail: dev-unsubscribe@ant.apache.org
For additional commands, e-mail: dev-help@ant.apache.org


Junut4 (was Re: svn commit: r381780 - in /ant/core/trunk: WHATSNEW docs/manual/OptionalTasks/junit.html src/main/org/apache/tools/ant/taskdefs/optional/junit/JUnitTestRunner.java src/main/org/apache/tools/ant/taskdefs/optional/junit/JUnitVersionHelper.java)

Posted by Steve Loughran <st...@apache.org>.
Martijn Kruithof wrote:
> Isn't this a bit premature, junit 4 isn't even "out" yet. 

shipped last week. Gump is still recovering.

>Furthermore I 
> thought junit 4 would get rid of the distinction between failure and 
> error, wouldn't we want to remain in-line with this new junit behaviour 
> when running junit 4 testcases in an junit 4 environment?

Just because junit4 wants that behaviour does not mean we need to follow.

On this topic, Jon Skeet is setting up the logistics for a conference 
call between the junit people and the ant team, primarily on the future 
of <junit>

Being a conference call, it would probably overload if everyone joined 
in, but at the same time, I dont want to keep it a secret from 
interested parties. We'll be discussing where we are with junit, what's 
wrong with it and where do we go for junit4 --which may mean the junit 
team will take over ownership of a junit4 task.

There was some discussion of junit4 implications in the ant-user mail 
list, but since then Jesse has just fixed two main failings of <junit> 
-classpath setup and (I believe) direct support for junit4.

We need to look at where we stand with this, whether it is enough, and 
what else should be done. Here is my opinion

What does Ant's junit task does well:

-integrates testing with the build
-runs well in a new JVM
-segues into reporting with junitreport (a bit fiddly; could be integrated)
-provides some minimal output as you go along, one that lets you infer 
state from the logs
-distinguish (possibly needlessly) errors and failures

What it does badly
  -installation. <junit> is the first time most people encounter ant lib 
setup grief.
  -forked JVM classpath setup. you need junit.jar, xerces on the CP.

What it doesnt do
  -drop abstract classes from the fileset (would be very nice)
  -only try and run classes that extend TestCase or are annotated as 
test methods (would be nice, no?)

what third party stuff adds
  -choreograph deploy+liveness+test+undeploy (cactus does that)
  -distribute. What if I want to test on a different machine? (I think 
JBoss' JRunner does this, and my distributed JUnit component for 
smartfrog is aimed at this problem)

I dont think the Ant task should try and do the third party things, but 
it must enable things like cactus. Furthermore, the stuff in "does 
badly" and "doesnt do" should be addressed, while retaining the things 
that work today.

There are some other wish-list items I'd like for junit, that I haven't 
covered. a medium priority spare time activity for me at work is 
distributed junit: deploying tests on hosts 1-10, collecting results on 
host 11, trying to present them in a way that makes sense. The GridUnit 
project does some of this; they share my code for serializable test 
results. I'd really like junit's results to be serializable out the box, 
and junit4 results to be compatible, but I can work around this, after 
all, exceptions don't serialize and I have to strip-mine meaningful data 
from them.


So: open discussion. What would people want from a <junit4> task?

---------------------------------------------------------------------
To unsubscribe, e-mail: dev-unsubscribe@ant.apache.org
For additional commands, e-mail: dev-help@ant.apache.org


Re: svn commit: r381780 - in /ant/core/trunk: WHATSNEW docs/manual/OptionalTasks/junit.html src/main/org/apache/tools/ant/taskdefs/optional/junit/JUnitTestRunner.java src/main/org/apache/tools/ant/taskdefs/optional/junit/JUnitVersionHelper.java

Posted by Jesse Glick <je...@sun.com>.
Martijn Kruithof wrote:
> Isn't this a bit premature, junit 4 isn't even "out" yet.

Seems junit.org has not announced it, but it's there for download and 
semi-announced at http://sourceforge.net/projects/junit.

> Furthermore I thought junit 4 would get rid of the distinction
> between failure and error, wouldn't we want to remain in-line with
> this new junit behaviour when running junit 4 testcases in an junit 4
> environment?

Possibly. Here's the problem I faced. If you delete the parts of the 
patch that deal with failure vs. error, all test failures are reported 
to Ant as errors. So you see e.g.

Tests run: 3, Failures: 0, Errors: 2, Time elapsed: 0.037 sec

just because two assertEquals(...) failed. This is pretty confusing 
because the test was not misconfigured and the above summary implies it 
was. Note that this happens even for JUnit 3 tests run using the 
adapter, which is definitely wrong.

The way the task is currently structured it is impossible to make all 
errors be failures while retaining JUnit 3 compatibility, since errors 
take Throwable and failures only AssertionFailedError.

So I decided to massage it a bit: when running against junit-4.0.jar, 
junit.framework.AssertionFailedError (from 3) and 
java.lang.AssertionError (used as of 4) are both treated as "failures" 
for purposes of reporting. All other throwables are treated as "errors".

Of course it would be most in the spirit of 4 to have failures vs. 
errors be reported as always for 3 tests, but report only failures for 4 
tests. Would require the task to _not_ use the adapter for a test it can 
determine conclusively to be a 3 test (not sure exactly how this is done).

But would not work anyway because JUnitResultFormatter extends 
junit.framework.TestListener which does not permit an arbitrary 
Throwable to be reported as a failure. Even if we changed the JURF 
interface and rewrote the shipped result formatters (plain, brief, XML, 
summary) to use a different mechanism we would have broken custom result 
formatters, which are supported by the task (and presumably are also 
expecting to display both failure and error counts).

So I don't yet see a reasonable way to have results from 4 tests (and 
only 4 tests) reported with only a failure count, while continuing to 
report failures and errors for 3 tests, and retaining compatibility with 
custom formatters. Anyone with an idea, please feel free to fix.

-J.

-- 
jesse.glick@sun.com  x22801  netbeans.org  ant.apache.org
         http://google.com/search?q=e%5E(pi*i)%2B1


---------------------------------------------------------------------
To unsubscribe, e-mail: dev-unsubscribe@ant.apache.org
For additional commands, e-mail: dev-help@ant.apache.org


Re: svn commit: r381780 - in /ant/core/trunk: WHATSNEW docs/manual/OptionalTasks/junit.html src/main/org/apache/tools/ant/taskdefs/optional/junit/JUnitTestRunner.java src/main/org/apache/tools/ant/taskdefs/optional/junit/JUnitVersionHelper.java

Posted by Martijn Kruithof <jk...@apache.org>.
Isn't this a bit premature, junit 4 isn't even "out" yet. Furthermore I 
thought junit 4 would get rid of the distinction between failure and 
error, wouldn't we want to remain in-line with this new junit behaviour 
when running junit 4 testcases in an junit 4 environment?

Martijn

---------------------------------------------------------------------
To unsubscribe, e-mail: dev-unsubscribe@ant.apache.org
For additional commands, e-mail: dev-help@ant.apache.org


Re: svn commit: r381780 - in /ant/core/trunk: WHATSNEW docs/manual/OptionalTasks/junit.html src/main/org/apache/tools/ant/taskdefs/optional/junit/JUnitTestRunner.java src/main/org/apache/tools/ant/taskdefs/optional/junit/JUnitVersionHelper.java

Posted by Jesse Glick <je...@sun.com>.
Stefan Bodewig wrote:
>> I will however patch JUnitTestRunner a tiny bit to be able to run 
>> JUnit 3 tests on JDK 1.4 if your classpath contains JUnit 3
>> _before_ JUnit 4.
> 
> This probably works that way right now, I'd expect Class.forName for 
> JUnit4TestAdapter to throw and exception because of the class file 
> version on JDK 1.4 and then JUnitTestRunner falls back to the old 
> behaviour.

That's not how it worked (cf. my "tweak" patch): just starting the task 
would fail right away since the JUnitTaskMirrorImpl statically refers to 
TestCase, which in junit-4.0.jar is built with -source 1.5.

-J.

-- 
jesse.glick@sun.com  x22801  netbeans.org  ant.apache.org
         http://google.com/search?q=e%5E(pi*i)%2B1


---------------------------------------------------------------------
To unsubscribe, e-mail: dev-unsubscribe@ant.apache.org
For additional commands, e-mail: dev-help@ant.apache.org


Re: svn commit: r381780 - in /ant/core/trunk: WHATSNEW docs/manual/OptionalTasks/junit.html src/main/org/apache/tools/ant/taskdefs/optional/junit/JUnitTestRunner.java src/main/org/apache/tools/ant/taskdefs/optional/junit/JUnitVersionHelper.java

Posted by Stefan Bodewig <bo...@apache.org>.
On Wed, 01 Mar 2006, Jesse Glick <je...@sun.com> wrote:
> Stefan Bodewig wrote:

>> Will this patch still allow me to run those tests?  Or will
>> wrapping the tests in a JUnit4TestAdapter force me to use
>> annotations?
> 
> No, you can still use the 3-compatible tests as before.

Great.

> You do need to be running JDK 5+

Yes, I know that.

> I will however patch JUnitTestRunner a tiny bit to be able to run
> JUnit 3 tests on JDK 1.4 if your classpath contains JUnit 3 _before_
> JUnit 4.

This probably works that way right now, I'd expect Class.forName for
JUnit4TestAdapter to throw and exception because of the class file
version on JDK 1.4 and then JUnitTestRunner falls back to the old
behaviour.

Stefan

---------------------------------------------------------------------
To unsubscribe, e-mail: dev-unsubscribe@ant.apache.org
For additional commands, e-mail: dev-help@ant.apache.org


Re: svn commit: r381780 - in /ant/core/trunk: WHATSNEW docs/manual/OptionalTasks/junit.html src/main/org/apache/tools/ant/taskdefs/optional/junit/JUnitTestRunner.java src/main/org/apache/tools/ant/taskdefs/optional/junit/JUnitVersionHelper.java

Posted by Jesse Glick <je...@sun.com>.
Stefan Bodewig wrote:
> I haven't looked into the implemenation of JUnit4TestAdapter so I
> have to ask you 8-)

Sure, was expecting some questions here...

> Even if I have JUnit 4 on my CLASSPATH I can still use JUnit 3 style
> of tests (no annotations, naming conventions instead).

Yes.

> Will this patch still allow me to run those tests?  Or will wrapping the tests
> in a JUnit4TestAdapter force me to use annotations?

No, you can still use the 3-compatible tests as before.

You do need to be running JDK 5+ since the JUnit team decided to compile 
even the compatibility classes with -source 1.5 and against JDK 5 
classes like StringBuilder, which Ant can't work around. I will however 
patch JUnitTestRunner a tiny bit to be able to run JUnit 3 tests on JDK 
1.4 if your classpath contains JUnit 3 _before_ JUnit 4. Not very much 
help but could make transition a bit easier for some folks: just include 
both versions of JUnit on your classpath in order, and you will be able 
to run JUnit 3 tests always, and 4 tests under JDK 5+.

-J.

-- 
jesse.glick@sun.com  x22801  netbeans.org  ant.apache.org
         http://google.com/search?q=e%5E(pi*i)%2B1


---------------------------------------------------------------------
To unsubscribe, e-mail: dev-unsubscribe@ant.apache.org
For additional commands, e-mail: dev-help@ant.apache.org


Re: svn commit: r381780 - in /ant/core/trunk: WHATSNEW docs/manual/OptionalTasks/junit.html src/main/org/apache/tools/ant/taskdefs/optional/junit/JUnitTestRunner.java src/main/org/apache/tools/ant/taskdefs/optional/junit/JUnitVersionHelper.java

Posted by Stefan Bodewig <bo...@apache.org>.
On Tue, 28 Feb 2006, <jg...@apache.org> wrote:

> +                Class junit4TestAdapterClass = null;
> +                // Note that checking for JDK 5 directly won't work; under JDK 4, this will already have failed.
> +                try {
> +                    if (loader == null) {
> +                        junit4TestAdapterClass = Class.forName("junit.framework.JUnit4TestAdapter");
> +                    } else {
> +                        junit4TestAdapterClass = Class.forName("junit.framework.JUnit4TestAdapter", true, loader);
> +                    }
> +                } catch (ClassNotFoundException e) {
> +                    // OK, fall back to JUnit 3.
> +                }
> +                junit4 = junit4TestAdapterClass != null;
> +

I haven't looked into the implemenation of JUnit4TestAdapter so I
have to ask you 8-)

Even if I have JUnit 4 on my CLASSPATH I can still use JUnit 3 style
of tests (no annotations, naming conventions instead).  Will this
patch still allow me to run those tests?  Or will wrapping the tests
in a JUnit4TestAdapter force me to use annotations?

If JUnit would build in Gump (somebody seems to have forgotten to
check in a file) we'd already know since Gump will provide JUnit 4
to allmost all builds while most of them (including Ant) still use
JUnit 3 style tests.

Stefan

---------------------------------------------------------------------
To unsubscribe, e-mail: dev-unsubscribe@ant.apache.org
For additional commands, e-mail: dev-help@ant.apache.org