欧美bbbwbbbw肥妇,免费乱码人妻系列日韩,一级黄片

一文詳解SpringBoot如何優(yōu)雅地實現(xiàn)異步調(diào)用

 更新時間:2023年03月17日 10:26:54   作者:JAVA旭陽  
SpringBoot想必大家都用過,但是大家平時使用發(fā)布的接口大都是同步的,那么你知道如何優(yōu)雅的實現(xiàn)異步呢?這篇文章就來和大家詳細(xì)聊聊

前言

SpringBoot想必大家都用過,但是大家平時使用發(fā)布的接口大都是同步的,那么你知道如何優(yōu)雅的實現(xiàn)異步呢?

這篇文章就是關(guān)于如何在Spring Boot中實現(xiàn)異步行為的。但首先,讓我們看看同步和異步之間的區(qū)別。

  • 同步編程:在同步編程中,任務(wù)一次執(zhí)行一個,只有當(dāng)一個任務(wù)完成時,下一個任務(wù)才會被解除阻塞。
  • 異步編程:在異步編程中,可以同時執(zhí)行多個任務(wù)。您可以在上一個任務(wù)完成之前轉(zhuǎn)到另一個任務(wù)。

Spring Boot中,我們可以使用@Async注解來實現(xiàn)異步行為。

實現(xiàn)步驟

1.定義一個異步服務(wù)接口AsyncService.java

public interface AsyncService {

    void asyncMethod() throws InterruptedException;

    Future<String> futureMethod() throws InterruptedException;
}

2.實現(xiàn)定義的接口AsyncServiceImpl.java

@Service
@Slf4j
public class AsyncServiceImpl implements AsyncService  {

    @Async
    @Override
    public void asyncMethod() throws InterruptedException {
        Thread.sleep(3000);
        log.info("Thread: [{}], Calling other service..", Thread.currentThread().getName());
    }

    @Async
    @Override
    public Future<String> futureMethod() throws InterruptedException {
        Thread.sleep(5000);
        log.info("Thread: [{}], Calling other service..", Thread.currentThread().getName());
        return new AsyncResult<>("task Done");
    }
}
  • AsyncServiceImpl 是一個 spring 管理的 bean
  • 您的異步方法必須是公共的,而且是被@Async注解修飾。
  • 返回類型被限制為 void 或 Future。

3.定義一個控制器AsyncController.java

@EnableAsync
@RestController
@Slf4j
public class AsyncController {
    @Autowired
    AsyncService asyncService;

    @GetMapping("/async")
    public String asyncCallerMethod() throws InterruptedException {
        long start = System.currentTimeMillis();
        log.info("call async method, thread name: [{}]", Thread.currentThread().getName());
        asyncService.asyncMethod();
        String response = "task completes in :" +
                (System.currentTimeMillis() - start) + "milliseconds";
        return response;
    }

    @GetMapping("/asyncFuture")
    public String asyncFuture() throws InterruptedException, ExecutionException {
        long start = System.currentTimeMillis();
        log.info("call async method, thread name: [{}]", Thread.currentThread().getName());
        Future<String> future = asyncService.futureMethod();
        // 阻塞獲取結(jié)果
        String taskResult = future.get();
        String response = taskResult + "task completes in :" +
                (System.currentTimeMillis() - start) + "milliseconds";
        return response;
    }
}
  • 關(guān)鍵點,需要添加啟用異步的注解@EnableAsync ,當(dāng)然這個注解加在其他地方也ok得。
  • 當(dāng)外部調(diào)用該接口時,asyncMethod()將由默認(rèn)任務(wù)執(zhí)行程序創(chuàng)建的另一個線程執(zhí)行,主線程不需要等待完成異步方法執(zhí)行。

4.運行一下

現(xiàn)在我們運行一下看看,是不是異步返回的。

可以看到調(diào)用/async接口,最終一步調(diào)用了方法。

調(diào)用/asyncFuture,發(fā)現(xiàn)返回5秒多,難道不是異步的嗎?其實也是異步的,看日志可以看出來,只不過我們返回的是Future,調(diào)用Futrue.get()是阻塞的。

自定義異步任務(wù)執(zhí)行器和異常處理

我們現(xiàn)在看看如果異常方法中報錯了會怎么樣?修改異步代碼如下所示,會拋運行時異常:

再次執(zhí)行異步接口,如下所示,會使用默認(rèn)的線程池和異常處理。

我們也可以自定義異步方法的處理異常和異步任務(wù)執(zhí)行器,我們需要配置 AsyncUncaughtExceptionHandler,如下代碼所示:

@Configuration
public class AsynConfiguration extends AsyncConfigurerSupport {
   @Override
   public Executor getAsyncExecutor() {
      ThreadPoolTaskExecutor executor = new 
                ThreadPoolTaskExecutor();
      executor.setCorePoolSize(3);
      executor.setMaxPoolSize(4);
      executor.setThreadNamePrefix("asyn-task-thread-");
      executor.setWaitForTasksToCompleteOnShutdown(true);
      executor.initialize();
      return executor;
  }
  @Override
  public AsyncUncaughtExceptionHandler  
         getAsyncUncaughtExceptionHandler() {
     return new AsyncUncaughtExceptionHandler() {
   
        @Override
        public void handleUncaughtException(Throwable ex, 
           Method method, Object... params) {
           System.out.println("Exception: " + ex.getMessage());
           System.out.println("Method Name: " + method.getName());
           ex.printStackTrace();
        }
    };
  }
}

再次運行,得到的結(jié)果如下:

@Async如何工作的

