Оформлена ли функция возврата Retry threadsafe?
У меня есть класс, который отправляет сообщение на удаленный сервис, как показано ниже. Я использую resilience4j-retry, чтобы повторить сетевой вызов. Поскольку экземпляр retry является потокобезопасным в соответствии с документацией, я создаю его на уровне класса и повторно использую его.
public class RemoteMessageService {
Retry retry = Retry.of("RemoteMessageService", RetryConfig.custom()
.maxAttempts(5)
.retryExceptions(ProcessingException.class)
.intervalFunction(IntervalFunction.ofExponentialBackoff())
.build());
public void postMessageWithRetry(final String message){
Function<Integer, Void> postMessageFunction = Retry.decorateFunction(retry, this::postMessage);
try {
postMessageFunction.apply(message)
} catch (final ProcessingException e) {
LOG.warn("Got processing exception: {}", e.getMessage());
} catch (final Exception e) {
LOG.error("Got unknown exception: {}", e.getMessage());
}
}
private Void postMessage(final String message){
// Do a network call to send the message to a rest service
// throw ProcessingException in case of timeout
return null;
}
}
Мой вопрос, если декорированная функция возвращается Retry.decorateFunction(retry, this::postMessage);
также потокобезопасен?
В этом случае я мог бы переместить это на уровень класса вместо того, чтобы повторять это каждый раз, когда вызывается функция postMessageWithRetry.
1 ответ
После просмотра в resilience4j-retry
код, я обнаружил, что декорированная функция на самом деле является потокобезопасной; до тех пор, пока функция, которую мы украшаем, в первую очередь является поточно-ориентированной.
Так что я могу переписать код, как показано ниже postMessage
функция является поточно-ориентированной, и поэтому postMessageFunction
функция также поточно-ориентированная.
public class RemoteMessageService {
private final Retry retry = Retry.of("RemoteMessageService", RetryConfig.custom()
.maxAttempts(5)
.retryExceptions(ProcessingException.class)
.intervalFunction(IntervalFunction.ofExponentialBackoff())
.build());
private final Function<Integer, Void> postMessageFunction = Retry.decorateFunction(retry, this::postMessage);
public void postMessageWithRetry(final String message) {
try {
postMessageFunction.apply(message)
} catch (final ProcessingException e) {
LOG.warn("Got processing exception: {}", e.getMessage());
} catch (final Exception e) {
LOG.error("Got unknown exception: {}", e.getMessage());
}
}
private Void postMessage(final String message) {
// Do a network call to send the message to a rest service
// throw ProcessingException in case of timeout
return null;
}
}