Spring Boot-异步线程池的使用

定义一个配置类,实现AsyncConfigurer接口,如下:

import org.springframework.aop.interceptor.AsyncUncaughtExceptionHandler;
import org.springframework.context.annotation.Configuration;
import org.springframework.scheduling.annotation.AsyncConfigurer;
import org.springframework.scheduling.annotation.EnableAsync;
import org.springframework.scheduling.concurrent.ThreadPoolTaskExecutor;
import java.util.concurrent.Executor;
import java.util.concurrent.ThreadFactory;
import java.util.concurrent.atomic.AtomicInteger;

@Configuration
@EnableAsync
public class AsyncConfig implements AsyncConfigurer {

    @Override
    public Executor getAsyncExecutor() {
        ThreadPoolTaskExecutor threadPoolTaskExecutor = new ThreadPoolTaskExecutor();
        //最大线程数
        threadPoolTaskExecutor.setMaxPoolSize(36);
        //核心线程数
        threadPoolTaskExecutor.setCorePoolSize(6);
        //队列最大容量
        threadPoolTaskExecutor.setQueueCapacity(16);
        //最大线程存活时间
        threadPoolTaskExecutor.setKeepAliveSeconds(6);
        //自定义线程工厂
        threadPoolTaskExecutor.setThreadFactory(new ThreadFactory() {
            AtomicInteger atomicInteger = new AtomicInteger();

            @Override
            public Thread newThread(Runnable r) {
                return new Thread(r, "get线程" + atomicInteger.incrementAndGet());
            }
        });
        //初始化线程池
        threadPoolTaskExecutor.initialize();
        return threadPoolTaskExecutor;
    }

    /**
     * 出现异常时的处理方式
     *
     * @return
     */
    @Override
    public AsyncUncaughtExceptionHandler getAsyncUncaughtExceptionHandler() {
        return null;
    }
}

重写getAsyncExecutor()方法,定义出需要返回怎样的线程池,重写getAsyncUncaughtExceptionHandler()方法,定义怎么处理线程池中线程抛出的异常。然后通过@Configuration注解注入IOC容器,通过@EnableAsync注解开启异步线程池。

写一个接口类AsyncService,如下:

public interface AsyncService {
    void get() throws InterruptedException;
}

写一个AsyncServiceImpl类,实现AsyncService接口,如下:

import org.springframework.scheduling.annotation.Async;
import org.springframework.stereotype.Service;
import java.time.LocalDateTime;
import java.time.format.DateTimeFormatter;
import java.util.concurrent.TimeUnit;

@Service
public class AsyncServiceImpl implements AsyncService {

    public String getCurrentDateTime() {
        DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss");
        return LocalDateTime.now().format(formatter);
    }

    @Override
    @Async
    public void get() throws InterruptedException {
        System.out.println(getCurrentDateTime() + ":【" + Thread.currentThread().getName() + "】" + "处理请求");
        TimeUnit.SECONDS.sleep(6);
    }
}

写一个AsyncServiceController,提供相应接口做测试,如下:

package com.example.springboot.codedemo;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

import java.time.LocalDateTime;
import java.time.format.DateTimeFormatter;

@RestController
@RequestMapping("/async")
public class AsyncServiceController {

    public String getCurrentDateTime() {
        DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss");
        return LocalDateTime.now().format(formatter);
    }


    @Autowired
    private AsyncService asyncService;

    @GetMapping("/get")
    public void get() throws InterruptedException {
        System.out.println(getCurrentDateTime() + ":【" + Thread.currentThread().getName() + "】" + "发出请求");
        asyncService.get();
    }
}

为了方便,以上的日期转换方法没有抽取出来单独成工具。

访问http://localhost:8080/async/get,输出结果如下:
在这里插入图片描述
从输出结果可以看到,请求是并发执行的,并没有等待6s,同时发出请求的线程和处理请求的线程也是不一样的。

猜你喜欢

转载自blog.csdn.net/weixin_38106322/article/details/107824156