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

时间:2015-09-02 11:55:38

标签: java spring apache-httpclient-4.x resttemplate

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

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

如果API处于脱机状态,应用程序应等待并再次尝试,直到API再次联机。

我是否可以在RestTemplate开箱即可实现此功能,而无需自行构建异常循环?

谢谢!

3 个答案:

答案 0 :(得分:8)

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

@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;
  }

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

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");
        });

答案 1 :(得分:6)

使用Spring Retry项目(https://dzone.com/articles/spring-retry-ways-integratehttps://github.com/spring-projects/spring-retry)。

它旨在解决像你这样的问题。

答案 2 :(得分:3)

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

将其添加到您的pom.xml

<dependency>
    <groupId>org.springframework.retry</groupId>
    <artifactId>spring-retry</artifactId>
    <version>1.1.2.RELEASE</version>
</dependency>

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

@SpringBootApplication
@EnableRetry
public class MyApplication {
  //...
}

使用@Retryable

可能会失败的保护方法
@Service
public class MyService {

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

}