Leitfaden für Spring Retry
1. Überblick
Spring Retry bietet die Möglichkeit, einen fehlgeschlagenen Vorgang automatisch erneut aufzurufen. Dies ist hilfreich, wenn die Fehler vorübergehender Natur sein können (wie ein vorübergehender Netzwerkfehler). Spring Retry bietet eine deklarative Steuerung des prozess- und richtlinienbasierten Verhaltens, die einfach erweitert und angepasst werden kann.
In diesem Artikel erfahren Sie, wie SieSpring Retry verwenden, um Wiederholungslogik in Spring-Anwendungen zu implementieren. Wir konfigurieren die Listener auch so, dass sie zusätzliche Rückrufe erhalten.
2. Maven-Abhängigkeiten
Beginnen wir mit dem Hinzufügen der Abhängigkeit zu unserenpom.xml:
org.springframework.retry
spring-retry
1.1.5.RELEASE
Wir können die neueste Version vonspring-retry inMaven Central überprüfen.
Wir müssen auch Spring AOP in unserer pom.xml hinzufügen:
org.springframework
spring-aspects
3. Aktivieren von Spring Retry
Um Spring Retry in einer Anwendung zu aktivieren, müssen wir die Annotation@EnableRetryzu unserer Klasse@Configurationhinzufügen:
@Configuration
@EnableRetry
public class AppConfig { ... }
4. Wiederholen Sie den Vorgang mit Anmerkungen
Mithilfe von Annotationen können Sie einen Methodenaufruf ausführen, der bei einem Fehler wiederholt werden soll.
4.1. @Retryable
Um Methoden Wiederholungsfunktionen hinzuzufügen, können@Retryable verwendet werden:
@Service
public interface MyService {
@Retryable(
value = { SQLException.class },
maxAttempts = 2,
backoff = @Backoff(delay = 5000))
void retryService(String sql) throws SQLException;
...
}
Hier wird das Wiederholungsverhalten mithilfe der Attribute@Retryable. angepasst. In diesem Beispiel wird ein erneuter Versuch nur versucht, wenn die MethodeSQLException. auslöst. Es gibt bis zu 2 Wiederholungsversuche und eine Verzögerung von 5000 Millisekunden.
Wenn@Retryable ohne Attribute verwendet wird und die Methode mit einer Ausnahme fehlschlägt, wird ein erneuter Versuch bis zu dreimal mit einer Verzögerung von einer Sekunde versucht.
4.2. @Recover
Die Annotation@Recover wird verwendet, um eine separate Wiederherstellungsmethode zu definieren, wenn eine Methode@Retryablemit einer angegebenen Ausnahme fehlschlägt:
@Service
public interface MyService {
...
@Recover
void recover(SQLException e, String sql);
}
Wenn also dieretryService()-Methode eineSQLException auslöst, wird dierecover()-Methode aufgerufen. Ein geeigneter Wiederherstellungshandler hat seinen ersten Parameter vom TypThrowable (optional). S Nachfolgende Argumente werden aus der Argumentliste der fehlgeschlagenen Methode in derselben Reihenfolge wie die fehlgeschlagene Methode und mit demselben Rückgabetyp ausgefüllt.
5. RetryTemplate
5.1 RetryOperations
Spring Retry bietet die Schnittstelle vonRetryOperations, die eine Reihe von Methoden vonexecute()bereitstellt:
public interface RetryOperations {
T execute(RetryCallback retryCallback) throws Exception;
...
}
DasRetryCallback, das ein Parameter desexecute() ist, ist eine Schnittstelle, die das Einfügen von Geschäftslogik ermöglicht, die bei einem Fehler wiederholt werden muss:
public interface RetryCallback {
T doWithRetry(RetryContext context) throws Throwable;
}
5.2. RetryTemplate Konfiguration
DasRetryTemplate ist eine Implementierung desRetryOperations. Konfigurieren wir eineRetryTemplate-Bean in unserer@Configuration-Klasse:
@Configuration
public class AppConfig {
//...
@Bean
public RetryTemplate retryTemplate() {
RetryTemplate retryTemplate = new RetryTemplate();
FixedBackOffPolicy fixedBackOffPolicy = new FixedBackOffPolicy();
fixedBackOffPolicy.setBackOffPeriod(2000l);
retryTemplate.setBackOffPolicy(fixedBackOffPolicy);
SimpleRetryPolicy retryPolicy = new SimpleRetryPolicy();
retryPolicy.setMaxAttempts(2);
retryTemplate.setRetryPolicy(retryPolicy);
return retryTemplate;
}
}
RetryPolicy bestimmt, wann eine Operation wiederholt werden soll. EinSimpleRetryPolicy wird verwendet, um eine feste Anzahl von Malen erneut zu versuchen.
BackOffPolicy wird verwendet, um das Zurücksetzen zwischen Wiederholungsversuchen zu steuern. AFixedBackOffPolicy pausiert für einen festgelegten Zeitraum, bevor es fortgesetzt wird.
5.3. Verwenden SieRetryTemplate
Um Code mit Wiederholungsbehandlung auszuführen, rufen wir retryTemplate.execute() auf: __
retryTemplate.execute(new RetryCallback() {
@Override
public Void doWithRetry(RetryContext arg0) {
myService.templateRetryService();
...
}
});
Dasselbe könnte mit einem Lambda-Ausdruck anstelle einer anonymen Klasse erreicht werden: __
retryTemplate.execute(arg0 -> {
myService.templateRetryService();
return null;
});
6. XML-Konfiguration
Spring Retry kann per XML mit dem Spring AOP-Namespace konfiguriert werden.
6.1. XML-Datei hinzufügen
Fügen Sie im Klassenpfadretryadvice.xml hinzu:
...
...
In diesem Beispiel wird ein benutzerdefiniertesRetryTemplate innerhalb des Interceptors derxmlRetryService-Methode verwendet.
6.2. Verwenden der XML-Konfiguration
Importieren Sieretryadvice.xml ausclasspath und aktivieren Sie die Unterstützung von@AspectJ:
@Configuration
@EnableRetry
@EnableAspectJAutoProxy
@ImportResource("classpath:/retryadvice.xml")
public class AppConfig { ... }
7. Zuhörer
Listener bieten zusätzliche Rückrufe bei erneuten Versuchen. Sie können für verschiedene Querschnittsthemen in verschiedenen Wiederholungsversuchen verwendet werden.
7.1. Rückrufe hinzufügen
Die Rückrufe werden in einerRetryListener-Schnittstelle bereitgestellt:
public class DefaultListenerSupport extends RetryListenerSupport {
@Override
public void close(RetryContext context,
RetryCallback callback, Throwable throwable) {
logger.info("onClose);
...
super.close(context, callback, throwable);
}
@Override
public void onError(RetryContext context,
RetryCallback callback, Throwable throwable) {
logger.info("onError");
...
super.onError(context, callback, throwable);
}
@Override
public boolean open(RetryContext context,
RetryCallback callback) {
logger.info("onOpen);
...
return super.open(context, callback);
}
}
Die Rückrufeopen undclosekommen vor und nach dem gesamten Wiederholungsversuch, undonError gilt für die einzelnenRetryCallback-Rückrufe.
7.2. Registrieren des Listeners
Als nächstes registrieren wir unsere Listener (DefaultListenerSupport) für unsereRetryTemplate Bean:
@Configuration
public class AppConfig {
...
@Bean
public RetryTemplate retryTemplate() {
RetryTemplate retryTemplate = new RetryTemplate();
...
retryTemplate.registerListener(new DefaultListenerSupport());
return retryTemplate;
}
}
8. Ergebnisse testen
Überprüfen wir die Ergebnisse:
@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration(
classes = AppConfig.class,
loader = AnnotationConfigContextLoader.class)
public class SpringRetryTest {
@Autowired
private MyService myService;
@Autowired
private RetryTemplate retryTemplate;
@Test(expected = RuntimeException.class)
public void givenTemplateRetryService_whenCallWithException_thenRetry() {
retryTemplate.execute(arg0 -> {
myService.templateRetryService();
return null;
});
}
}
Wenn wir den Testfall ausführen, bedeutet der folgende Protokolltext, dass wirRetryTemplate und Listener erfolgreich konfiguriert haben:
2017-01-09 20:04:10 [main] INFO o.b.s.DefaultListenerSupport - onOpen
2017-01-09 20:04:10 [main] INFO o.example.springretry.MyServiceImpl
- throw RuntimeException in method templateRetryService()
2017-01-09 20:04:10 [main] INFO o.b.s.DefaultListenerSupport - onError
2017-01-09 20:04:12 [main] INFO o.example.springretry.MyServiceImpl
- throw RuntimeException in method templateRetryService()
2017-01-09 20:04:12 [main] INFO o.b.s.DefaultListenerSupport - onError
2017-01-09 20:04:12 [main] INFO o.b.s.DefaultListenerSupport - onClose
9. Fazit
In diesem Artikel haben wir Spring Retry vorgestellt. Wir haben Beispiele für Wiederholungsversuche mit Anmerkungen undRetryTemplate gesehen. Wir haben dann zusätzliche Rückrufe mit Listenern konfiguriert.
Sie finden den Quellcode für diesen Artikelover on GitHub.