必須通過使用 @EnableAsync注解注解主應(yīng)用程序類或任何直接或間接異步方法調(diào)用程序類來啟用異步支持。主要通過代理模式實現(xiàn),默認(rèn)模式是 Proxy,另一種是 AspectJ。代理模式只允許通過代理攔截調(diào)用。永遠(yuǎn)不要從定義它的同一個類調(diào)用異步方法,它不會起作用。

當(dāng)使用 @Async對方法進(jìn)行注解時,它會根據(jù)“proxyTargetClass”屬性為該對象創(chuàng)建一個代理。當(dāng) spring 執(zhí)行這個方法時,默認(rèn)情況下它會搜索關(guān)聯(lián)的線程池定義。上下文中唯一的 spring 框架 TaskExecutor bean 或名為“taskExecutor”的 Executor bean。如果這兩者都不可解析,默認(rèn)會使用spring框架SimpleAsyncTaskExecutor來處理異步方法的執(zhí)行。

總結(jié)

在本文中,我們演示了在 spring boot 中如何使用 @Async 注解和異步方法中的異常處理實現(xiàn)異步行為。我們可以在一個接口中,需要訪問不同的資源,比如異步調(diào)用各個其他服務(wù)的接口,可以使用@Async,然后將結(jié)果通過Future的方式阻塞匯總,不失為一個提高性能的好方法。

到此這篇關(guān)于一文詳解SpringBoot如何優(yōu)雅地實現(xiàn)異步調(diào)用的文章就介紹到這了,更多相關(guān)SpringBoot異步調(diào)用內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!

相關(guān)文章

  • Java基本數(shù)據(jù)類型與對應(yīng)的包裝類(動力節(jié)點java學(xué)院整理)

    Java基本數(shù)據(jù)類型與對應(yīng)的包裝類(動力節(jié)點java學(xué)院整理)

    Java是面向?qū)ο蟮木幊陶Z言,包裝類的出現(xiàn)更好的體現(xiàn)這一思想,Java語言提供了八種基本類型。六種數(shù)字類型(四個整數(shù)型,兩個浮點型),一種字符類型,還有一種布爾型。 下面通過本文給大家詳細(xì)介紹,感興趣的朋友一起學(xué)習(xí)吧
    2017-04-04
  • Java多線程實現(xiàn)的兩種方式

    Java多線程實現(xiàn)的兩種方式

    本文主要介紹了Java多線程實現(xiàn)的兩種方式:繼承Thread類、實現(xiàn)Runnable接口。具有一定的參考價值,下面跟著小編一起來看下吧
    2017-01-01
  • Java實戰(zhàn)之王者榮耀的英雄是怎么產(chǎn)生的?

    Java實戰(zhàn)之王者榮耀的英雄是怎么產(chǎn)生的?

    這篇文章主要介紹了Java實戰(zhàn)之王者榮耀的英雄是怎么產(chǎn)生的?文中有非常詳細(xì)的代碼示例,對正在學(xué)習(xí)java的小伙伴們有很好地幫助,需要的朋友可以參考下
    2021-05-05
  • 移動指定文件夾內(nèi)的全部文件

    移動指定文件夾內(nèi)的全部文件

    移動指定文件夾內(nèi)的全部文件
    2009-01-01
  • Java字符串中刪除指定子字符串的方法簡介

    Java字符串中刪除指定子字符串的方法簡介

    這篇文章主要介紹了Java字符串中刪除指定子字符串的方法,是Java入門學(xué)習(xí)中的基礎(chǔ)知識,需要的朋友可以參考下
    2015-11-11
  • Spring Security驗證流程剖析及自定義驗證方法

    Spring Security驗證流程剖析及自定義驗證方法

    Spring Security是一個能夠為基于Spring的企業(yè)應(yīng)用系統(tǒng)提供聲明式的安全訪問控制解決方案的安全框架。這篇文章主要介紹了Spring Security驗證流程剖析及自定義驗證方法,需要的朋友可以參考下
    2018-03-03
  • SpringBoot多數(shù)據(jù)源配置的全過程記錄

    SpringBoot多數(shù)據(jù)源配置的全過程記錄

    在用SpringBoot開發(fā)項目時,隨著業(yè)務(wù)量的擴(kuò)大,我們通常會進(jìn)行數(shù)據(jù)庫拆分或是引入其他數(shù)據(jù)庫,從而我們需要配置多個數(shù)據(jù)源,下面這篇文章主要給大家介紹了關(guān)于SpringBoot多數(shù)據(jù)源配置的相關(guān)資料,需要的朋友可以參考下
    2021-11-11
  • Java常用函數(shù)式接口總結(jié)

    Java常用函數(shù)式接口總結(jié)

    今天給大家?guī)淼氖顷P(guān)于Java的相關(guān)知識,文章圍繞著Java常用函數(shù)式接口展開,文中有非常詳細(xì)的介紹及代碼示例,需要的朋友可以參考下
    2021-06-06
  • Java的List集合框架之LinkedList詳細(xì)解析

    Java的List集合框架之LinkedList詳細(xì)解析

    這篇文章主要介紹了Java的List集合框架之LinkedList詳細(xì)解析,LinkedList底層是內(nèi)部Node類的存儲,prev、next、item值,同時最外層還有first、last節(jié)點,需要的朋友可以參考下
    2023-11-11
  • SpringBoot整合FastDFS中間件實現(xiàn)文件分布管理

    SpringBoot整合FastDFS中間件實現(xiàn)文件分布管理

    FastDFS是一個開源的輕量級分布式文件系統(tǒng),它對文件進(jìn)行管理,功能包括:文件存儲、文件同步、文件上傳、文件下載等,解決了大容量存儲和負(fù)載均衡的問題,本文介紹了SpringBoot整合FastDFS中間件實現(xiàn)文件分布管理,需要的朋友可以參考下
    2024-08-08

最新評論