概述

如何实现异步方法调用,很多人首先会想到使用线程或者线程池技术,springboot中有一个很简单的方法可以实现异步方法调用,那就是在方法上使用@Async注解

例子

首先在Springboot启动类上添加@EnableAsync注解,表明使用@Async注解

@SpringBootApplication
@EnableAsync
public class Application{ public static void main(String[] args) {
SpringApplication.run(Application.class, args);
}
}

异步调用测试类

package com.example.mongo_demo.test;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.scheduling.annotation.Async;
import org.springframework.stereotype.Component; /**
* created by qinming on 2018/5/17
**/
@Component
public class AsyncTest {
public static final Logger LOGGER = LoggerFactory.getLogger(AsyncTest.class); @Async
public void asyn1() throws InterruptedException {
Long timeMilles = System.currentTimeMillis();
Thread.sleep(7000);
LOGGER.error("》》》》》》》》》》》》asyn1耗时:{}《《《《《《《《《",System.currentTimeMillis()-timeMilles);
}
@Async
public void asyn2() throws InterruptedException {
Long timeMilles = System.currentTimeMillis();
Thread.sleep(7000);
LOGGER.error("》》》》》》》》》》》》asyn2耗时:{}《《《《《《《《《",System.currentTimeMillis()-timeMilles);
}
@Async
public void asyn3() throws InterruptedException {
Long timeMilles = System.currentTimeMillis();
Thread.sleep(10000);
LOGGER.error("》》》》》》》》》》》》asyn3耗时:{}《《《《《《《《《",System.currentTimeMillis()-timeMilles);
}
}

通过一个简单的接口测试即可

/**
* created by qinming on 2018/5/17
**/
@RestController
@RequestMapping("/api")
public class DemostrationController {
@Autowired
private AsyncTest asyncTest;
public static final Logger LOGGER = LoggerFactory.getLogger(DemostrationController.class);
@RequestMapping("/async/test")
public String get() throws InterruptedException {
long timeMillis = System.currentTimeMillis();
asyncTest.asyn1();
asyncTest.asyn2();
asyncTest.asyn3();
Thread.sleep(1000);
LOGGER.error("//////耗时:{}",System.currentTimeMillis()-timeMillis);
return "";
}
}

结果如下:

2018-05-17 14:27:40.252 ERROR 7843 --- [nio-8080-exec-1] c.e.m.ctrl.DemostrationController : //////耗时:1019
2018-05-17 14:27:46.253 ERROR 7843 --- [cTaskExecutor-1] com.example.mongo_demo.test.AsyncTest : 》》》》》》》》》》》》asyn1耗时:7003《《《《《《《《《
2018-05-17 14:27:46.255 ERROR 7843 --- [cTaskExecutor-2] com.example.mongo_demo.test.AsyncTest : 》》》》》》》》》》》》asyn2耗时:7005《《《《《《《《《
2018-05-17 14:27:49.254 ERROR 7843 --- [cTaskExecutor-3] com.example.mongo_demo.test.AsyncTest : 》》》》》》》》》》》》asyn3耗时:10004《《《《《《《《《

这样就实现了异步方法的简单调用

带有返回值的方法如何使用@Async注解

使用@Async注解的方法返回值为java.util.concurrent.Future 的实现类 org.springframework.scheduling.annotation.AsyncResult 类型,代码如下:

/**
* created by qinming on 2018/5/17
**/
@Component
public class AsyncWIthReturnValueTest {
public static final Logger LOGGER = LoggerFactory.getLogger(AsyncWIthReturnValueTest.class); @Async
public Future<String> aysnc1() throws InterruptedException {
Long st = System.currentTimeMillis();
LOGGER.error(">>>>>>>aysnc1 start at {}>>>>>",st);
Thread.sleep(7000);
long end =System.currentTimeMillis();
LOGGER.error(">>>>>>>aysnc1 cost :{}>>>>>",end - st);
return new AsyncResult<String>("aysnc1 is done");
}
@Async
public Future<String> aysnc2() throws InterruptedException {
Long st = System.currentTimeMillis();
LOGGER.error(">>>>>>>aysnc2 start at {}>>>>>",st);
Thread.sleep(7000);
long end =System.currentTimeMillis();
LOGGER.error(">>>>>>>aysnc2 cost :{}>>>>>",end - st);
return new AsyncResult<String>("aysnc2 is done");
}
@Async
public Future<String> aysnc3() throws InterruptedException {
Long st = System.currentTimeMillis();
LOGGER.error(">>>>>>>aysnc3 start at {}>>>>>",st);
Thread.sleep(7000);
long end =System.currentTimeMillis();
LOGGER.error(">>>>>>>aysnc3 cost :{}>>>>>",end - st);
return new AsyncResult<String>("aysnc3 is done");
}
}

调用方法例子如下:

@RequestMapping("/async/test")
public String get() throws InterruptedException, ExecutionException {
long timeMillis = System.currentTimeMillis();
Future<String> async1 = asyncWIthReturnValueTest.aysnc1();
Future<String> async2 = asyncWIthReturnValueTest.aysnc2();
Future<String> async3 = asyncWIthReturnValueTest.aysnc3();
while (true) {
if (async1.isDone()){
LOGGER.error("----{}1-------",async1.get());
}
if (async2.isDone()){
LOGGER.error("----{}2-------",async2.get());
}
if (async3.isDone()){
LOGGER.error("----{}3-------",async3.get());
}
if (async1.isDone() && async2.isDone() && async3.isDone()) {
break;
}
Thread.sleep(1000);
}
LOGGER.error("//////耗时:{}",System.currentTimeMillis()-timeMillis);
return "SUCCESS";
}

