I have a method that performs some task with a timeout. I use the ExecutorServer.submit() to get a Future object, and then I call future.get() with a timeout. This is workin
I wouldn't say I recommend this, but here is a way you can do it. It is type-safe and whoever comes to modify it after you will probably be unhappy with it.
public class ConsumerClass {
public static byte[] doSomethingWithTimeout(int timeout)
throws ProcessExecutionException, InterruptedException, IOException, TimeoutException {
MyCallable callable = new MyCallable();
ExecutorService service = Executors.newSingleThreadExecutor();
try {
Future future = service.submit(callable);
return future.get(timeout, TimeUnit.MILLISECONDS);
} catch (ExecutionException e) {
throw callable.rethrow(e);
} finally {
service.shutdown();
}
}
}
// Need to subclass this new callable type to provide the Exception classes.
// This is where users of your API have to pay the price for type-safety.
public class MyCallable extends CallableWithExceptions {
public MyCallable() {
super(ProcessExecutionException.class, IOException.class);
}
@Override
public byte[] call() throws ProcessExecutionException, IOException {
//Do some work that could throw one of these exceptions
return null;
}
}
// This is the generic implementation. You will need to do some more work
// if you want it to support a number of exception types other than two.
public abstract class CallableWithExceptions
implements Callable {
private Class e1;
private Class e2;
public CallableWithExceptions(Class e1, Class e2) {
this.e1 = e1;
this.e2 = e2;
}
public abstract V call() throws E1, E2;
// This method always throws, but calling code can throw the result
// from this method to avoid compiler errors.
public RuntimeException rethrow(ExecutionException ee) throws E1, E2 {
Throwable t = ee.getCause();
if (e1.isInstance(t)) {
throw e1.cast(t);
} else if (e2.isInstance(t)) {
throw e2.cast(t);
} else if (t instanceof Error ) {
throw (Error) t;
} else if (t instanceof RuntimeException) {
throw (RuntimeException) t;
} else {
throw new RuntimeException(t);
}
}
}