I am getting null while calling the getCause
function of Throwable
.
package com.salman.demo;
public class MyClass {
public static void main(String[] args) {
// TODO Auto-generated method stub
try {
NormalClass.testIt();
} catch (Throwable th) {
System.out.println(th.getCause());
}
}
}
package com.salman.demo;
import com.salman.exceptions.ValidationException;
public class NormalClass {
public static void testIt() throws ValidationException {
System.out.println("Inside testIt funtion.");
throw new ValidationException("Validation Exception..");
}
}
On running MyClass
, it prints following output
Inside testIt funtion.
null
however on debugging this, I can see value of cause private variable is set to ValidationException
which is expected but while calling getter of that private field returns null.
The ValidationException
you've thrown will be th
in your calling code... there's no cause for that ValidationException
. The point of getCause()
is for one exception to be able to refer to another one as an underlying cause - but there's only one exception in your case.
The fact that you see the private cause
variable's value being the ValidationException
is entirely in line with how that field is documented (emphasis mine):
The throwable that caused this throwable to get thrown, or null if throwable was not caused by another throwable, or if the causative throwable is unknown. If this field is equal to this throwable itself, it indicates that the cause of this throwable has not yet been initialized.
And that's why getCause()
is implemented as:
return (cause==this ? null : cause);
If you want to see the intended chaining in effect, you could create two exceptions, one chained to the other:
throw new ValidationException("Validation Exception..",
new IllegalArgumentException("Bang!"));
Now calling getCause()
on the ValidationException
will return the IllegalArgumentException
.
You probably just want to change your calling code to log th
instead of th.getCause()
though.
See more on this question at Stackoverflow