Цепочка ListenableFutures с условиями раннего возврата - PullRequest
0 голосов
/ 20 апреля 2020

У меня есть цепочка ListenableFutures, где выход предыдущего является входом следующего. Я сталкиваюсь с тем, что в некоторых особых случаях мы можем получить результат на ранней стадии процесса. Код выглядит примерно следующим образом (но имеет гораздо больше параметров, локальных переменных, вызовов вспомогательных методов и т. Д. c.):

public ListenableFuture<R> result(I input) {
  if (specialCase(input)) {
    return Futures.immedateFuture(specialResult(input));
  }
  ListenableFuture<A> futureA = getA(input);
  return Futures.transformAsync(futureA, a -> process(a), directExecutor);
}

public ListenableFuture<R> process(A a) {
  if (specialCase(a)) {
    return Futures.immedateFuture(specialResult(a));
  }
  ListenableFuture<B> futureB = getB(a);
  return Futures.transform(futureB, b -> process(b), directExecutor);
} 

public R process(A b) {
  if (specialCase(b)) {
    return specialResult(b);
  }
  return finalResult(b);
}

Я хотел бы улучшить читаемость этого кода, поэтому что более очевидно, что является основным конвейером обработки (т. е. getA -> getB -> finalResult) в основной функции, без необходимости отслеживать его. Я думал как-то использовать FluentFuture , но я не знаю, как лучше всего обработать эти ранние операторы возврата.

Одна из идей, которые у меня были, - это использовать выделенное Исключение и не удалось. фьючерсы в качестве побочного канала для этих специальных результатов, но это не кажется элегантным - это правильные возвращаемые значения, а не ошибки в конце концов.

...