spring boot 自定义线程池与使用
一、进行线程池创建
import cn.hutool.core.thread.ThreadFactoryBuilder; import lombok.extern.slf4j.Slf4j; import org.springframework.aop.interceptor.AsyncUncaughtExceptionHandler; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import org.springframework.scheduling.annotation.AsyncConfigurerSupport; import org.springframework.scheduling.annotation.EnableAsync; import org.springframework.scheduling.concurrent.ThreadPoolTaskScheduler; import java.lang.reflect.Method; import java.util.concurrent.Executor; /** * 线程池配置(异步线程) */ @Slf4j
@Configuration
@EnableAsync public class ThreadPoolTaskSchedulerConfig extends AsyncConfigurerSupport {
@Bean( "threadPoolTaskScheduler" ) public ThreadPoolTaskScheduler threadPoolTaskScheduler() { // 这里使用的为定时任务线程池,替代@Scheduled注解,进行动态定时任务配置 ThreadPoolTaskScheduler scheduler = new ThreadPoolTaskScheduler();
scheduler.setThreadFactory(ThreadFactoryBuilder.create().build());
scheduler.setPoolSize( 60 );
scheduler.setRemoveOnCancelPolicy( true );
scheduler.setThreadNamePrefix( "TASK-SCHEDULE-" );
scheduler.initialize(); return scheduler;
}
@Override public Executor getAsyncExecutor() { return threadPoolTaskScheduler();
}
@Override public AsyncUncaughtExceptionHandler getAsyncUncaughtExceptionHandler() { return (Throwable t, Method m, Object... args) -> {
log.error( "=============================" + t.getMessage() + "==============================" );
log.error( "threadPoolTaskScheduler exception Method:" + m.getName());
};
}
}
二、创建bean操作对象 提供根据beanName获取,手动注入bean等方法,适用于不被spring管理的类中(thread、callback)
import org.springframework.beans.BeansException; import org.springframework.beans.factory.config.BeanFactoryPostProcessor; import org.springframework.beans.factory.config.ConfigurableListableBeanFactory; import org.springframework.beans.factory.support.DefaultListableBeanFactory; import org.springframework.context.ApplicationContext; import org.springframework.context.ApplicationContextAware; import org.springframework.context.ConfigurableApplicationContext; import org.springframework.stereotype.Component; /** * @author lu_wanli
* */ @Component public class SpringHelper implements BeanFactoryPostProcessor, ApplicationContextAware { private static ConfigurableListableBeanFactory beanFactory; /** * 获取 Spring Bean工厂
*
* @return beanFactory */ public static ConfigurableListableBeanFactory getBeanFactory() { return beanFactory;
}
@Override public void postProcessBeanFactory(ConfigurableListableBeanFactory beanFactory) throws BeansException {
SpringHelper.beanFactory = beanFactory;
} /** * 获取指定name的bean */ @SuppressWarnings( "unchecked" ) public static <T> T getBean(String name) throws BeansException { return (T) beanFactory.getBean(name);
} /** * 获取指定type的Bean */ public static <T> T getBean(Class<T> clz) throws BeansException { return beanFactory.getBean(clz);
} /** * 包含Bean
*
* @param name beanClassName
* @return true/false */ public static boolean containsBean(String name) { return beanFactory.containsBean(name);
} /** * 判断以给定名字注册的bean定义是一个singleton还是一个prototype。 如果与给定名字相应的bean定义没有被找到,将会抛出一个异常(NoSuchBeanDefinitionException)
*
* @param name beanName
* @return boolean */ public static boolean isSingleton(String name) { return beanFactory.isSingleton(name);
} private static ApplicationContext applicationContext;
@Override public void setApplicationContext(ApplicationContext applicationContext) throws BeansException {
SpringHelper.applicationContext = applicationContext;
} /** * 动态注入单例bean实例
*
* @param beanName bean名称
* @param singletonObject 单例bean实例
* @return 注入实例 */ public static Object registerSingletonBean(String beanName, Object singletonObject) { // 将applicationContext转换为ConfigurableApplicationContext ConfigurableApplicationContext configurableApplicationContext = (ConfigurableApplicationContext) applicationContext; // 获取BeanFactory DefaultListableBeanFactory defaultListableBeanFactory = (DefaultListableBeanFactory) configurableApplicationContext.getAutowireCapableBeanFactory(); // 动态注册bean. defaultListableBeanFactory.registerSingleton(beanName, singletonObject); // 获取动态注册的bean. return configurableApplicationContext.getBean(beanName);
}
}
三、创建异步线程的管理类
import org.springframework.scheduling.concurrent.ThreadPoolTaskExecutor; /** * 异步任务管理器
* */ public class AsyncManager { /** * 异步操作任务调度线程池 */ private final ThreadPoolTaskExecutor taskExecutor = SpringHelper.getBean("threadPoolTaskExecutor" ); /** * 单例模式 */ private AsyncManager() {
} private static final AsyncManager ME = new AsyncManager(); public static AsyncManager me() { return ME;
} /** * 执行任务
*
* @param task 任务 */ public void execute(Runnable task){
taskExecutor.execute(task);
} /** * 停止线程池 */ public void shutdown() {
taskExecutor.shutdown();
}
}
四、在项目关闭时关闭相关线程池资源
import org.slf4j.Logger; import org.slf4j.LoggerFactory; import org.springframework.stereotype.Component; import javax.annotation.PreDestroy; /** * 关闭线程池资源 */ @Component public class ShutDownManager { private static final Logger logger = LoggerFactory.getLogger(ShutDownManager. class );
@PreDestroy public void destory() {
shutdownAsyncManager();
} private void shutdownAsyncManager() { try {
logger.info( "========关闭任务池==========" );
AsyncManager.me().shutdown();
} catch (Exception e) {
logger.error(e.getMessage(), e);
}
}
}