I am working with some legacy code that has some System.out.print
commands in itself.
My eCobertura plugin shows this lines red, so I want to unit test them.
Here in stackoverflow I found a way to unit test console outputs which i thing is very interesting.
This is how I do it:
private final ByteArrayOutputStream outContent = new ByteArrayOutputStream();
@Before
public void setUpStreams() {
System.setOut(new PrintStream(outContent));
}
@After
public void cleanUpStreams() {
System.setOut(null);
}
@Test
public void out() {
System.out.print("Some message from the system");
assertEquals("Some message from the system", outContent.toString());
}
So far so good, the test goes green but when I run the code coverage plugin again, I get this message:
Exception in thread "Thread-0" java.lang.NullPointerException at net.sourceforge.cobertura.coveragedata.TouchCollector.applyTouchesOnProjectData(TouchCollector.java:186) at net.sourceforge.cobertura.coveragedata.ProjectData.saveGlobalProjectData(ProjectData.java:267) at net.sourceforge.cobertura.coveragedata.SaveTimer.run(SaveTimer.java:31) at java.lang.Thread.run(Thread.java:662)
I have some doubts:
System.out.print()'s
?You should Unit Test your API endpoints, it's easy! It's going to involve a bit of refactoring of the base project to make the code unit test friendly, however it should be intuitive to follow along.
Aim for 95% or higher coverage with unit tests for new application code. When developers unit test as they program, they improve the longevity and quality of the codebase. The time a development team invests in unit tests pays off with less time spent troubleshooting defects and analyzing problems later.
Is it correct to try to unit test System.out.print()'s?
This highly depends on what you are trying to test. I don't think it is necessary to test System.out.print() itself, I hope Sun/Oracle has done this enough. But if your application outputs important information to the console and this is your only way to validate the output, than yes, you need to test it. If you can test your code by testing the corresponding classes, then you probably don't need to test the output stream itself.
Look at databases, for example: I don't test the JDBC driver it self, but I do test all code/functionality that is part of loading/saveing data from and to the database.
The red line only means the code line was never executed. This can be okay or it could mean that your tests don't touch a part of your code that they should. Getting test coverage high is important, but aiming for 100% might not always be necessary (think Pareto principle)
As for your Null Pointer Exception
Your call to System.setOut(null);
set the System.out to null and eCobertura probably tries to write something to Standard Out, which is null now. You might need to save the orignial Out Stream in your @Before Method and restore it in our @After method to allow the code that follows to use StdOut
Is eCobertura incompatible with this type of test?
If eCobertura is not compatible with this type of test, why does it show the line red?
why is eCobertura giving me this error?
It could be that the communication between eclipse and eCobertura happens via Standard Out, but I am not sure. If this is the case, than if you redirect Standard Out not only your output but also the output from Cobertura gets redirected and the GUI does not see anymore what gets executed and what not, thus coloring it red
Is there something wrong in my test?
It might be necessary to ensure StdOut is correctly restored.
I am using jUnit 4.11 do you think this has something to do with it?
No, I don't think so
If it's correct to use System.out.println's in your code, then it's correct to (unit/integration) test them.
There is a useful System test utility called System Rules for testing this kind of code.
http://stefanbirkner.github.com/system-rules/
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With