3

I have a class the implements A which will run a certain method of class B. There is a requirement that this A should never crash when running this operation (which is not possible, right?).

To reduce the chance of crashing I'm catching Throwable around the operation, like so:

public void method(B b)
{
    try
    {
        b.operation
    }
    catch(Throwable e)
    {
        //Log e
        //Clean up stuff
    }
}

My questions are:

  • Would this actually help in reducing crashes caused by any thrown Error?
  • Is it a good idea to ever catch an Error?
7
  • The ExecutorService will not stop running if your code throws an exception, it's just the Runnable will stop and not be rescheduled. Other than that - Do you really need this particular module to continue working even if the rest of the app just went haywire?
    – Ordous
    Commented Oct 6, 2014 at 14:22
  • 1
    possible duplicate of Defensive Programming vs Exception Handling?
    – user53019
    Commented Oct 6, 2014 at 14:26
  • @Ordous Damn I forgot about that. I was trying to use ExecutorService as an example because I can't share real code due to company policy. I'll edit the question :p
    – Adam
    Commented Oct 6, 2014 at 14:26
  • 1
    Also see here and much of the questions here
    – user53019
    Commented Oct 6, 2014 at 14:27
  • @Ordous I know it's weird by I don't make the requirements and have no influence on them. So if they say don't crash this module that means I have to do the best to not crash this module. I've been explicitly told this.
    – Adam
    Commented Oct 6, 2014 at 14:28

4 Answers 4

11

Simple Answers: No and no.

For example catching an OutOfMemoryError can be bad as without memory what could you do?

Also all other errors are most likely indicate some more serious error where you can do nothing.

For reference see the errors in the package java.lang and decide for every one what you will do when you catch it. If you're happy you will find that perhaps every tenth error could be handled by you.

12
  • But are there any other Errors that can be "handled"?
    – Adam
    Commented Oct 6, 2014 at 14:22
  • 3
    @Adam No, there are none. One of the reasons they are not exceptions is stated right on the Error class - reasonable applications should not catch these. Another trait is that Errors are not local. For most exceptions all side effects are in the calling method, for an Error that is not the case.
    – Ordous
    Commented Oct 6, 2014 at 14:24
  • 1
    Usually you'd catch an OOME at a pretty high level, with many objects going out of scope and freeing up space. And if the error was caused by a single oversized allocation request, then there really is no problem at all. Commented Oct 6, 2014 at 15:05
  • 3
    @MichaelBorgwardt actually is quite the opposite, catching an OOME might make some sense at low level (say, I am requesting a 30 MB+ buffer to load a video file). In that case, you can expect and deal with the error easily (just replacing it with an exception/could not load control code). If you just capture the error at high level, the state of the system would be unknown (it is unknown which operations failed), and the only realistic option would be "resetting" all of the program states.
    – SJuan76
    Commented Oct 6, 2014 at 16:26
  • 1
    So I agree that catching Errors is often futile, but contrary to some of the absolute statements here, there are legitimate circumstances to catch Errors.
    – Brandon
    Commented Oct 7, 2014 at 19:11
3

When you encounter an Error, it typically means your program is now in an undefined state: a .class file is corrupted, or memory is completely full, or you've run into an internal bug in the JVM, or something of similar severity. Ask yourself: even if you catch the Error to prevent an immediate crash, is it meaningful to continue running under these circumstances? Can you trust the program to behave correctly afterward? What can you do to actually handle an Error once you catch it?

If your "never crash" requirement means "never stop executing", then by all means, log and continue. Clearly your client believes that a misbehaving program is better than a terminated one. But if "never crash" means "never stop functioning", you should focus your defensive efforts elsewhere to prevent the Error from occurring in the first place, let it terminate the program if it somehow occurs anyway, and configure your server to automatically restart the program if that happens.

1

In general, you should NEVER catch things like Exception, Throwable, or Error, but only those specific subclasses of those that your application can reasonably be expected to handle and survive (or at least log something useful about before crashing).

Exception handling is supposed to be just that, handling error conditions and dealing with them in such a way that the application can continue running or report what happened before terminating.
It's not meant to be error masking, hiding problems and then just try to continue as if nothing happened. Not only will it rarely work (it will rear its ugly head somewhere else in the application soon, making the problem worse as now you have even more corruption in your state and/or data, but you now have a problem that's that much harder to track down and debug, and eventually fix.

0

I won't write a java program without catching Throwable at the top level of every process. The caught error is (by definition) unexpected, and is a bug that needs to be logged and fixed. The errors you catch this way will surprise you, and you will never learn of them unless you make every possible attempt to get the word back from the real world to your development desk.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.