I have a class as following:
public class XConstants {
public static final int A_TYPE = 1;
public static final int B_TYPE = 2;
}
I am using both variables in my tests but when I examine the test coverage with Jacoco it shows %0 test coverage for this class. My guess is, it's because I never instantiate this class, just use its static variables. I tried creating an instance and test coverage went %100. How can I overcome this problem?
For the code coverage to increase , one would need to run the tests with the coverage enabled and then view the report generated locally to see the areas covered by jacoco during its coverage parse, then from these one would see the methods (per class) that needs to be covered from the view of the jacoco agent.
Why does the coverage report not show highlighted source code? Make sure the following prerequisites are fulfilled to get source code highlighting in JaCoCo coverage reports: Class files must be compiled with debug information to contain line numbers. Source files must be properly supplied at report generation time.
JaCoCo also calculates branch coverage for all if and switch statements. This metric counts the total number of such branches in a method and determines the number of executed or missed branches. Branch coverage is always available, even in absence of debug information in the class files.
The JaCoCo measures test coverage based on percentage of bytecode which was actually executed. Declaring static final primitive or String constant creates no bytecode to execute, it's just an entry inside the constant pool. The only bytecode you have here is an implicit default constructor, usually like this:
aload_0
invokespecial Object.<init>
return
So when you don't call it, you have 0%, when you call it, you have 100%.
My suggestion is to ignore this problem. You shouldn't try to achieve 100% coverage no matter what. After all it doesn't guarantee anything: even 100% covered code may contain serious bugs.
In our project we overcome problem of no coverage for class containing only constants by creating private constructor (following pattern from java.lang.Math
):
private XConstants {}
and then using Trajano commons-testing
library to assert that this constructor is private and invoke it to satisfy coverage:
assertUtilityClassWellDefined(XConstants.class)
You've made a class, which can be instantiated, but you never instantiated it, so technically you didn't cover that code. The simple solution for a "class full of constants" is to make it an interface instead. Also note that variables in an interface are public, static, and final by default, so your code can simply look like this:
public interface XConstants {
int A_TYPE = 1;
int B_TYPE = 2;
}
[Updated] jacoco 0.8.0 has this by default configurated, for it to work you will need to add a private constructor.
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