SpringBoot非官方教程 | 第二十三篇: 异步方法
来源:互联网 发布:林若宁 知乎 编辑:程序博客网 时间:2024/05/17 23:13
转载请标明出处:
http://blog.csdn.net/forezp/article/details/71024169
本文出自方志朋的博客
这篇文章主要介绍在springboot 使用异步方法,去请求github api.
创建工程
在pom文件引入相关依赖:
org.springframework.boot spring-boot-starter org.springframework spring-web com.fasterxml.jackson.core jackson-databind
创建一个接收数据的实体:
@JsonIgnoreProperties(ignoreUnknown=true)public class User { private String name; private String blog; public String getName() { return name; } public void setName(String name) { this.name = name; } public String getBlog() { return blog; } public void setBlog(String blog) { this.blog = blog; } @Override public String toString() { return "User [name=" + name + ", blog=" + blog + "]"; }}
创建一个请求的 githib的service:
@Servicepublic class GitHubLookupService { private static final Logger logger = LoggerFactory.getLogger(GitHubLookupService.class); private final RestTemplate restTemplate; public GitHubLookupService(RestTemplateBuilder restTemplateBuilder) { this.restTemplate = restTemplateBuilder.build(); } @Async public Future findUser(String user) throws InterruptedException { logger.info("Looking up " + user); String url = String.format("https://api.github.com/users/%s", user); User results = restTemplate.getForObject(url, User.class); // Artificial delay of 1s for demonstration purposes Thread.sleep(1000L); return new AsyncResult<>(results); }}
通过,RestTemplate去请求,另外加上类@Async 表明是一个异步任务。
开启异步任务:
@SpringBootApplication@EnableAsyncpublic class Application extends AsyncConfigurerSupport { public static void main(String[] args) { SpringApplication.run(Application.class, args); } @Override public Executor getAsyncExecutor() { ThreadPoolTaskExecutor executor = new ThreadPoolTaskExecutor(); executor.setCorePoolSize(2); executor.setMaxPoolSize(2); executor.setQueueCapacity(500); executor.setThreadNamePrefix("GithubLookup-"); executor.initialize(); return executor; }}
通过@EnableAsync开启异步任务;并且配置AsyncConfigurerSupport,比如最大的线程池为2.
测试
测试代码如下:
@Componentpublic class AppRunner implements CommandLineRunner { private static final Logger logger = LoggerFactory.getLogger(AppRunner.class); private final GitHubLookupService gitHubLookupService; public AppRunner(GitHubLookupService gitHubLookupService) { this.gitHubLookupService = gitHubLookupService; } @Override public void run(String... args) throws Exception { // Start the clock long start = System.currentTimeMillis(); // Kick of multiple, asynchronous lookups Future page1 = gitHubLookupService.findUser("PivotalSoftware"); Future page2 = gitHubLookupService.findUser("CloudFoundry"); Future page3 = gitHubLookupService.findUser("Spring-Projects"); // Wait until they are all done while (!(page1.isDone() && page2.isDone() && page3.isDone())) { Thread.sleep(10); //10-millisecond pause between each check } // Print results, including elapsed time logger.info("Elapsed time: " + (System.currentTimeMillis() - start)); logger.info("--> " + page1.get()); logger.info("--> " + page2.get()); logger.info("--> " + page3.get()); }}
启动程序,控制台会打印:
2017-04-30 13:11:10.351 INFO 1511 — [ GithubLookup-1] com.forezp.service.GitHubLookupService : Looking up PivotalSoftware
2017-04-30 13:11:10.351 INFO 1511 — [ GithubLookup-2] com.forezp.service.GitHubLookupService : Looking up CloudFoundry
2017-04-30 13:11:13.144 INFO 1511 — [ GithubLookup-2] com.forezp.service.GitHubLookupService : Looking up spring-Projects
耗时:3908
分析:可以卡的前面2个方法分别在GithubLookup-1 和GithubLookup-2执行,第三个在GithubLookup-2执行,注意因为在配置线程池的时候最大线程为2.如果你把线程池的个数为3的时候,耗时减少。
如果去掉@Async,你会发现,执行这三个方法都在main线程中执行。耗时总结,如下:
2017-04-30 13:13:00.934 INFO 1527 — [ main] com.forezp.service.GitHubLookupService : Looking up PivotalSoftware
2017-04-30 13:13:03.571 INFO 1527 — [ main] com.forezp.service.GitHubLookupService : Looking up CloudFoundry
2017-04-30 13:13:04.865 INFO 1527 — [ main] com.forezp.service.GitHubLookupService : Looking up Spring-Projects
耗时:5261
通过这一个小的栗子,你应该对异步任务有了一定的了解。
参考资料
https://spring.io/guides/gs/async-method/
源码下载
https://github.com/forezp/SpringBootLearning
优秀文章推荐:
- 更多springboot 教程:springBoot非官方教程 | 文章汇总
- 更多springcoud 教程:史上最简单的 SpringCloud 教程 | 文章汇总
- SpringBoot非官方教程 | 第二十三篇: 异步方法
- SpringBoot非官方教程 | 第二十三篇: 异步方法
- SpringBoot非官方教程 | 第二十三篇: 异步方法
- SpringBoot非官方教程 | 第二十三篇: 异步方法
- SpringBoot非官方教程 | 第十七篇:上传文件
- SpringBoot非官方教程 | 第十七篇:上传文件
- SpringBoot非官方教程 | 第十七篇:上传文件
- SpringBoot非官方教程 | 第十七篇:上传文件
- SpringBoot非官方教程 | 第二十五篇:2小时学会springboot
- SpringBoot非官方教程 | 第三篇:SpringBoot用JdbcTemplates访问Mysql
- SpringBoot非官方教程 | 第四篇:SpringBoot 整合JPA
- SpringBoot非官方教程 | 第五篇:springboot整合 beatlsql
- SpringBoot非官方教程 | 第六篇:springboot整合mybatis
- SpringBoot非官方教程 | 第七篇:springboot开启声明式事务
- SpringBoot非官方教程 | 第八篇:springboot整合mongodb
- SpringBoot非官方教程 | 第九篇: springboot整合Redis
- SpringBoot非官方教程 | 第十二篇:springboot集成apidoc
- SpringBoot非官方教程 | 第十三篇:springboot集成spring cache
- 我必须得告诉大家的MySQL优化原理
- mybatis中refid是什么意思
- SpringBoot非官方教程 | 第二十二篇: 创建含有多module的springboot工程
- 解析存储过程中常见变量
- Failed to execute goal org.apache.maven.plugins:maven-deploy-plugin:2.7:deploy (default-deploy) on p
- SpringBoot非官方教程 | 第二十三篇: 异步方法
- wordpress博客网站去掉域名中的/wordpess
- 浅谈移动端rem的用法
- 原始套接字&&数据链路层访问
- SpringBoot非官方教程 | 第二十四篇: springboot整合docker
- Android开发几种常用工具类
- plsql中文乱码,显示问号
- 深入理解 java 内部类
- matlab左右翻转图像