Mockito catch exception in void method - java

I have this method:
public void deleteTableEsiti() throws Exception {
try{
EsitiDAO esitiDAO = new EsitiDAO();
int deletedEsiti = esitiDAO.deleteTableEsiti(em);
}
catch(Exception e ){
log.error(e);
}
finally{
em.close();
}
}
I'm trying to make the test that cover the catch exception. I have tried many times but I can't cover that lines with Mockito.
This is the test that i have write:
#Test(expected=Exception.class)
public void mockException(){
ServiceG service = Mockito.mock(ServiceG.class);
try {
Mockito.doThrow(Exception.class).when(service).deleteTableEsiti();
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
};
//Mockito.when(service.deleteTableEsiti()).thenThrow(new Exception());
}
I have always this error:
[ERROR] Failures:
[ERROR] JUnit.mockException Expected exception: java.lang.Exception
and lines are not covered by test.

Firstly, your method deleteTableEsiti() never throws any exception. It catches it and logs it, but always returns normally. If you want your method to throw an exception, don't catch it, or catch it and throw a custom exception that wraps the original exception.
Your unit test does not actually call the mocked method deleteTableEsiti() anyway, since all it does is set up a mock rule to throw an exception when the method is called (which you never call).
So, after calling Mockito.when, you should call (or do something that calls) that method in your unit test.

Related

java junit exception hadling for code coverage

I am new to java, Junit and jacoco. I am doing exception handling as below. I am catching Exception class as well in case the method throws any other exception that were missed to catch earlier.
private void myMethod1() throws MyCustomException {
....
try {
..... straight JDBC calls for select, insert, update operations ....
} catch (SQLException sqEx) {
logger.error(....);
new MyCustomException(.....);
} catch (RuntimeException rEx) {
logger.error(....);
new MyCustomException(.....);
} catch (Exception ex) {
logger.error(....);
new MyCustomException(.....);
}
}
in Junit test, tried below. When I have runtime any exception I throw is always going to RuntimeException catch block itself unless I throw Exception. which other checked exception can I try so it goes into Exception catch block. Due to this I am unable to get the code coverage needed.
private void testMyMethod1() {
....
try {
.....
when(...).thenThrow(new SocketException());
spy.myMethod1();
} catch (SQLException sqEx) {
assertTrue(false);
} catch (RuntimeException rEx) {
assertTrue(false)
} catch (Exception ex) {
assertTrue(true);
}
}
your help is appreciated.
In thenThrow you have throwed socket exception,but you are trying to catch some other exception like SQLException. If the exception thrown is not a child of SQLException then it won't come into that block.
Also please make sure you are creating proper exception inside when()..thenThrow() statement by debugging.Sometimes creating inappropriate exception will cause problems.
A few things... if your myMethod1() is not in the same java class, you can't test a private method in a separate unit test class. Its best to make your myMethod1() package protected. In your test class, its also best not to have any try catch or if statements inside it. You must make separate test methods per test case, not all in one. You can take advantage of #Rule or #expected annotations. I recommend doing something like this...
#Test(expected = MyCustomException.class)
public void testMyMethod1_handlesSQLException(){
doThrow(SQLException.class).when(...);
Foo foo = new Foo();
foo.myMethod1();
}
#Test(expected = MyCustomException.class)
public void testMyMethod1_handlesRuntimeException(){
doThrow(RuntimeException.class).when(...);
Foo foo = new Foo();
foo.myMethod1();
}
#Test(expected = MyCustomException.class)
public void testMyMethod1_handlesException(){
doThrow(Exception.class).when(...);
Foo foo = new Foo();
foo.myMethod1();
}
In JUnit 5, a possible way would be:
#ParameterizedTest
#ValueSource(classes = {
SQLException.class,
RunTimeException.class,
Exception.class
})
void methodWrapsException(Exception toBeWrapped) {
Foo foo = new Foo(...);
doThrow(toBeWrapped).when(...);
assertThrows(MyCustomException.class, () -> foo.myMethod1());
}
This makes use of JUnit 5 support for parameterized classes and its lambda-based assertions for exceptions.

Test a method which throws an exception using Junit

