I have a java.util.concurrent.Execution service - a single threaded thread pool executor. I submit certain tasks to it. If the task throws an unchecked exception the thread dies but the service ensures that a new thread is spawned and subsequent tasks are performed in that. However I do not want this feature and still want to use a threadPoolExecutor. i.e. I want the service to shutDownNow() if the task throws an unchecked exception.
What is the best way to achieve this? Would using a custom thread factory which restricts the number of threads spawned make good sense?
You can create a ThreadPoolExecutor subclass and override the afterExecute method. The method has a throwable parameter that will be non-null if there was an exception.
You could wrap your threadPoolExecutor in an ExecutorCompletionService. Then continually take() from it, retrieving Futures. If future.get() throws an Exception, call threadpoolexecutor.shutdown().
Related
I need to execute only a a single thread with the ability to cancel it. I found that I can achieve this using Future<T>s. Right now I use it like this:
ExecutorService executorService = Executors.newSingleThreadExecutor();
Future<Void> future = executorService.submit(copyCallable);
executorService.shutdown();
Since ExecutorServices are usually used to manage a multiple threads, I was wondering if there was a more efficient way to achieve this without creating one. Thanks.
Interryprion is implemented by both Thread and calling method. Your thread need to listen for InterruptedException or check interruption flag at convenient points in time. Calling code should call t.interrupt() for notifying Thread that it should stop.
I'm writing a scheduler which accepts a Runnable which is either queued for synchronous or asynchronous execution.
I would like to be able to implement a SomeScheduler.interrupt(int taskId) which causes a InterruptedException() to be thrown from within the thread.
Is this possible or am I going about this all wrong?
Threads can be interrupted, a Runnable is just class that implements the run method.
On it's own it doesn’t belong to a thread, if you want to interrupt the execution of the runnable you need to interrupt it's calling thread.
The typical way this is done is to use an ExecutorService. When you submit a runnable or callable to the executor service it will return a Future you can then interrupt a particular task by using the Future#cancel method.
Note that simply interrupting the thread doesn’t cause InterruptedException to be thrown unless the thread is running code that checks the interrupt status and throws InterruptedException, for example the Thread#sleep method.
Why the unhanded exception is rethrown in worker when calling execute method ? As result new Thread will be created on next execution to maximize threads count
Why java ThreadPoolExecutor kill thread when RuntimeException occurs?
I can only guess that the reason why ThreadPoolExecutor.execute(...) has the thread call runnable.run() directly and not wrap it in a FutureTask is so you would not incur the overhead of the FutureTask if you didn't care about the result.
If your thread throws a RuntimeException, which is hopefully a rare thing, and there is no mechanism to return the exception to the caller then why pay for the wrapping class? So worst case, the thread is killed and will be reaped and restarted by the thread-pool.
There is no way to handle exception properly. Exception can't be propagated to caller thread and can't be simply swallowed.
Unhandled exception is thrown in thread is delegated to ThreadGroup.uncaughtException method, which prints output to System.err.print, until desired behavior is overridden for ThreadGroup.
So this is expected behavior, it can be compared with throwing unhanded exception in main method. In this case, JVM terminates execution and prints exception to the output.
But I'm not sure, why ThreadPoolExecutor does not handle it itself, ThreadPoolExecutor can log it itself. Creating new Thread is not so cheap.
Maybe there is an assumption, that some resources (native, threadLocal, threadStack, etc) associated with Thread should be released.
I've got an application which regularly submits tasks to be executed in a dedicated thread. Those tasks are FutureTask<V> and the thread is no more than an infinite loop which executes the jobs as they get into a queue, going to sleep if empty.
Sometimes I need to wait for the result of a computation, so I call FutureTask's get() method, which will also throw an exception if something bad happened. But there are cases where I don't care what the result was, if any, but I need to know (log, printStackTrace() or whatever...) if there was some kind of failure during the task execution.
Is there any way I could achieve this without having to wait on a get() that I don't need?
Thanks in advance!
UPDATE: Calling get() on the runner thread after executing the task seemed to be the only way to catch the exception if no one else would wait for the result.
Another solution would be extending FutureTask class to provide a method which, via java reflection, exposes sync.exception private field.
If I understand your problem correctly, there is a simple solution. Modify your dedicated task-runner thread to call Future.get() after running each task, and catch and log the ExecutionException (if any).
Note that calling get in the task-runner thread after running the task is guaranteed not to block.
(Uncaught exception handlers won't help because any exception and error thrown by the run() method of the future's wrapped Runnable will be caught byFutureTask.run()`.)
Check Thread.UncaughtExceptionHandler
I think you should use 'setException' to report the failure from your task. It will make get() report an ExecutionException. See this as well:
How to catch exceptions in FutureTask
A CompletionService might be a possibility here. Using one of those will allow you to call get() on the Futures once they are definitely finished. Alternatively, the Guava libraries have ways to add a listener to a Future or FutureTask to execute when the task is complete (the ListenableFuture and its related objects).
You can also check an example I wrote for Futuretask
I use ThreadPoolExecutor to run some actions, at some time I cancelled some future tasks and stored it into a list to arrange some other tasks to do, and after that I want to reactive the saved cancelled future tasks.
But the problem is when I submit the task into the pool, it would not be executed, looks like the cancelled or done flag is saved and recognized by the thread executor, and thus that thread would not be called.
What should I do?
The FutureTask implementation maintains the canceled state. Essentially, when the run() method is called again, it does a CAS operation which fails since the state is not runnable and returns immediately without invoking the inner Callable's call() method. I couldn't see a way to retrieve the original Callable out of it or restore the FutureTask to a non-canceled state.
In response to what should you do...
Do you have to cancel them? Why not let them run? If you want priority execution, could you try creating your ThreadPoolexecutor with a PriorityBlockingQueue and use a Comparator to establish the priority. This will allow tasks to be executed in the proper order since they will be added to the PriorityBlockingQueue based on the results of the Comparator.
Use Runnable instead of threads. The execution pool can handle a Runnable the same way a Thread, but a Runnable could be rerunned number of times.
If you want to have a return value you can use a Callable. http://download.oracle.com/javase/1.5.0/docs/api/java/util/concurrent/Callable.html