Есть ли способ выполнить действие после завершения всех последующих этапов? - PullRequest
0 голосов
/ 06 июля 2018

CompletionStage.whenComplete() выполняет действие после завершения текущего этапа, но что произойдет, если этап имеет зависимые этапы? Есть ли способ выполнить действие после завершения всех зависимых этапов, когда у меня нет доступа к зависимостям?

Пример:

CompletionStage<Void> parent = ...;
registerCleanup(parent);
CompletionStage<Void> child = parent.thenApply(expensiveOperation);

registerCleanup() получает доступ только к parent, но хочет зарегистрировать действие, которое будет очищено после выполнения child. Можно ли это сделать?

1 Ответ

0 голосов
/ 30 августа 2018

Обычно это невозможно, по крайней мере с API CompletionStage или CompletableFuture.

Если учесть это, для этого потребуется знать

  • когда все зависимости были выполнены
  • но, кроме того, будут ли добавлены какие-либо новые зависимости в будущем

Когда вы посмотрите на пример кода, как registerCleanup() узнает, что вы добавите зависимость thenApply() в следующую строку? Как он мог знать, что вы не добавите другую зависимость через 2 часа?

Единственный способ узнать это - отследить самый последний момент до того, как начальный CompletionStage и все его зависимости будут собираться мусором, после чего невозможно будет добавить больше зависимостей.

Возможно, это можно реализовать, полагаясь на PhantomReferences или новый Cleaner API в Java 9, но вам, вероятно, следует делать это не на самом CompletionStage, а на результат, который он произвел - я полагаю, что вы действительно хотите очистить.

Действительно, кто-то мог сохранить ссылку на этот результат где-то еще, так что даже после выполнения всех зависимых этапов вы все еще не знаете, сможете ли вы выполнить очистку.

Обратите внимание, что может быть проще документировать ваш API, чтобы пользователи позаботились об очистке.

...