背景
动态线程池,指的是线程池中的参数可以动态修改并生效,比如corePoolSize、maximumPoolSize等。
在工作中,线程池的核心线程数和最大线程数等参数是很难估计和固定的,如果能在应用运行过程中动态进行调整,也就很有必要了。
前置条件
- 直接基于SpringBoot
- 支持Nacos配置中心配置
核心配置项
dtp:
enable: true
core-pool-size: 10
maximum-pool-size: 50
复制代码
我希望,能通过以上配置就能配置出一个动态线程池:
- dtp:表示dynamic thread pool,动态线程池的缩写
- enable:表示是否使用动态线程池,默认为true
- core-pool-size:表示dtp的核心线程数
- maximum-pool-size:表示dtp的最大线程数
- 对于线程池的其他参数,可以后续再扩展
另外,我希望能做到,只有项目的配置中存在dtp配置,并且enable不等于false,那就表示开启动态线程池,就需要向Spring容器中添加一个线程池对象作为一个Bean对象,这样其他Bean就能通过依赖注入来使用动态线程池了。
另外,对于上面的配置,我们最好是配置在nacos中,这样才能动态修改。
动手实现
首先创建两个项目:
- dtp-autoconfiguration:表示动态线程池的自动配置模块,会存放一些相关的自动配置类
- user:表示一个业务应用,会使用动态线程池
然后把user改写为一个SpringBoot应用:
引入依赖:
<dependencyManagement>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-dependencies</artifactId>
<version>2.3.12.RELEASE</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
</dependencies>
复制代码
新建启动类和Controller:
@SpringBootApplication
public class MyApplication {
public static void main(String[] args) {
SpringApplication.run(MyApplication.class, args);
}
}
复制代码
@RestController
public class ZhouyuController {
@GetMapping("/test")
public String test(){
return "hello";
}
}
复制代码
现在,我喜欢能在ZhouyuController中使用动态线程池,就像如下:
@RestController
public class ZhouyuController {
@Autowired
private ThreadPoolExecutor threadPoolExecutor; // 需要一个动态线程池
@GetMapping("/test")
public String test(){
threadPoolExecutor.execute(() -> {
System.out.println("执行任务");
});
return "hello";
}
}
复制代码
这段要能工作,得有几个条件:
- Spring容器中得有一个ThreadPoolExecutor类型的Bean
- 并且这个ThreadPoolExecutor对象还得是我们所说的动态线程池对象
定义DtpExecutor
这里就引出一个问题,我们到底该如何表示一个动态线程池,动态线程池和普通线程池的区别在于,动态线程池能支持通过nacos来修改其参数。
那我们是不是需要新