I am trying to write a test case for a method which throws an exception based on certain logic. However the test case fails as the expected exception and obtained exceptions are different.
Method to test -
public void methodA (//parameters) throws ExceptionA
{
certainlogic=//call some method
if (certainlogic)
throw new ExceptionA(//exception details)
else
//code snippet
}
Test method -
#Test (expected=ExceptionA.class)
public void testMethodA
{
try
{
when (//mock method).thenReturn(true);
//call methodA
}
catch (ExceptionA e)
{
fail(e.printStackTrace(e));
}
}
I am receiving the below error -
Unexpected exception, expected<cExceptionA> but was<java.lang.AssertionError>
How do I solve this issue?
You have to remove the catch in your test
#Test (expected=ExceptionA.class)
public void testMethod()
{
when (//mock method).thenReturn(true);
//call methodA
}
Otherwise you catch the ExceptionA and by calling fail you throw an AssertionError. Obviously the AssertionError is not an ExceptionA and therefore your test fails.
You should remove the try-catch block entirely or at least the catch.
The "expected = ExceptionA.class" tells junit to monitor for thrown exceptions, catch them and compare their class against the given class.
If you catch the thrown exception, the #Test-annotated junit method cannot detect if such an exception is thrown.
By calling fail(...) you implicitly throw an AssertionError which junit detects and thus your test fails because AssertionError.class != ExceptionA.class

Why is catch block optional?

I have the following code
public static void nocatch()
{
try
{
throw new Exception();
}
finally
{
}
}
Which gives the error
Exception in thread "main" java.lang.Error: Unresolved compilation problem:
Unhandled exception type CustomException
My Question is why was it designed that the catch block is optional, when there is no way of getting around not having a catch?
From finally()'s perspective, I understand that
finally should have atleast a try block, catch is optional. The point of finally blocks is to make sure stuff gets cleaned up whether an exception is thrown or not. As per the JLS
A finally clause ensures that the finally block is executed after the try block and any catch block that might be executed, no matter how control leaves the try block or catch block.
Edit:
By adding a return in the finally block, compiler does not give the error WHY?!
public static void nocatch()
{
try
{
throw new Exception();
}
finally
{
return; //By adding this statement, the compiler error goes away! Please let me know why
}
}
My Question is why was it designed that the catch block is optional, when there is no way of getting around not having a catch?
Yes there is: Declare that the method throws the exception:
public static void nocatch() throws CustomException
{
try
{
throw new CustomException();
}
finally
{
}
}
try/finally without catch is to ensure that you clean up anything you need to clean up, even if you aren't handling the exception yourself. (Be sure not to allow any other exception to be thrown from within finally, or you'll hide the primary exception.)
Here's an example to play with (live copy):
private static class CustomException extends Exception {
}
public static void main (String[] args) throws java.lang.Exception
{
try
{
System.out.println("Calling nocatch(false)");
nocatch(false);
}
catch (CustomException ce) {
System.out.println("Caught CustomException for false case");
}
try
{
System.out.println("Calling nocatch(true)");
nocatch(true);
}
catch (CustomException ce) {
System.out.println("Caught CustomException for true case");
}
}
public static void nocatch(boolean foo) throws CustomException
{
try
{
if (foo) {
System.out.println("Throwing");
throw new CustomException();
}
}
finally
{
System.out.println("In finally");
}
System.out.println("Reached outside the try/finally block");
}
Output:
Calling nocatch(false)
In finally
Reached outside the try/finally block
Calling nocatch(true)
Throwing
In finally
Caught CustomException for true case
As you can see, the finally block's code runs regardless of whether an exception occurred, but the code after the try/finally doesn't.
Re your follow-up asking why adding return within the finally makes the error go away:
try
{
throw new CustomException();
}
finally
{
return; // <=== Makes the compiler happy (but don't do it!)
}
Interesting edge case! It's because the code in the finally block always runs, and so you'll always return rather than throw, hiding the exception that occurred. E.g., this is the sequence:
throw new CustomException() throws the exception, which transfers control to the finally block
Code in the finally block issues a normal return from the method
This hides the fact the exception occurred; in effect, you've "handled" the exception (without actually handling it) via the finally block. In general, this isn't a good idea; use catch to handle exceptions, or declare them on the method so calling code can handle them.

Instantiating a java if statement referencing an error

How would one write an "if statement" that checks if an error occurred in a method if so it would start a separate method that deals with the error otherwise open the next method
It is called Exception Handling.
Example:
void someMethod()
{
try
{
// Open a File
}
catch(FileNotFoundException e)
{
// Call another method
}
finally
{
// this block executes whether exception occurs or not
}
// Continue execution
}
Use a try catch statement for this. Assumign you want to crash out if the first method errors (after dealing with the exception) then the below format should work
try {
methoda();
} catch(Exception e) {
methodToDealWithError(e);
throw(e);
}
methodb();
i think try-catch block will do it for you. call your first method in try block, then call your method which deals with exceptions in catch block.
Why not just use Exceptions? Make the method throw an exception on error, catch the exception in the calling code, place error handling in the catch block??? That's what Exceptions are for!
It depends on how the method reports the error. If it returns "false" upon error you can do a trivial test:
boolean res = method();
if (!rest) {
// manage error
}
If the method however raises exception, you have to catch them with:
try {
method();
} catch (Exception e) {
// Manage exception or raise
}
Actually it depends on how method is implemented. Can you give some more info ?
methodA: The first method, it throws an exception in case en error occurs
methodB: next Method to execute, if no error occurs
methodC: error dealing method
try{
methodA();
methodB();
catch(Exception e){
methodC();
}
use Exception handling by using try catch block as
try {
Place Your Code Here...
} catch(Exception e) {
callAnotherMethodHere();
}

Java: How do I catch an exception created inside the Method.invoke?

It seems like I can't catch exceptions in my code when the method was called from the Method.invoke method. How can catch it from inside the method itself?
void function() {
try {
// code that throws exception
}
catch( Exception e ) {
// it never gets here!! It goes straight to the try catch near the invoke
}
}
try {
return method.invoke(callTarget, args);
}
catch( InvocationTargetException e ) {
// exception thrown in code that throws exception get here!
}
Thanks!
You can get the real cause of the MethodInvocationException by checking its getCause() method that will return the exception thrown from function()
Note: you might need to call getCause() recursively on the returned exceptions to arrive at yours.
Note: getCause() returns a Throwable, which you will have to check for its actual type (e.g. instanceof or getClass())
Note: getCause() returns null if no more "cause" is available -- you have arrived at the base cause of the execption thrown
Update:
The reason why the catch() in function() is not getting executed is that xxxError is not an Exception, so your catch won't catch it -- declare either catch(Throwable) or catch(Error) in function() if you don't want to declare all specific errors -- note that this is usually a bad idea (what are you going to dio with an OutOfMemoryError?.
One reason that you can't catch UnsatisfiedLinkError with Exception is that UnsatisfiedLinkError is not a subclasses of Exception. In fact, it is a subclass of Error.
You should be careful about catching Error exceptions. They almost always indicate that something really bad has happened, and in most cases it is not possible to recover from them safely. For instance, an UnsatisfiedLinkError means that the JVM can't find a native library ... and that whatever depended on that library is (probably) unusable. Generally speaking. Error exceptions should be treated as fatal errors.
MethodInvocationException means you're calling the method wrong, it shouldn't have even gotten to inside your try block. From the docs:
Signals that the method with the specified signature could not be invoked with the provided arguments.
Edit: That's if this is the Spring MethodInvokationException, the Apache Velocity one does wrap function exceptions.
You throw exceptions as normal. The fact its inside an invoke makes no difference.
public class B {
public static void function() {
try {
throw new Exception();
} catch (Exception e) {
System.err.println("Caught normally");
e.printStackTrace();
}
}
public static void main(String... args) throws NoSuchMethodException, IllegalAccessException {
Method method = B.class.getMethod("function");
Object callTarget = null;
try {
method.invoke(callTarget, args);
} catch (InvocationTargetException e) {
// should never get called.
throw new AssertionError(e);
}
}
}
prints
Caught normally
java.lang.Exception
at B.function(B.java:15)
... deleted ...
at B.main(B.java:26)
... deleted ...

Categories