How to make TestNG continue test execution on an exception? - java

When i get an exception, the test run immediately ends, and any following test validations are skipped. I would like to catch the exception, handle it, then continue the workflow.
In the below example, If objPage.Method1(); throws an exception, the entire #Test immediately ends. I would like the catch to execute, then move on to objPage.Method2().
#Test (enabled=true)
public void MyClientsFunctions() throws Exception {
ExtentTest t = ReportFactory.getTest();
try {
Login objPage = new PageObject(driver);
//this method throws exception
objPage.Method1();
if (x=y)
t.log(LogStatus.PASS, "Pass message");
else
t.log(LogStatus.FAIL,"Fail message"+ screenshotMethod());
objPage.Method2();
if (a=b)
t.log(LogStatus.PASS, "Pass message");
else
t.log(LogStatus.FAIL,"Fail message"+ screenshotMethod());
} catch (Exception e) {
t.log(LogStatus.ERROR, "Exception found: " + e.getMessage() + screenshotMethod());
}
}
I am using PageFactory and ExtentReports. I am use if statements to report failures. No asserts. I believe if an assert fails, the result is the same, and the test ends.

Write the objPage.Method2() in final block then it will execute.

Credit to #JeffC for pointing me in the right direction.
For my case, I have at least a dozen action methods called from the Page Object class. I can't put them all in their own final block.
What I did was put each workflow (one or more methods, then validation) in it's own try/catch. The catch includes logging/screenshot, then redirects to the page that the next workflow needs to execute. So, we try/catch(login), try/catch(enterHoursWorked) etc... As others have said, it's ugly, but in my case it works. Now the exception is added to the log, and the next workflow executes
public void MyClientsFunctions() throws Exception {
ExtentTest t = ReportFactory.getTest();
try {
Login objPage = new PageObject(driver);
// this method throws exception
try {
objPage.Login();
if (x = y)
t.log(LogStatus.PASS, "Pass message");
else
t.log(LogStatus.FAIL, "Fail message" + screenshotMethod());
} catch (Exception e) {
t.log(LogStatus.ERROR, "Exception found: " + e.getMessage() + screenshotMethod());
objPage.BackToHomePage();
}
try {
objPage.EnterHoursWorked();
if (a = b)
t.log(LogStatus.PASS, "Pass message");
else
t.log(LogStatus.FAIL, "Fail message" + screenshotMethod());
} catch (Exception e) {
t.log(LogStatus.ERROR, "Exception found: " + e.getMessage() + screenshotMethod());
objPage.BackToHomePage();
}
} catch (Exception e) {
t.log(LogStatus.ERROR, "Exception found: " + e.getMessage() + screenshotMethod());
}
}

Related

Comparison of exception message always fails in if my statement

I have this variable in my Constants class:
public static final String EXCEPTION_STRING= "My Exceptions message";
I want to check for it in my catch and throw a particular message if it's found. This is what I came up with:
} catch (Exception e) {
if (e.getMessage().equals(Constants.EXCEPTION_STRING)) {
throw new ServiceException(MyClassName.class.toString(),
Constants.EXCEPTION_STRING);
} else {
LOGGER.info("Save failed: " + e);
}
}
The if never seems to get entered even though I can see the correct exception message. What am I doing wrong?
Does your own custom exception get wrapped in another exception? In that case you need to do something like:
e.getCause().getMessage()
This is what I did:
} catch (Exception e) {
if (e instanceof AxisFault) {
if (e.getMessage().equals(Constants.EXCEPTION_STRING)) {
throw new ServiceException(MyClassName.class.toString(),
Constants.EXCEPTION_STRING);
}
} else {
LOGGER.info("Save failed: " + e);
}
}

How to handle custom exceptions in Spring Aspect class?

