对单个作业使用threadpooltaskexecutor

holgip5t  于 2021-07-14  发布在  Java
关注(0)|答案(1)|浏览(342)

我加入了公司的一个新团队,我看到他们广泛使用“threadpooltaskexecutor”。它基本上是一个前端的后端rest应用程序,它调用其他soap API并将结果返回给客户机—只是一个传递。99%的情况下,每个rest端点只调用一个soap api,并将json格式的响应返回给客户端。不过,尽管这只是一个soap调用,但它们使用“threadpooltaskexecutor”并调用.get()阻塞方法。
@configuration class上的threadpooltaskexecutor@bean:

@Bean(name=“soapAsyncExecutor")
@Qualifier("soapAsyncExecutor")
   public ThreadPoolTaskExecutor getSoapAsyncExecutor() {
    final ThreadPoolTaskExecutor executor = new ThreadPoolTaskExecutor();
    final ThreadFactory customThreadfactory = new ThreadFactoryBuilder()
        .setNameFormat(“SoapExecutor-%d")
        .setUncaughtExceptionHandler(uncaughtExceptionHandler())
        .setDaemon(true)
        .build();
    executor.setRejectedExecutionHandler(new ThreadPoolExecutor.CallerRunsPolicy());
    executor.setCorePoolSize(80);
    executor.setMaxPoolSize(200);
    executor.setQueueCapacity(80);
    executor.setKeepAliveSeconds(60);
    executor.setAllowCoreThreadTimeOut(true);
    executor.setThreadFactory(customThreadfactory);
    executor.afterPropertiesSet();
    return executor;
   }

@service上的代码:

@Async("soapAsyncExecutor")
@Override
public Future<OrderInfo> getOrderInfoAsync(final String orderId) {
    return new AsyncResult<OrderInfo>(this.getOrderInfo(orderId);
}

private OrderInfo getOrderInfo(final String orderId) {
    // return result from SOAP call which typically take 1 second
}

然后从上面的@restcontroller异步方法调用如下:

@GetMapping(value = "/order/{orderId}")
public OrderInfo getOrderInfo(@PathVariable("orderId") final String orderId) {
   OrderInfo orderInfo = orderService.getOrderInfoAsync(orderId).get();
   return orderInfo;
}

据我所知,spring中对rest端点的每个请求都会产生一个新线程(因为我没有更好的词,所以我们称之为主线程)。在那里调用“.get()”方法会阻塞主线程。我的问题是,在这个封锁期,
官方的主线是什么状态——“封锁”还是“等待”?如果被阻塞了,那么对单个作业使用这样的“threadpooltaskexecutor”是否有一点好处,因为它会阻塞主线程?
是否可以通过任何方式调整此代码以带来好处,或者在restcontroller端点中对这样的单个作业使用异步编程是没有意义的?

vwkv1x7d

vwkv1x7d1#

官方的主线是什么状态——“封锁”还是“等待”?
此 路 不通。
如果被阻塞了,那么对单个作业使用这样的“threadpooltaskexecutor”是否有一点好处,因为它会阻塞主线程?
不。没有。事实上,我打赌将任务分派到线程池会带来额外的开销。不过,如果端点要等待多个任务完成,这是有意义的。
是否可以通过任何方式调整此代码以带来好处,或者在restcontroller端点中对这样的单个作业使用异步编程是没有意义的?
当然。下面是一个例子。这是另一个。基本上,在您的场景中,只要返回 CompletableFuture 而不是打电话 .get() .

相关问题