You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Spring @Async方法已执行但仍阻塞,寻求解决方案

Spring @Async失效导致阻塞的解决办法

核心问题

你遇到的阻塞问题根源在于**@Async注解不能作用于静态方法**。Spring的异步功能依赖动态代理实现,静态方法不属于对象实例,Spring无法为其生成代理类,调用时还是会以同步方式执行,自然会阻塞请求。

具体修复步骤

  1. 移除静态修饰符
    把asyncTest方法改成非静态方法:
@Async
public void asyncTest() {
    System.out.println("* * * * * * ASYNC TEST 1");
    new BigInteger(9999, 5, new Random());
    System.out.println("* * * * * * ASYNC TEST 2");
}
  1. 让类被Spring管理
    在包含asyncTest方法的类上添加@Component(或@Service等)注解,确保Spring能创建它的代理对象:
@Component
public class AsyncTestService {
    @Async
    public void asyncTest() {
        // 原有逻辑
    }
}
  1. 通过依赖注入调用方法
    在接口控制器中,不要直接调用静态方法,而是注入Spring管理的AsyncTestService实例来调用异步方法:
@RestController
public class TestController {
    private final AsyncTestService asyncTestService;

    // 构造方法注入(Spring 1.5.x支持此方式)
    public TestController(AsyncTestService asyncTestService) {
        this.asyncTestService = asyncTestService;
    }

    @GetMapping("/trigger-async")
    public String triggerAsync() {
        asyncTestService.asyncTest();
        return "请求已接收,耗时任务将在后台异步执行";
    }
}
  1. 可选:自定义异步线程池
    如果默认线程池不满足需求,可在配置类中自定义TaskExecutor:
@Configuration
@EnableAsync
public class ApplicationConfiguration {
    @Bean
    public TaskExecutor asyncTaskExecutor() {
        ThreadPoolTaskExecutor executor = new ThreadPoolTaskExecutor();
        executor.setCorePoolSize(5); // 核心线程数
        executor.setMaxPoolSize(10); // 最大线程数
        executor.setQueueCapacity(20); // 队列容量
        executor.setThreadNamePrefix("Async-Worker-"); // 线程名称前缀
        executor.initialize();
        return executor;
    }
}

额外注意事项

  • 不要在同一个类内部直接调用@Async方法,这种调用会绕过Spring代理,依然是同步执行。如果需要内部调用,可通过Spring容器获取自身的代理对象,或者把异步逻辑抽离到单独的服务类中。
  • 确认Spring的组件扫描范围包含你的异步类和配置类,避免Spring无法发现这些类。

内容的提问来源于stack exchange,提问作者mazi

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.06 21:15:56