Объединение других этапов не изменяет предыдущие этапы. Другими словами, параллелизм полностью находится вне вашего контроля, поскольку он уже определен.
Более конкретно, когда вы вызываете injectedClass1.longRunningOp(param1, param2)
, реализация метода longRunningOp
решает, как будет возвращено будущее будет завершена. Аналогично, когда вы вызываете injectedClass2.serviceCall(param1, param2, someOtherData)
, реализация serviceCall
будет определять завершение возвращенного future-объекта. Оба метода могут использовать один и тот же исполнитель за кулисами или совершенно разные подходы. будущее. В этом случае вам придется заключить каждый вызов в другую асинхронную операцию, чтобы позволить им работать параллельно. Но было бы странно возвращать будущее при выполнении длительной операции в потоке вызывающего.
Ваш код
CompletableFutures.combine(firstFuture, secondFuture, (a, b) -> a)
не соответствует документированному API . Допустимый вызов:
firstFuture.thenCombine(secondFuture, (a, b) -> a)
В этом случае вы не влияете на завершение firstFuture
или secondFuture
. Вы только указываете, что должно произойти после оба фьючерса были завершены.
Между прочим, нет причин указывать такую тривиальную функцию, как (a, b) -> a
в thenCombine
, просто чтобы связать еще один thenApply
. Вы можете использовать в первую очередь
firstFuture.thenCombine(secondFuture,
(v, b) -> ServiceResponse.newBuilder().setParam(v.toString()).build())
.