I need to know how can i handle custom exceptions in my Aspect class, so that i can print log out of it?
Below is my Aspect class:
#Around("#annotation(com.aspect.LoggableService)")
public Object ServiceMetrices(ProceedingJoinPoint pjp) throws Throwable {
try {
pjp.proceed();
} catch(CustomException ex) {
// logging exception details here
LOGGER.info("Logs for API Metrices " + pjp.getSignature() + " {} " +
return pjp.proceed();
} catch (Exception ex) {
// Logging exception details
LOGGER.info("Logs for API Metrices " + pjp.getSignature() + " {} " +
return pjp.proceed();
}
I am calling this aspect annotation after the execution from my service class.
try {
//Code
}
catch(HttpClientErrorException x) {
throw new CustomException(x.getStatusCode(),"POST Request failed");
}
I want my exceptions to be handled by my CustomException block in my Aspect class instead of handling it in Exception class.

How to handle Transaction timeout with #TransactionTimeout

I do have method:
#TransactionTimeout(value = 1, unit = TimeUnit.SECONDS)
#Asynchronous
public void asyncMethod() {
System.out.println("start running asyncMethod in thread " + Thread.currentThread().getName());
try {
Thread.sleep(3000);
} catch (InterruptedException e) {
e.printStackTrace();
}
System.out.println("finished running asyncMethod in thread " + Thread.currentThread().getName());
}
As you can see I running this in Transaction and timeout is set to 1 second and inside I have 3 second sleep. So as a result of running this method I am gettin:
javax.transaction.RollbackException
But let say I would like to implement service which will print information that transaction timeout has occured to the user. How could I achieve that?
#Glains gave me some advice in comment to use Interceptor.
I have added something like that:
#Interceptor
public class LoggingTimeoutInterceptor {
#AroundInvoke
public Object log(InvocationContext ctx) throws Exception {
try {
System.out.println("Logger interceptor");
System.out.println("method " + ctx.getMethod().getName());
return ctx.proceed();
}catch (RollbackException e) {
System.out.println("Transaction RollbackException occured");
return null;
}
catch (Exception e) {
System.out.println("Exception occured");
return null;
}
}
}
This code is writing first two sysout correctly. But is not catching any exception and I dont know why. I was trying to change #AroundInvoke to #AroundTimeout but then it is not running at all.

In Main function, after a try block throws an exception how can I make it keep on execute the next try block

In Main function, after a try_block throws an exception the function is supposed to be break. My question is how can I make it keep on executing to the next try_block. Below I'm giving an example:
public static void main(String [] s){
ABC aBC = new ABC();
try {
aBC.execute();
} catch (Exception e) {
_log.error(ErrorCodeEnum.ERROR,
"XXXXXXX!!! in " + new Date(),e);
}
BCD bCD = new BCD();
try {
bCD.execute();
} catch (Exception e) {
_log.error(ErrorCodeEnum.ERROR,
"YYYYYYYYYYY!!! in " + new Date(),e);
}
}
The code should work as it stands - i.e. the second block should still get executed if the first block throws and catches an Exception.
However you might want to consider catching Throwable rather than Exception if you truly want to catch everything. In particular, java.lang.Error is not a subclass of Exception, but is a subclass of Throwable.
Just to be sure, you can wrap the statements you want executed in a finally block as follows:
ABC aBC = new ABC();
try
{
aBC.execute();
}
catch (Exception e)
{
_log.error(ErrorCodeEnum.ERROR, "XXXXXXX!!! in " + new Date(), e);
}
finally
{
BCD bCD = new BCD();
try
{
bCD.execute();
}
catch (Exception e)
{
_log.error(ErrorCodeEnum.ERROR, "YYYYYYYYYYY!!! in " + new Date(), e);
}
}
The statements in the finally block will get executed regardless if an exception occurs in the outer try block.

exception.getMessage() output with class name

I'm trying to fix an issue, in my application I have this code
try {
object1.method1();
} catch(Exception ex) {
JOptionPane.showMessageDialog(nulll, "Error: "+ex.getMessage());
}
and the object1 would do something like that:
public void method1() {
//some code...
throw new RuntimeException("Cannot move file");
}
I get a messsage in my option pane like this:
Error: java.lang.RuntimeException: Cannot move file
but I used getMessage and not toString method, so the name of the class shouldn´t appear, right?
What I am doing wrong?
I already tryied with a lot of exceptions, even Exception itself. I'm looking to solve this no without the need to implement my own Exception subclass
PROBLEM SOLVED - thank you all!
The try and catch were actually being called in get() method from SwingWorker which constructs an ExecutionException with my exception thrown from doInBackground()
I fixed doing this:
#Override
protected void done() {
try {
Object u = (Object) get();
//do whatever u want
} catch(ExecutionException ex) {
JOptionPane.showMessageDialog(null, "Error: "+ex.getCause().getMessage());
} catch(Exception ex) {
JOptionPane.showMessageDialog(null, "Error: "+ex.getMessage());
}
}
I think you are wrapping your exception in another exception (which isn't in your code above). If you try out this code:
public static void main(String[] args) {
try {
throw new RuntimeException("Cannot move file");
} catch (Exception ex) {
JOptionPane.showMessageDialog(null, "Error: " + ex.getMessage());
}
}
...you will see a popup that says exactly what you want.
However, to solve your problem (the wrapped exception) you need get to the "root" exception with the "correct" message. To do this you need to create a own recursive method getRootCause:
public static void main(String[] args) {
try {
throw new Exception(new RuntimeException("Cannot move file"));
} catch (Exception ex) {
JOptionPane.showMessageDialog(null,
"Error: " + getRootCause(ex).getMessage());
}
}
public static Throwable getRootCause(Throwable throwable) {
if (throwable.getCause() != null)
return getRootCause(throwable.getCause());
return throwable;
}
Note: Unwrapping exceptions like this however, sort of breaks the abstractions. I encourage you to find out why the exception is wrapped and ask yourself if it makes sense.
My guess is that you've got something in method1 which wraps one exception in another, and uses the toString() of the nested exception as the message of the wrapper. I suggest you take a copy of your project, and remove as much as you can while keeping the problem, until you've got a short but complete program which demonstrates it - at which point either it'll be clear what's going on, or we'll be in a better position to help fix it.
Here's a short but complete program which demonstrates RuntimeException.getMessage() behaving correctly:
public class Test {
public static void main(String[] args) {
try {
failingMethod();
} catch (Exception e) {
System.out.println("Error: " + e.getMessage());
}
}
private static void failingMethod() {
throw new RuntimeException("Just the message");
}
}
Output:
Error: Just the message

Categories

Resources