Can I make JUnit more verbose?

2019-09-09 09:41发布

问题:

I'd like to have it yell hooray whenever an assert statement succeeds, or at the very least have it display the number of successful assert statements that were encountered.

I'm using JUnit4.

Any suggestions?

回答1:

If you want to see some output for each successful assertion, another simple approach which requires no external dependencies or source code, would be to define your own Assert class which delegates all methods to the standard JUnit Assert class, as well as logging successful assertions (failed assertions will be reported as usual by the JUnit class).

You then run a global search-and-replace on your test classes from "org.junit.Assert" => "com.myco.test.Assert", which should fix-up all regular and static import statements.

You could also then easily migrate your approach to the quieter-is-better-camp and change the wrapper class to just report the total # of passed assertions per test or per class, etc.



回答2:

Adding some info that would have been helpful to me when I wanted JUnit to be more verbose and stumbled on this question. Maybe it will help other testers in the future.

If you are running JUnit from Ant, and want to see what tests are being run, you can add the following to your task:

<junit showoutput="true" printsummary="on" enabletestlistenerevents="true" fork="@{fork}" forkmode="once" haltonfailure="no" timeout="1800000">

Note that showoutput, printsummary, and enabletestlistenerevents are what helped, not the other task attributes. If you set these, you'll get output like:

Running com.foo.bar.MyTest
junit.framework.TestListener: tests to run: 2
junit.framework.TestListener: startTest(myTestOne)
junit.framework.TestListener: endTest(myTestOne)
junit.framework.TestListener: startTest(myTestTwo)
junit.framework.TestListener: endTest(myTestTwo)
Tests run: 2, Failures: 0, Errors: 0, Time elapsed: 0.495 sec

This was useful to me when my tests were timing out and I wasn't sure which tests were actually taking too long, and which tests got cancelled because they were unlucky enough to be running when the time was up.



回答3:

You can use AOP (with Spring or AspectJ) define pointcuts on all assert methods in junit.framework.Assert class. Using spring you can implement your own class as after returning advice (http://static.springframework.org/spring/docs/2.5.x/reference/aop.html#aop-advice-after-returning) which will only be called if the assert method passed (otherwise it throws an exception: junit.framework.AssertionFailedError ). In you own class you can implement a simple counter and print it at the end.



回答4:

Are you really interested in an assertion that succeeds? Normally, the only interesting assertions are ones that fail.

Being a fervent JUnit devotee myself, I try and make the output of the tests as quiet as possible because it improves the signal-to-noise ratio when something doesn't pass. The best test run is one where everything passes and there's not a peep from stdout.

You could always work on your unit test until it succeeds and run "grep Assert test.java | wc -l". :-)



回答5:

Hard to be done. All assert methods are static members of the class Assert, which implies that the RunNotifier (which counts the successful and failed tests) is not within reach.

If you dont refrain from an ungly hack: take the sources from JUnit, patch them to store the current notifier in a static field of Assert when running tests such that the static methods can report successful asserts to this notifier.



回答6:

I'm pretty sure you can create a custom TestRunner that does that. We ended up with something similar in our homemade Unit-testing framework (a clone of NUnit).

Oh, wait - now that I'm reading your question again, if you really want output for each successful assertion, you'll have to dig into the plumbing more. The TestRunner only gets called once for each testcase start/end, so it'll count passed and failed tests, not assertions.

This isn't much of a problem for me, since I tend towards one assertion per test, generally.



回答7:

I don't think, it's the goal of JUnit to count matched assertions or print out more verbose information. If tests are atomic, you'll get most information in there. So I would review my tests.

You're also able to establish a LogFile in JUnit. It's possible, but it will decrease test execution performance...



回答8:

junit's javadoc unfortunately says that only failed assertions are recorded (http://junit.sourceforge.net/javadoc_40/index.html)

so it seems it would not be possible



回答9:

Can you consider ?

1) download junit source
2) to modify the class org.junit.Assert to do whatever modifications you're looking for



标签: java junit