Spring可Bean化线程池

# 配置

1.yaml文件中配置线程池的基本参数

spring:
  thread:
    pool:
      core-size: 5
      max-size: 10
      queue-capacity: 100
      keep-alive-seconds: 1000
1
2
3
4
5
6
7

#

  1. 配置类(spring会自动转换-为驼峰格式)
@ConfigurationProperties(prefix = "spring.thread.pool")
@Configuration
@Data
public class PoolConfig {

    private int coreSize;

    private int maxSize;

    private int queueCapacity;

    private int keepAliveSeconds;
}
1
2
3
4
5
6
7
8
9
10
11
12
13
  1. 配置线程池(1. 注意必须开启@EnableAsync异步注解 2.bean名称作为开启异步注解)
@Configuration
@EnableAsync
public class AsyncConfiguration implements AsyncConfigurer {

    private static final Logger logger = LoggerFactory.getLogger(AsyncConfiguration.class);
    @Resource
    PoolConfig config;

    @Bean("threadPoolTaskExecutor")
    public ThreadPoolTaskExecutor threadPoolTaskExecutor() {
        ThreadPoolTaskExecutor executor = new ThreadPoolTaskExecutor();
        executor.setCorePoolSize(config.getCorePoolSize());
        executor.setMaxPoolSize(config.getMaxPoolSize());
        executor.setKeepAliveSeconds(config.getKeepAliveSeconds);
        executor.setQueueCapacity(config.getQueueCapacity());
        executor.setRejectedExecutionHandler(new ThreadPoolExecutor.CallerRunsPolicy());
        executor.setThreadGroupName("线程组...");
        executor.setThreadNamePrefix("线程...");
        executor.initialize();
        return executor;
    }

    @Override
    public Executor getAsyncExecutor() {
        return threadPoolTaskExecutor();
    }

    @Override
    public AsyncUncaughtExceptionHandler getAsyncUncaughtExceptionHandler() {
        return (ex, method, params) -> logger.error(String.format("执行异步任务'%s'", method), ex);
    }
}    
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
  1. service中使用(注意方法嵌套导致失效问题)
@Service
public class TestService{
    //注解中的value默认是实现Spring的executor,也可以指定自定义的executor
    @Async(value = "threadPoolTaskExecutor")
    public void c() {
        log.info("c方法开始执行");
    }
}
1
2
3
4
5
6
7
8
  1. 在controller中注入service调用方法c即可,console中日志显示开启子线程。

# 监控

 @Async(value = "threadPoolTaskExecutor")
    public void c() {
        final ThreadPoolTaskExecutor executor = (ThreadPoolTaskExecutor)asyncConfiguration.getAsyncExecutor();
        log.info("c方法开始结束");
        log.info("线程池活跃线程数量={},总任务数量={},已完成数量={},现存任务队列大小={}",
                executor.getActiveCount(),executor.getPoolSize(),executor.getThreadPoolExecutor().getCompletedTaskCount(),executor.getThreadPoolExecutor().getQueue().size());
 }
1
2
3
4
5
6
7

以上就是使用Spring提供线程池的使用的方法,总结备忘.