2017-01-05 6 views
0

Я задал этот вопрос раньше, но не смог его открыть снова, так как мое обновление не ударило процесс повторного открытия. Таким образом, повторная отправкаКак справиться с ситуацией, когда ExecutorService ThreadFactory возвращает нуль вместо aad

Мой вопрос: как получить ExecutorService, чтобы понять, что поток недействителен (null) сразу, не дожидаясь выхода в будущее.

У меня есть прецедент, когда при создании потока в ThreadFactory я хочу вернуть значение null, если поток не может быть настроен правильно (например, он не может подключиться к серверу).

Когда ExecutorService запускает отправку по вызываемому, и ThreadFactory возвращает значение null, как показано ниже, код будет работать, но будет ждать в будущем. (5, TimeUnit.SECONDS); а затем выбросить исключение TimeoutException. Проблема в том, что ThreadFactory.newThread() не позволяет мне создавать исключение здесь.

public class TestThreadFactory implements ThreadFactory { 
    @Override 
    public Thread newThread(Runnable r) { 
     // try to create a conneciton that fails 
     // I cannot throw an exception here, so if there is a problem I have to return null 
     return null; 
    } 
} 

public class ExecutorServicePool { 

    public static ExecutorService getService() { 
     return Executors.newFixedThreadPool(10, new TestThreadFactory()); 
    } 
} 

public static void main(String[] args) { 
    ExecutorService executorService = ExecutorServicePool.getService(); 

    Callable callable = new Callable<String>() { 
     @Override 
     public String call() throws Exception { 
      return "callable"; 
     } 
    }; 

    Future<String> future = executorService.submit(callable); 
    try { 
     future.get(5, TimeUnit.SECONDS); 
    } catch (InterruptedException e) { 
     e.printStackTrace(); 
    } catch (ExecutionException e) { 
     e.printStackTrace(); 
    } catch (TimeoutException e) { 
     e.printStackTrace(); 
    } 
    executorService.shutdown(); 
} 
+1

Это очень странный образец. Когда вы захотите _want_ вернуть null из 'ThreadFactory'? Какова цель? – Gray

+0

The Thread устанавливает соединение с сервером при его создании. Если попытка подключения не удалась, поток не должен быть создан, и об этом нужно сообщить об этом. Должен ли я пытаться по-другому. – user1213428

ответ

2

Вы можете выбросить RuntimeException, который чувствует себя как разумная вещь.

RuntimeException s отлично подходит для ситуаций, которые обычно не подлежат восстановлению. Неспособность подключиться к базе данных, например, является ярким примером одной из этих ситуаций. В основном в этом сценарии вы хотите сказать: «Что-то действительно не так, и на минуту я не могу обработать ваш запрос Повторите попытку позже»

RuntimeException s может быть брошен в методе если интерфейс не объявляет их. Таким образом, вы можете обновить свою реализацию ThreadFactory, чтобы выбросить RuntimeException, а не возвращать null. Вы могли бы даже создать определенный подкласс класса RuntimeException, чтобы убедиться, что это ясно, что ошибка в вашем приложении, например. FailedToInitialiseThreadException

+0

Да, это работает. Я пытался бросить подкласс Exception до этого, и это нарушило подпись ThreadFactory.newThread(). – user1213428

2

Вы можете создавать собственные службы ИСПОЛНИТЕЛЬ путем расширения ThreadPoolExecutor и

методы переопределения где threadfactory вызывается для получения нового потока вашей потребности.