如果主机脱机,则重试java RestTemplate HTTP请求

Rob*_*ski 15 java spring resttemplate apache-httpclient-4.x

嗨,我正在使用spring RestTemplate调用REST API.API可能非常慢甚至脱机.我的应用程序是通过一个接一个地发送数千个请求来构建缓存.响应也可能非常慢,因为它们包含大量数据.

我已经将超时时间增加到120秒.我现在的问题是API可以脱机,我得到一个org.apache.http.conn.ConnectionPoolTimeoutException: Timeout waiting for connection from pool例外.

在API处于脱机状态的情况下,应用程序应等待并再次尝试,直到API再次联机.

我是否可以在RestTemplate开箱即用的情况下实现这一点而无需自己构建异常循环?

谢谢!

小智 11

我有同样的情况,做了一些谷歌搜索找到了解决方案.给予回答希望它能帮助别人.您可以为每次尝试设置最大尝试次数和时间间隔.

@Bean
  public RetryTemplate retryTemplate() {

    int maxAttempt = Integer.parseInt(env.getProperty("maxAttempt"));
    int retryTimeInterval = Integer.parseInt(env.getProperty("retryTimeInterval"));

    SimpleRetryPolicy retryPolicy = new SimpleRetryPolicy();
    retryPolicy.setMaxAttempts(maxAttempt);

    FixedBackOffPolicy backOffPolicy = new FixedBackOffPolicy();
    backOffPolicy.setBackOffPeriod(retryTimeInterval); // 1.5 seconds

    RetryTemplate template = new RetryTemplate();
    template.setRetryPolicy(retryPolicy);
    template.setBackOffPolicy(backOffPolicy);

    return template;
  }
Run Code Online (Sandbox Code Playgroud)

我想要执行的休息服务如下.

retryTemplate.execute(context -> {
        System.out.println("inside retry method");
        ResponseEntity<?> requestData = RestTemplateProvider.getInstance().postAsNewRequest(bundle, ServiceResponse.class, serivceURL,
                CommonUtils.getHeader("APP_Name"));

        _LOGGER.info("Response ..."+ requestData);
            throw new IllegalStateException("Something went wrong");
        });
Run Code Online (Sandbox Code Playgroud)


che*_*ffe 6

您还可以使用Spring Retry解决此注释驱动的问题。这样,您将避免实现模板。

将其添加到您的pom.xml

<dependency>
    <groupId>org.springframework.retry</groupId>
    <artifactId>spring-retry</artifactId>
    <version>1.1.2.RELEASE</version>
</dependency>
Run Code Online (Sandbox Code Playgroud)

为您的应用程序/配置启用它

@SpringBootApplication
@EnableRetry
public class MyApplication {
  //...
}
Run Code Online (Sandbox Code Playgroud)

保护可能会失败的方法 @Retryable

@Service
public class MyService {

  @Retryable(maxAttempts=5, value = RuntimeException.class, 
             backoff = @Backoff(delay = 15000, multiplier = 2))
  public List<String> doDangerousOperationWithExternalResource() {
     // ...
  }

}
Run Code Online (Sandbox Code Playgroud)