spring boot-执行Async任务时,使用自定义的线程池

来源:互联网 发布:网络麻将群主违法吗 编辑:程序博客网 时间:2024/05/21 05:38

在前面的博客中,http://blog.csdn.net/liuchuanhong1/article/details/54605697 我们使用了spring boot的异步操作,当时,我们使用的是默认的线程池,但是,如果我们想根据项目来定制自己的线程池了,下面就来说说,如何定制线程池!

一、增加配置属性类

package com.chhliu.springboot.async.configuration;import org.springframework.boot.context.properties.ConfigurationProperties;@ConfigurationProperties(prefix = "spring.task.pool") // 该注解的locations已经被启用,现在只要是在环境中,都会优先加载public class TaskThreadPoolConfig {private int corePoolSize;private int maxPoolSize;private int keepAliveSeconds;private int queueCapacity;…………省略getter,setter方法…………}
二、创建线程池

package com.chhliu.springboot.async.pool;import java.util.concurrent.Executor;import java.util.concurrent.ThreadPoolExecutor;import org.springframework.beans.factory.annotation.Autowired;import org.springframework.context.annotation.Bean;import org.springframework.context.annotation.Configuration;import org.springframework.scheduling.annotation.EnableAsync;import org.springframework.scheduling.concurrent.ThreadPoolTaskExecutor;import com.chhliu.springboot.async.configuration.TaskThreadPoolConfig;@Configuration@EnableAsyncpublic class TaskExecutePool {@Autowiredprivate TaskThreadPoolConfig config;@Beanpublic Executor myTaskAsyncPool() {ThreadPoolTaskExecutor executor = new ThreadPoolTaskExecutor();executor.setCorePoolSize(config.getCorePoolSize());executor.setMaxPoolSize(config.getMaxPoolSize());executor.setQueueCapacity(config.getQueueCapacity());executor.setKeepAliveSeconds(config.getKeepAliveSeconds());executor.setThreadNamePrefix("MyExecutor-");// rejection-policy:当pool已经达到max size的时候,如何处理新任务// CALLER_RUNS:不在新线程中执行任务,而是由调用者所在的线程来执行executor.setRejectedExecutionHandler(new ThreadPoolExecutor.CallerRunsPolicy());executor.initialize();return executor;}}
三、在主类中开启配置支持

package com.chhliu.springboot.async;import org.springframework.boot.SpringApplication;import org.springframework.boot.autoconfigure.SpringBootApplication;import org.springframework.boot.context.properties.EnableConfigurationProperties;import org.springframework.scheduling.annotation.EnableAsync;import com.chhliu.springboot.async.configuration.TaskThreadPoolConfig;@SpringBootApplication@EnableAsync@EnableConfigurationProperties({TaskThreadPoolConfig.class} ) // 开启配置属性支持public class SpringbootAsyncApplication {public static void main(String[] args) {SpringApplication.run(SpringbootAsyncApplication.class, args);}}
四、测试类

package com.chhliu.springboot.async.pool;import org.slf4j.Logger;import org.slf4j.LoggerFactory;import org.springframework.scheduling.annotation.Async;import org.springframework.stereotype.Component;@Component  public class AsyncTask {    protected final Logger logger = LoggerFactory.getLogger(this.getClass());            @Async("myTaskAsyncPool")  //myTaskAsynPool即配置线程池的方法名,此处如果不写自定义线程池的方法名,会使用默认的线程池    public void doTask1(int i) throws InterruptedException{          logger.info("Task"+i+" started.");      }  }  
五、测试

package com.chhliu.springboot.async;import java.util.concurrent.ExecutionException;import org.junit.Test;import org.junit.runner.RunWith;import org.slf4j.Logger;import org.slf4j.LoggerFactory;import org.springframework.beans.factory.annotation.Autowired;import org.springframework.boot.test.context.SpringBootTest;import org.springframework.test.context.junit4.SpringRunner;import com.chhliu.springboot.async.pool.AsyncTask;@RunWith(SpringRunner.class)@SpringBootTestpublic class SpringbootAsyncApplicationTests {protected final Logger logger = LoggerFactory.getLogger(this.getClass());@Autowiredprivate AsyncTask asyncTask;@Testpublic void AsyncTaskTest() throws InterruptedException, ExecutionException {for (int i = 0; i < 100; i++) {asyncTask.doTask1(i);}logger.info("All tasks finished.");}}
测试结果如下:

2017-03-20 20:15:15.208  INFO 4068 --- [  MyExecutor-10] c.c.springboot.async.pool.AsyncTask      : Task60 started.2017-03-20 20:15:15.208  INFO 4068 --- [  MyExecutor-25] c.c.springboot.async.pool.AsyncTask      : Task61 started.2017-03-20 20:15:15.208  INFO 4068 --- [   MyExecutor-6] c.c.springboot.async.pool.AsyncTask      : Task62 started.2017-03-20 20:15:15.208  INFO 4068 --- [  MyExecutor-23] c.c.springboot.async.pool.AsyncTask      : Task63 started.2017-03-20 20:15:15.208  INFO 4068 --- [  MyExecutor-20] c.c.springboot.async.pool.AsyncTask      : Task64 started.2017-03-20 20:15:15.208  INFO 4068 --- [  MyExecutor-19] c.c.springboot.async.pool.AsyncTask      : Task65 started.2017-03-20 20:15:15.208  INFO 4068 --- [  MyExecutor-16] c.c.springboot.async.pool.AsyncTask      : Task66 started.2017-03-20 20:15:15.208  INFO 4068 --- [  MyExecutor-15] c.c.springboot.async.pool.AsyncTask      : Task67 started.2017-03-20 20:15:15.208  INFO 4068 --- [  MyExecutor-12] c.c.springboot.async.pool.AsyncTask      : Task68 started.2017-03-20 20:15:15.209  INFO 4068 --- [   MyExecutor-1] c.c.springboot.async.pool.AsyncTask      : Task69 started.2017-03-20 20:15:15.209  INFO 4068 --- [  MyExecutor-11] c.c.springboot.async.pool.AsyncTask      : Task81 started.2017-03-20 20:15:15.209  INFO 4068 --- [   MyExecutor-8] c.c.springboot.async.pool.AsyncTask      : Task82 started.2017-03-20 20:15:15.209  INFO 4068 --- [   MyExecutor-7] c.c.springboot.async.pool.AsyncTask      : Task83 started.2017-03-20 20:15:15.209  INFO 4068 --- [   MyExecutor-4] c.c.springboot.async.pool.AsyncTask      : Task84 started.2017-03-20 20:15:15.209  INFO 4068 --- [  MyExecutor-29] c.c.springboot.async.pool.AsyncTask      : Task85 started.2017-03-20 20:15:15.209  INFO 4068 --- [  MyExecutor-21] c.c.springboot.async.pool.AsyncTask      : Task86 started.2017-03-20 20:15:15.209  INFO 4068 --- [  MyExecutor-17] c.c.springboot.async.pool.AsyncTask      : Task88 started.

测试结果ok!

六、配置默认的线程池

如果我们想使用默认的线程池,但是只是想修改默认线程池的配置,那怎么做了,此时我们需要实现AsyncConfigurer类,示例代码如下:

import java.lang.reflect.Method;import java.util.concurrent.Executor;import java.util.concurrent.ThreadPoolExecutor;import org.springframework.aop.interceptor.AsyncUncaughtExceptionHandler;import org.springframework.beans.factory.annotation.Autowired;import org.springframework.context.annotation.Configuration;import org.springframework.scheduling.annotation.AsyncConfigurer;import org.springframework.scheduling.concurrent.ThreadPoolTaskExecutor;import com.chhliu.cq.emailservice.threadconfiguration.TaskThreadPoolConfig;import lombok.extern.slf4j.Slf4j;  /** * 注意:该线程池被所有的异步任务共享,而不属于某一个异步任务 * 描述:配置异步任务的线程池 * @author chhliu * 创建时间:2017年5月22日 上午10:20:56 * @version 1.2.0 */@Slf4j@Configurationpublic class AsyncTaskExecutePool implements AsyncConfigurer{        @Autowired      private TaskThreadPoolConfig config;  // 配置属性类,见上面的代码  @Overridepublic Executor getAsyncExecutor() {ThreadPoolTaskExecutor executor = new ThreadPoolTaskExecutor();        executor.setCorePoolSize(config.getCorePoolSize());          executor.setMaxPoolSize(config.getMaxPoolSize());          executor.setQueueCapacity(config.getQueueCapacity());          executor.setKeepAliveSeconds(config.getKeepAliveSeconds());          executor.setThreadNamePrefix("taskExecutor-");            // rejection-policy:当pool已经达到max size的时候,如何处理新任务          // CALLER_RUNS:不在新线程中执行任务,而是由调用者所在的线程来执行          executor.setRejectedExecutionHandler(new ThreadPoolExecutor.CallerRunsPolicy());        executor.initialize();          return executor;  }@Overridepublic AsyncUncaughtExceptionHandler getAsyncUncaughtExceptionHandler() {// 异步任务中异常处理return new AsyncUncaughtExceptionHandler() {@Overridepublic void handleUncaughtException(Throwable arg0, Method arg1, Object... arg2) {log.error("=========================="+arg0.getMessage()+"=======================", arg0);log.error("exception method:"+arg1.getName());}};}  }
使用的时候,只需在方法上加上@Async即可。
4 0
原创粉丝点击
热门问题 老师的惩罚 人脸识别 我在镇武司摸鱼那些年 重生之率土为王 我在大康的咸鱼生活 盘龙之生命进化 天生仙种 凡人之先天五行 春回大明朝 姑娘不必设防,我是瞎子 孕妇睡眠质量差怎么办吃什么 39周2天了还不生怎么办 孕中期体重猛长怎么办 4个半月胎位不正怎么办 41周不产生宫缩怎么办 生完孩子胎盘没有脱落怎么办 39周还是臀位怎么办 怀孕7个月胎位不正怎么办 怀孕六个多月胎位不正怎么办 怀孕七个月了胎位不正怎么办 怀孕七个月胎位不正怎么办 怀孕肚子上有妊娠纹怎么办 怀孕九个月肚子长痱子怎么办 怀孕前体重偏胖怎么办 怀孕打胰岛素血糖控制不好怎么办 孕后期憋的难受怎么办 怀孕6个月不想生怎么办 孕六个月不想要怎么办 怀孕9个月喝酒了怎么办 怀孕8个月喝醉了怎么办 怀孕6个月胃酸烧心怎么办 怀孕7个月胃酸怎么办 怀孕5个月胃酸怎么办 怀孕2个月胃酸怎么办 怀孕六个月胃酸烧心怎么办 孕六个月反胃酸怎么办 怀孕三个月胃酸吐酸水怎么办 孕六个月胃难受怎么办 孕6个月胃酸厉害怎么办 孕妇6个月胃酸怎么办 孕早期胎盘早剥怎么办 孕妇晕车怎么办最有效方法 怀孕了受凉胃疼怎么办 怀孕4个月胎位低怎么办 6个月胎位低怎么办 7个多月了胎位低怎么办 瑜伽按摩球破了怎么办 孕妇吐完胸口疼怎么办 孕25周胸口堵怎么办呢 孕期没做过产检怎么办 宝宝的泪囊堵塞怎么办