У меня есть метод, который выполняет некоторую задачу с таймаутом. Я использую ExecutorServer.submit() для получения объекта Future, а затем я вызываю future.get() с таймаутом. Это работает нормально, но мой вопрос - лучший способ обработать проверенные исключения, которые могут быть выбраны моей задачей. Следующий код работает и сохраняет проверенные исключения, но он кажется чрезвычайно неуклюжим и подвержен перерыву, если изменяется список проверенных исключений в сигнатуре метода.
Любые предложения по устранению этого? Мне нужно настроить таргетинг на Java 5, но мне также было бы интересно узнать, есть ли хорошие решения в более новых версиях Java.
public static byte[] doSomethingWithTimeout( int timeout ) throws ProcessExecutionException, InterruptedException, IOException, TimeoutException {
Callable<byte[]> callable = new Callable<byte[]>() {
public byte[] call() throws IOException, InterruptedException, ProcessExecutionException {
//Do some work that could throw one of these exceptions
return null;
}
};
try {
ExecutorService service = Executors.newSingleThreadExecutor();
try {
Future<byte[]> future = service.submit( callable );
return future.get( timeout, TimeUnit.MILLISECONDS );
} finally {
service.shutdown();
}
} catch( Throwable t ) { //Exception handling of nested exceptions is painfully clumsy in Java
if( t instanceof ExecutionException ) {
t = t.getCause();
}
if( t instanceof ProcessExecutionException ) {
throw (ProcessExecutionException)t;
} else if( t instanceof InterruptedException ) {
throw (InterruptedException)t;
} else if( t instanceof IOException ) {
throw (IOException)t;
} else if( t instanceof TimeoutException ) {
throw (TimeoutException)t;
} else if( t instanceof Error ) {
throw (Error)t;
} else if( t instanceof RuntimeException) {
throw (RuntimeException)t;
} else {
throw new RuntimeException( t );
}
}
}
=== UPDATE ===
Многие люди опубликовали ответы, которые рекомендовали либо 1) повторное бросание в качестве общего исключения, либо 2) повторное бросание в качестве неконтролируемого исключения. Я не хочу делать ничего из этого, потому что эти типы исключений (ProcessExecutionException, InterruptedException, IOException, TimeoutException) важны - каждый из них будет обрабатываться по-разному обработанным вызовом. Если мне не нужна функция тайм-аута, я бы хотел, чтобы мой метод выбрал эти 4 конкретных типа исключений (ну, кроме исключения TimeoutException). Я не думаю, что добавление функции тайм-аута должно изменить мою сигнатуру метода, чтобы создать общий тип исключения.