I want an app that throws an exception from a button.
The exception should then shutdown the application (unhandled exception).
( I need that to check my code in Runtime.getRuntime().addShutDownHook() )
So I wrote this
button1.addActionListener(new ActionListener() {
#Override public void actionPerformed(ActionEvent e) {
throw new NullPointerException("");
}
});
And tried also tried throwing a RuntimeException, but the application did not close.
Any suggestion how can I close my app due to an exception?
Thanks.
EDIT
I will explain -
In the Java docs - http://docs.oracle.com/javase/6/docs/api/java/lang/Runtime.html#addShutdownHook(java.lang.Thread)
it is noted that when you write a JVM shut down hook - make it a fast running piece of code. Quote:
"Shutdown hooks should also finish their work quickly...."
My code is running a bit longer and I wanted to test it by an exception (and not System.exit() - though it should be the same, but sometimes the results are not the same)
Just wondered how you throw an exception from a button (I know the code is bad, it's for testing ).
check this answer:
How do I catch this exception in Swing?
In implementation of uncaughtException just exit your app.
You need to catch the exception and call System.exit()
It is explained here in the comments (suggested by Duncan Jones ;)
The setDefaultUncaughtExceptionHandler will only work if the thread die (thread abruptly terminates due to an uncaught exception). But EventQueue thread will never die unless the application ends. Therefore without special handling all uncaught exception will be swallow by EventQueue and go into system out silently.
So I would add an uncaught exception handler to trap when other threads die, but to check exceptions throw in the EDT, you have to catch them yourself.
any suggestion how can I close my app due to an exception?
For a start, throwing an exception from the action listener won't work. It will kill the Swing event dispatcher thread, but that won't make the application exit.
The simple solution is to call System.exit(...) from the listener to tell the JVM to shutdown. However, if that approach is a bit "brutal" and may cause tasks being performed asynchronous to be abandoned. You can ameliorate by using shutdown hooks to give the tasks to bail out, but it is still not nice. For instance, shutdown hooks don't fire in a predictable order ...
A better solution is to design your application to attempt to perform an orderly shutdown before it pulls the plug by calling System.exit(). For instance, once the "main" thread has launched the Swing dispatcher event thread, it could wait on a condition which tells it to shutdown. The action listener for the "exit" button would signal this condition, and the main thread would wake up and start shutting things down.
Related
I've written a custom UncaughtExceptionHandler that should print the exception to the console and shut down the application with a custom exit code.
The class looks like this:
public class FatalUncaughtExceptionHandler implements Thread.UncaughtExceptionHandler {
#Override
public void uncaughtException(final Thread t, final Throwable e) {
System.out.println("Handled exception in " + t.getName() + ":");
e.printStackTrace();
System.exit(ExitCodes.UNKNOWN_EXCEPTION);
}
}
I set the UncaughtExceptionHandler in my Main.class like this:
Thread.setDefaultUncaughtExceptionHandler(new FatalUncaughtExceptionHandler());
Then I generate and start 4 threads.
In one of the running threads I purposely generate a NumberFormatException using Integer.valueOf("Test") in order to test my Handler. This works fine; Here's the output:
Handled exception in WatchdogThread:
java.lang.NumberFormatException: For input string: "Test"
at java.lang.NumberFormatException.forInputString(NumberFormatException.java:65)
at java.lang.Integer.parseInt(Integer.java:580)
at java.lang.Integer.valueOf(Integer.java:766)
at com.csg.gfms.gms.ctmgate.runnable.WatchdogThread.run(WatchdogThread.java:43)
Now I have a problem. For some reason the thread in which the exception was thrown is not being shutdown by the System.exit() command. Apparently my ShutdownHook has a lock on it. (As seen in the output of jvisualvm):
"WatchdogThread" #38 prio=5 os_prio=0 tid=0x000000001efa3800 nid=0xd40 in Object.wait() [0x0000000021a5e000]
java.lang.Thread.State: WAITING (on object monitor)
at java.lang.Object.wait(Native Method)
- waiting on <0x000000076e30a7c0> (a com.csg.gfms.gms.ctmgate.runnable.CTMShutdownHook)
at java.lang.Thread.join(Thread.java:1252)
- locked <0x000000076e30a7c0> (a com.csg.gfms.gms.ctmgate.runnable.CTMShutdownHook)
at java.lang.Thread.join(Thread.java:1326)
at java.lang.ApplicationShutdownHooks.runHooks(ApplicationShutdownHooks.java:107)
at java.lang.ApplicationShutdownHooks$1.run(ApplicationShutdownHooks.java:46)
at java.lang.Shutdown.runHooks(Shutdown.java:123)
at java.lang.Shutdown.sequence(Shutdown.java:167)
at java.lang.Shutdown.exit(Shutdown.java:212)
- locked <0x00000006c9605b00> (a java.lang.Class for java.lang.Shutdown)
at java.lang.Runtime.exit(Runtime.java:109)
at java.lang.System.exit(System.java:971)
at com.csg.gfms.gms.ctmgate.handlers.FatalUncaughtExceptionHandler.uncaughtException(FatalUncaughtExceptionHandler.java:13)
at java.lang.ThreadGroup.uncaughtException(ThreadGroup.java:1057)
at java.lang.ThreadGroup.uncaughtException(ThreadGroup.java:1052)
at java.lang.Thread.dispatchUncaughtException(Thread.java:1959
Even IntelliJ tells me that the System.exit command will fail. It displays a little badge next to it saying "Method will fail" when debugging my UncaughtExceptionHandler.
This leads me to my question:
Is it not allowed to call System.exit() from an UncaughtExceptionHandler?
Is the shutdown hook initiated twice in my case?
What could be the reason for the lock on the shutdown hook?
See that com.csg.gfms stuff in the trace?
It's not java; it's you. That's your code that's blocking in another shutdown hook; one that is calling Thread.join.
Generally when running into such weirdness, if it is at all possible to make a stand-alone super simple test case, then you should do so. I have done this for you:
class Test {
public static void main(String[] args) throws Exception {
Thread.setDefaultUncaughtExceptionHandler(new Thread.UncaughtExceptionHandler() {
public void uncaughtException(Thread t, Throwable e) {
System.out.println("EXITING");
System.exit(1);
}
});
for (int i = 0; i < 10; i++) {
Thread t = new Thread(new Runnable() {
public void run() {
try {
Thread.sleep(1000L);
} catch (Exception ignore) {}
throw new RuntimeException();
}
});
t.start();
}
Thread.sleep(2000L);
System.out.println("Still alive?");
}
}
When I run this, I get an arbitrary number of EXITING prints (2 to 3, it's dependent on how many cores are simultaneously working on these threads), and then the VM hard-exits. Still alive? is never printed, no locking occurs, the VM actually exits.
Thus proving that calling System.exit() from within the uncaught exception handler is not an issue.
The shutdown hook is not invoked twice; the shutdown hook is invoked due to you invoking System.exit, not because we got to the uncaught exception handler. But, if you're worried about this, hey, it's your app, print something in your shutdown hooks to be sure.
The lock issue is not on the shutdown hook. You can register any amount of shutdown hooks. It's in a shutdown hook. Specifically: somebody registered an instance of com.csg.gfms.gms.ctmgate.runnable.CTMShutdownHook, that code is joining some thread, and that thread is not shutting down, thus that hook never exits, thus System.exit is not exiting the VM. The solution is to fix CTMShutdownHook, which is broken.
Joining a thread in a shutdown hook is... well, I'll just say it bluntly: Stupid. I don't quite know what this is trying to accomplish, but the only thing I can think of is forced adherence to a bad standard. Therefore, I can foresee that you, or the author of CTMShutdownHook, first needs some introspective on how to deal with JVM shutdowns, so that they understand that the idea underlying their implementation is fundamentally misguided and needs to be rethought.
I will do that here.
There is this mindset that to 'properly' shut down a VM, one should never invoke System.exit, one should instead carefully tell all running threads to stop, and one should carefully manage the daemon flag on all threads, so that the VM will end up shutting down on its own volition because all still alive threads have the daemon flag set. The argument being that this gives each thread the chance to 'shut down nicely'.
This is bad code style.
Your app will just shut down if someone hits CTRL+C or otherwise asks the VM to exit, this will not result in a nice 'ask all threads to clean up and stop' process. In fact, your app gets zero opportunity to clean up anything if someone trips over a powercable, the computer hard-crashes, or someone terminates the app.
This leads to the following rules:
Any code that is written so that it breaks if not shut down nicely (e.g. you keep some state in memory, and upon being asked to quit, you save this state to disk; it is quite a serious bug if this state is just forgotten) is bad code. It is always possible to write code so that recovery is possible. Even extreme cases, such as filesystems, can (these days) handle just pulling the cord using e.g. journalling technology.
If you want to at least 'be nice' and try to save state or otherwise cleanup, do not wait for someone to tell your thread to 'exit nicely'. Just register a shutdown handler which does the cleanup, and assume your main thread loop will just straight up abort at some arbitrary point without any further notification. This is not actually hard to write.
Said differently: Don't ever assume your thread will be told to clean up after itself. Assume that usually any registered shutdownhandlers are invoked, but don't rely on them entirely, as in rare scenarios (power pulse, kill -9, VM core crash, memory issues, someone runs this in an IDE and just kills it, which is usually a hard-kill, the list is long) those don't run either.
By adding a shutdownhook that 'joins' a thread (joining = pause this thread until that thread exits), you've created a very silly scenario where of the 3 different ways to shut an app down:
Someone trips over a powercable or kill -9s your app: Everything dies on the spot, no cleanup possible.
CTRL+C is hit or someone calls System.exit or normal SIGKILLs your app: Everything dies on the spot, but all shutdown hooks are invoked.
(Misguided) Within the app some process starts trying to get all non-daemon threads to return, and they will presumably be doing their cleanup internally.
What 'join this thread in a shutdown hook' does is effectively downgrade that second form to the (bad) third form.
With that context, you can now fix the broken code in CTMShutdownHook, or talk to the developer of that hook and explain to them that the elegant-sounding idea of allowing all running threads to shut down nicely is in fact bad.
Then as a more general point of principle, shutdown hooks should block as little as possible and should definitely not wait for other threads to act.
So, I have a main thread that spawns a bunch of "worker-threads" that works alongside it for the duration of the process. What I want is that if a worker-thread dies from an exception or whatnot, the main thread should also throw a runtime-exception and die peacefully.
This can be achieved by catching the exception in the worker-tread and setting an error-flag before exiting. The main thread then polls this flag and throws an exception if it's set. This can be done by try-catch or setting an exception handler.
My question is whether there's a simpler way that doesn't include polling in the main thread. Something that goes automatic if you know what I mean.
Edit:
Well, many claim that setting a handler is the answer and that this is a duplicate. Well, unless I'm mistaking things here, the handler is executed by the thread that throws the exception in the first place, so I still have to set a flag to kill the main thread. I thought this was clear. SO let me clarify;
What I want is that if a worker-thread dies from an exception or whatnot, the main thread should also throw a runtime-exception and die peacefully, without using flags, but have it done "automatically"
Have a CountdownLatch in the main thread, have it wait on the CountdownLatch.
When a thread exits decrement the CountdownLatch. When that happens have the main thread act appropriately.
This is not a question about how to cleanly terminate a thread, ie by calling interrupt on it and having the thread respond appropriately. I cannot modify code the thread is executing in any way.
I specifically want to immediately terminate a Thread, I don't care at all what state things are left in. I know something similar is possible using Thread.stop, however this actually throws a ThreadDeath exception, and for the Thread to terminate this exception cannot be caught. However the code I am dealing with catches this exception and is not rethrowing it.
Thread.destroy() seemed to be what I was looking for, however this method was never implemented. Is there any other way of achieving this?
I believe that there's no way in Java to just kill off a thread like you're describing. As you note in a comment, interrupt won't do what you want. If the thread is executing, it just sets a flag and it's up to the thread to notice it. if the thread is waiting or sleeping, it will throw an InterruptedException.
The only way I can imagine doing what you're describing is to kill the process in which the thread is running. (E.g., call System.exit(int).)
No there isn't a way. From Java Concurrency in Practice:
Since there is no preemptive way to stop a thread, they must instead
be persuaded to shut down on their own.
Interrupting a thread is not the cleaner way as you said. Clean ways could be:
ExecutorService.shutdown()
Future.cancel()
Poison Pills
You aren't meant to submit tasks to threads that take ages to be done. You would rather divide them into smaller tasks and send a poison pill to cancel the bigger task. If there is not a way to do that, then spawn/fork a process and kill it if you want to cancel the task.
If you don't trust the thread in question to the point that you need to kill it, you would probably be better off running it in a separate process, and kill the process instead.
Anyway, the following code might work if you are ok with the deprecated Thread methods:
while (theThread.isAlive()) {
theThread.stop();
}
Depending on how badly the thread is trying to survive…
You might want to run this code in several threads or repeat the stop() call if that's not enough. However, I managed to kill the following thread with this code:
final Thread iWontDie = new Thread(() -> {
int i = 0;
while (true) {
try {
System.out.println("I'm still alive! " + ++i);
} catch (Throwable t) {
// eat t
}
}
});
iWontDie.start();
If you are on Java 7 or earlier, you could use the overloaded stop(Throwable obj) method to throw something besides a ThreadDeath error:
Forces the thread to stop executing. If the argument obj is null, a NullPointerException is thrown (in the current thread). The thread represented by this thread is forced to stop whatever it is doing abnormally and to throw the Throwable object obj as an exception. This is an unusual action to take; normally, the stop method that takes no arguments should be used.
This method, like the parameterless version, is deprecated, so just keep that in mind.
Is there a way to make my java application shut down there is an error? e.g. if I have a nullpointerexception, can I just make it completely close out?
Any uncaught exception at the top level will automatically halt the thread it's in. If you have more than one thread in your program, the other threads will still survive. If you want to terminate explicitly, you can call System.exit()
You can use System.exit(0); to terminate the JVM.
However, you should avoid NullPointerException by checking the reference before using it:
if(foo != null) foo.doSomething();
As others have said, catching the exception and calling System.exit() is (generally) the right approach. But there is more to it than that:
Q: Do I really need to catch it?
A: If your application is a conventional command-line application, and the exception is thrown on the "main" thread, then you may not need to catch it. Uncaught exceptions on the main thread will cause the application to exit ... if there are no other non-daemon threads in existence. (In fact, the same thing goes for any thread ... )
However if your thread has more than one non-daemon thread, then you need to do something to stop the application. Like catch the exception and call exit().
Q: Where do you catch it?
A: On the stack of any thread where the "fatal" exception might be thrown. There are two ways to do this:
Put a try / catch (Throwable) in the main(String[]) method, a thread's run() method, etcetera.
Install a default uncaught exception handler.
What you DON'T want to do is to add System.exit() calls all through your codebase. That approach leads to all sorts of problems with reusability, unit testing and generally figuring out "why has the effing application died again".
Q: What if it is already caught?
A: One reason why your application might not be exiting naturally, is that your code is already catching the exception ... by accident. For instance:
try {
doSomething()
} catch (Exception ex) {
handle an IO exception
}
In the above, some ignorant / lazy programmer hasn't bothered to consider the exceptions that might be thrown in doSomething and has assumed that they are all some kind of IO related exception. But if the exception was actually an unexpected NullPointerException ... or something worse ... then the code has just squashed it.
The cure for this kind of thing is code-reviews and mentoring to cure the programmer of his bad habits ... hopefully before he does too much damage to the codebase! And if you find this kind of thing in your codebase, you should fix it immediately ... and probably "grep" for similar occurrences and fix them too.
I'm relatively new to Threading in Java and I've noticed that everytime I use Thread.sleep() I have to catch InterrupetdException.
What kind of behaviour causes this, and in simple applications where I have a monitor thread can I just Ignore the exception?
It happens when something calls interrupt() on the thread. This article by Brian Goetz explains the interruption mechanism and how you should handle InterruptedExceptions:
"The most common response to InterruptedException is to swallow it -- catch it and do nothing (or perhaps log it, which isn't any better) -- as we'll see later in Listing 4. Unfortunately, this approach throws away important information about the fact that an interrupt occurred, which could compromise the application's ability to cancel activities or shut down in a timely manner."
"If you catch InterruptedException but cannot rethrow it, you should preserve evidence that the interruption occurred [...]. This task is accomplished by calling interrupt() to "reinterrupt" the current thread."
As others have said, it is caused by some other thread calling interrupt() on the Thread object that is sleeping.
What this means in plain english, is that some other thread has decided to cancel the sleeping thread. The try/catch block is there so you can gracefully handle the cancellation of the thread, and safely clean up any resources, or shut down whatever operation it was doing correctly.
If you don't actually need to do any of that, then yes, you still need an empty catch block. But that's Java for you...
Some advices from Java Concurrency in Practice:
Propagate the exception (possibly after some task-specific cleanup), making your method an interruptible blocking method, too; or
Restore the interruption status so that code higher up on the call stack can deal with it.
Only code that implements a thread's interruption policy may swallow an interruption request. General-purpose task and library code should never swallow interruption requests.
The primary case is when someone calls Thread.interrupt() on your thread.
It may be safer to throw a RuntimeException if it happens when you're really not expecting it, but for very simple cases you can probably ignore it.
From the javadocs:
Class InterruptedException
Thrown when a thread is waiting,
sleeping, or otherwise paused for a
long time and another thread
interrupts it using the interrupt
method in class Thread.
Hope that answers your question.
Well if some other Thread calls thread.interupt(), while the thread is sleeping, you'll get the Exception. And yes, you can probably just put try..catch arround the sleep() and ignore it ;)
InterruptedException is a checked exception so unfortunately you cannot just ignore it. In most simple cases you do not have to do anything in the catch clause because you are sure that it will not happen.
From the API
Thrown when a thread is waiting, sleeping, or otherwise paused for a long time and another thread interrupts it using the interrupt method in class Thread.