spring@Async注解实现异步方法调用的更多相关文章

  1. 使用Spring中@Async注解实现异步调用

    异步调用? 在解释异步调用之前,我们先来看同步调用的定义:同步就是整个处理过程顺序执行,当各个过程都执行完毕,并返回结果. 异步调用则是只是发送了调用的指令,调用者无需等待被调用的方法完全执行完毕,继 ...

  2. 异步任务spring @Async注解源码解析

    1.引子 开启异步任务使用方法: 1).方法上加@Async注解 2).启动类或者配置类上@EnableAsync 2.源码解析 虽然spring5已经出来了,但是我们还是使用的spring4,本文就 ...

  3. (转)spring boot注解 --@EnableAsync 异步调用

    原文:http://www.cnblogs.com/azhqiang/p/5609615.html EnableAsync注解的意思是可以异步执行,就是开启多线程的意思.可以标注在方法.类上. @Co ...

  4. spring boot注解 --@EnableAsync 异步调用

    EnableAsync注解的意思是可以异步执行,就是开启多线程的意思.可以标注在方法.类上. @Component public class Task { @Async public void doT ...

  5. Spring —— @Async注解的使用

    参考文档 Spring Boot使用@Async实现异步调用:自定义线程池 Spring Boot使用@Async实现异步调用:ThreadPoolTaskScheduler线程池的优雅关闭

  6. springboot(整合多数据源demo,aop,定时任务,异步方法调用,以及获取properties中自定义的变量值)

    有这么一个需求 每个部门,需要操作的数据库不同,A部门要将数据放test数据库,B 部门数据 要放在test1数据库 同一个项目 需要整合 多个数据源 上传个demo 方便自己以后回看!!!!!!!! ...

  7. Spring @Async的异常处理

    楼主在前面的2篇文章中,分别介绍了Java子线程中通用的异常处理,以及Spring web应用中的异常处理.链接如下: Java子线程中的异常处理(通用) Spring web引用中的异常处理 今天, ...

  8. SpringCloud 微服务中 @Async 注解自定义线程池 引发的aop 问题

    背景 在 使用springCloud 的@Async注解来做异步操作时,想自定义其线程池. 引发问题 自定义完线程池后,发现代码里并没有使用自定义线程池里的线程,于是新建一个demo工程,一样的配置代 ...

  9. Spring中@Async注解实现“方法”的异步调用

    原文:http://www.cnblogs.com/zhengbin/p/6104502.html 简单介绍: Spring为任务调度与异步方法执行提供了注解支持.通过在方法上设置@Async注解,可 ...

随机推荐

  1. Let's Code

    Let's Code Happy Coding, Happy OI #include <bits/stdc++.h> using namespace std; int main() { c ...

  2. 【Python】**kwargs和takes 1 positional argument but 2 were given

    Python的函数定义中可以在参数里添加**kwargs——简单来说目的是允许添加不定参数名称的参数,并作为字典传递参数.但前提是——你必须提供参数名. 例如下述情况: class C(): def ...

  3. 关于Linux fontconfig 字体库的坑

    01.安装字体软件 yum -y install fontconfig 然后把字体拷过去就行了 cd /usr/share/fonts fc-list 这是查看 02.拷贝字体到指定目录 cp sim ...

  4. hdu 5446 lucas+crt+按位乘

    http://acm.hdu.edu.cn/showproblem.php?pid=5446 题意:题目意思很简单,要你求C(n,m)mod p的值 p=p1*p2*...pn; 题解:对于C(n,m ...

  5. Android 官方下拉刷新 SwipeRefreshLayout

    0.build.gradle compile 'com.android.support:support-v4:23+' 1.布局文件 <android.support.v4.widget.Swi ...

  6. Django rest-framework框架-CSRF验证

    settings.py里面有一个中间件 django.middleware.csrf.CsrfViewmiddleware  #如果注释掉全站不需要csrf验证  如果打开全站都要csrf验证 全局使 ...

  7. 4. Java入门程序

    以eclipse为例,建立一个简单的Java程序. 首先启动eclipse,进入到如下主页面: 新建一个项目,选择“File-New-Java Project”: 弹出了一个如下页面,假设命名为Tes ...

  8. 8. Object References, Mutability, and Recycling

    1. Variables Are Not Boxes # Think variables as sticky notes a = [1, 2, 3] b = a a.append(4) print b ...

  9. ndk学习之C语言基础复习----基本数据类型、数组

    关于NDK这个分类在N年前就已经创建了,但是一直木有系统的记录其学习过程,当然也没真正学会NDK的技术真谛,所以一直也是自己的一个遗憾,而如今对于Android程序员的要求也是越来越高,对于NDK也是 ...

  10. ubuntu卸载/更新Cmake

    CMake安装或CMake Error at CMakeLists 发生情景: 使用cmake命令安装软件时,报如下错误: CMake Error at CMakeLists.txt:4 (CMAKE ...