近期,需要对之前的接口进行优化,缩短接口的响应时间,但是springcloud中的feign是不支持传递异步化的回调结果的,因此有了以下的解决方案,记录一下,仅供参考。
一、背景
对于一个页面上的所有实例有一个查询权限的接口,同时有四个操作类型的需要查询且接口仅支持单个实例单个操作类型操作。简单来说,假设实例查询退订权限需要1秒钟,那么四个操作共需4秒钟,一共20个实例的话,那么实际所需时间为80秒。这样显然是不符合要求的。经过本文的优化后,可以达到20秒。
二、设计方案
需要指出,由于各种限制原因,无法直接在工程中进行rest接口的调用,否则是直接可以@Async异步调用的。
(一)使用框架
产品工程使用SpringCloud微服务,同时通过Feign调用权限的微服务,服务都是使用SpringBoot实现。
(二)实现方案
由于Feign的特殊性,目前并不支持异步返回Future,直接通过Future是会报错的。因此可以在权限微服务中异步执行查询操作权限,同时再异步起一个线程去等待所有的异步结果,这一个线程是阻塞的,同时由阻塞得到的最终结果,封装成自己想要的返回体,返回给调用方即可,这样相当于大致只需要等待一个实例的操作时间即可。
三、示例代码
项目代码我就不放上来了,我将写一个Demo作为示例,基本的思想都在里面了。
(一)被调用方
1. 配置异步化及异步线程池 - AsyncConfig类
@Configuration
@EnableAsync
public class AsyncConfig implements AsyncConfigurer {
@Bean("taskPoolExecutor")
public Executor taskPoolExecutor() {
ThreadPoolTaskExecutor executor = new ThreadPoolTaskExecutor();
executor.setCorePoolSize(20);
executor.setMaxPoolSize(30);
executor.setQueueCapacity(200);
executor.setKeepAliveSeconds(60);
executor.setThreadNamePrefix("taskPoolExecutor-");
executor.setRejectedExecutionHandler(new ThreadPoolExecutor.CallerRunsPolicy());
return executor;
}
@Override
public AsyncUncaughtExceptionHandler getAsyncUncaughtExceptionHandler() {
return new SimpleAsyncUncaughtExceptionHand