为多个API调用配置spring boot retry

时间:2016-11-21 10:39:39

标签: java spring performance spring-boot spring-retry

我有一个spring boot api应用程序,它有一个POST端点,让我们把它称为/ doSomething作为方法。当收到/ doSomething端点的请求时   我需要将这些数据保存在我们的应用程序中,然后需要对另一个api [A]进行GET请求,该请求必须从API [B]获取,然后再次发布到API [B]。在这种情况下,什么是处理弹簧重试的最佳方法。

请找到以下代码

@RequestMapping(value = "/subpub", method = RequestMethod.POST, headers = {"content-type=application/x-www-form-urlencoded"})
    public String subPub(HttpServletRequest request, HttpServletResponse response, @RequestBody String rawBody) {
    //persists some data on this database

    //this method will invoke api[A] and api[B]
    integrationServiceBean.processCourseMetaData("_id");
    return "OK"
}; 

IntegrationServiceBean类

package com.pearson.reader.integration;

@Service
public class IntegrationServiceBean {


    /**
     * This method will process meta data submission for registrar api by invoking authentication service, receive
     * section details by section id and update meta data
     *
     * @param sectionId
     */
    @Retryable(RuntimeException.class)
    public void processCourseMetaData(final String sectionId) {

        System.out.println("Invoking processCourseMetaData");

        ResponseEntity<String> responseEntity = registrarService.findOneSection(sectionId);
        String responseBody = responseEntity.getBody();

        LinkedHashMap requestObj = (LinkedHashMap) JsonUtils.jsonToObject(responseBody);
        LinkedHashMap metaDataObj = (LinkedHashMap) requestObj.get(Constant.Response.META_DATA);
        if (!contextConfig.getMetaDataCopyable().isEmpty()) {

            metaDataObj.put(Constant.MetaData.COPYABLE, contextConfig.getMetaDataCopyable());
        }
        if (!contextConfig.getMetaDataPending().isEmpty()) {

            metaDataObj.put(Constant.MetaData.PENDING, contextConfig.getMetaDataPending());
        }
        metaDataObj.put(Constant.MetaData.LAUNCH_URL, getLaunchUrlByEnvironment(requestObj, sectionId));

        String updatedSectionPayload = JsonUtils.toJsonString(requestObj);

        registrarService.updateSection(sectionId, updatedSectionPayload);
    }

    @Recover
    public void recover(RuntimeException e){
        System.out.println("Recovering - returning safe value"+e.getMessage());

    }



}

我的问题是,如果对集成服务bean应用了重试,那么对于主要端点上的保存数据,它将对应用程序的主要部分产生性能影响。

什么是最佳实践

1 个答案:

答案 0 :(得分:1)

通过阻塞当前正在执行的线程,在分离的线程中调用方法@Retryable

根据您的代码预期,

在线程(比如线程A)中进行保存,并且正在其他线程(比如线程B)中处理Integration服务。因此,线程A被阻塞直到B完成。因此integrationServiceBean.processCourseMetaData("_id");的下一行被阻止,直到成功或耗尽重试限制为止。

来到你​​的问题。

保存数据不受​​影响。所以我不认为,有任何表现受到打击。

谈论最佳做法

使用重试,只要服务之间存在网络分区,就是一种很好的做法。 它使应用程序健壮。