Close

Spring - Using AsyncListenableTaskExecutor and ListenableFutureCallback

[Last Updated: Dec 22, 2023]

In this tutorial we are going to see example of AsyncListenableTaskExecutor

As SimpleAsyncTaskExecutor also implements AsyncListenableTaskExecutor, we can add callback listeners, instead of blocking on Future.get() call.

Example

package com.logicbig.example;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.ApplicationContext;
import org.springframework.context.annotation.AnnotationConfigApplicationContext;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.core.task.AsyncListenableTaskExecutor;
import org.springframework.core.task.SimpleAsyncTaskExecutor;
import org.springframework.util.concurrent.ListenableFuture;
import org.springframework.util.concurrent.ListenableFutureCallback;

import java.util.concurrent.Callable;

public class AsyncListableTaskExecutorExample {

    public static void main (String[] args) throws Exception {
        ApplicationContext context =
                  new AnnotationConfigApplicationContext(MyConfig.class);
        MyBean bean = context.getBean(MyBean.class);
        bean.runTasks();
    }

    @Configuration
    public static class MyConfig {

        @Bean
        MyBean myBean () {
            return new MyBean();
        }

        @Bean
        AsyncListenableTaskExecutor taskExecutor () {
            SimpleAsyncTaskExecutor t = new SimpleAsyncTaskExecutor();
            t.setConcurrencyLimit(100);
            return t;
        }

        @Bean
        ListenableFutureCallback<String> taskCallback () {
            return new MyListenableFutureCallback();
        }
    }

    private static class MyBean {
        @Autowired
        private AsyncListenableTaskExecutor executor;
        @Autowired
        private ListenableFutureCallback threadListenableCallback;


        public void runTasks () throws Exception {

            for (int i = 0; i < 10; i++) {
                ListenableFuture<String> f =
                          executor.submitListenable(getTask(i));
                f.addCallback(threadListenableCallback);
            }
        }

        private Callable<String> getTask (int i) {
            return () -> {
                System.out.printf("running task %d. Thread: %s%n",
                                  i,
                                  Thread.currentThread().getName());
                return String.format("Task finished %d", i);
            };
        }
    }

    private static class MyListenableFutureCallback
              implements ListenableFutureCallback<String> {
        @Override
        public void onFailure (Throwable ex) {
            System.out.println("faliure message: " + ex.getMessage());
            ex.printStackTrace();
        }

        @Override
        public void onSuccess (String result) {
            System.out.println("success object: " + result);
        }
    }
}

Output

running task 0. Thread: SimpleAsyncTaskExecutor-1
success object: Task finished 0
running task 1. Thread: SimpleAsyncTaskExecutor-2
running task 3. Thread: SimpleAsyncTaskExecutor-4
running task 4. Thread: SimpleAsyncTaskExecutor-5
success object: Task finished 1
running task 2. Thread: SimpleAsyncTaskExecutor-3
running task 7. Thread: SimpleAsyncTaskExecutor-8
running task 9. Thread: SimpleAsyncTaskExecutor-10
success object: Task finished 4
running task 6. Thread: SimpleAsyncTaskExecutor-7
success object: Task finished 3
running task 5. Thread: SimpleAsyncTaskExecutor-6
success object: Task finished 6
success object: Task finished 9
success object: Task finished 7
running task 8. Thread: SimpleAsyncTaskExecutor-9
success object: Task finished 2
success object: Task finished 8
success object: Task finished 5

In Spring 6.0 AsyncListenableTaskExecutor has been deprecated in favor of AsyncTaskExecutor's method which return CompletableFuture. We will see example of those methods in the next tutorial.




Example Project

Dependencies and Technologies Used:

  • spring-context 6.1.2 (Spring Context)
     Version Compatibility: 4.0.0.RELEASE - 6.1.2Version List
    ×

    Version compatibilities of spring-context with this example:

    • 4.0.0.RELEASE
    • 4.0.1.RELEASE
    • 4.0.2.RELEASE
    • 4.0.3.RELEASE
    • 4.0.4.RELEASE
    • 4.0.5.RELEASE
    • 4.0.6.RELEASE
    • 4.0.7.RELEASE
    • 4.0.8.RELEASE
    • 4.0.9.RELEASE
    • 4.1.0.RELEASE
    • 4.1.1.RELEASE
    • 4.1.2.RELEASE
    • 4.1.3.RELEASE
    • 4.1.4.RELEASE
    • 4.1.5.RELEASE
    • 4.1.6.RELEASE
    • 4.1.7.RELEASE
    • 4.1.8.RELEASE
    • 4.1.9.RELEASE
    • 4.2.0.RELEASE
    • 4.2.1.RELEASE
    • 4.2.2.RELEASE
    • 4.2.3.RELEASE
    • 4.2.4.RELEASE
    • 4.2.5.RELEASE
    • 4.2.6.RELEASE
    • 4.2.7.RELEASE
    • 4.2.8.RELEASE
    • 4.2.9.RELEASE
    • 4.3.0.RELEASE
    • 4.3.1.RELEASE
    • 4.3.2.RELEASE
    • 4.3.3.RELEASE
    • 4.3.4.RELEASE
    • 4.3.5.RELEASE
    • 4.3.6.RELEASE
    • 4.3.7.RELEASE
    • 4.3.8.RELEASE
    • 4.3.9.RELEASE
    • 4.3.10.RELEASE
    • 4.3.11.RELEASE
    • 4.3.12.RELEASE
    • 4.3.13.RELEASE
    • 4.3.14.RELEASE
    • 4.3.15.RELEASE
    • 4.3.16.RELEASE
    • 4.3.17.RELEASE
    • 4.3.18.RELEASE
    • 4.3.19.RELEASE
    • 4.3.20.RELEASE
    • 4.3.21.RELEASE
    • 4.3.22.RELEASE
    • 4.3.23.RELEASE
    • 4.3.24.RELEASE
    • 4.3.25.RELEASE
    • 4.3.26.RELEASE
    • 4.3.27.RELEASE
    • 4.3.28.RELEASE
    • 4.3.29.RELEASE
    • 4.3.30.RELEASE
    • 5.0.0.RELEASE
    • 5.0.1.RELEASE
    • 5.0.2.RELEASE
    • 5.0.3.RELEASE
    • 5.0.4.RELEASE
    • 5.0.5.RELEASE
    • 5.0.6.RELEASE
    • 5.0.7.RELEASE
    • 5.0.8.RELEASE
    • 5.0.9.RELEASE
    • 5.0.10.RELEASE
    • 5.0.11.RELEASE
    • 5.0.12.RELEASE
    • 5.0.13.RELEASE
    • 5.0.14.RELEASE
    • 5.0.15.RELEASE
    • 5.0.16.RELEASE
    • 5.0.17.RELEASE
    • 5.0.18.RELEASE
    • 5.0.19.RELEASE
    • 5.0.20.RELEASE
    • 5.1.0.RELEASE
    • 5.1.1.RELEASE
    • 5.1.2.RELEASE
    • 5.1.3.RELEASE
    • 5.1.4.RELEASE
    • 5.1.5.RELEASE
    • 5.1.6.RELEASE
    • 5.1.7.RELEASE
    • 5.1.8.RELEASE
    • 5.1.9.RELEASE
    • 5.1.10.RELEASE
    • 5.1.11.RELEASE
    • 5.1.12.RELEASE
    • 5.1.13.RELEASE
    • 5.1.14.RELEASE
    • 5.1.15.RELEASE
    • 5.1.16.RELEASE
    • 5.1.17.RELEASE
    • 5.1.18.RELEASE
    • 5.1.19.RELEASE
    • 5.1.20.RELEASE
    • 5.2.0.RELEASE
    • 5.2.1.RELEASE
    • 5.2.2.RELEASE
    • 5.2.3.RELEASE
    • 5.2.4.RELEASE
    • 5.2.5.RELEASE
    • 5.2.6.RELEASE
    • 5.2.7.RELEASE
    • 5.2.8.RELEASE
    • 5.2.9.RELEASE
    • 5.2.10.RELEASE
    • 5.2.11.RELEASE
    • 5.2.12.RELEASE
    • 5.2.13.RELEASE
    • 5.2.14.RELEASE
    • 5.2.15.RELEASE
    • 5.2.16.RELEASE
    • 5.2.17.RELEASE
    • 5.2.18.RELEASE
    • 5.2.19.RELEASE
    • 5.2.20.RELEASE
    • 5.2.21.RELEASE
    • 5.2.22.RELEASE
    • 5.2.23.RELEASE
    • 5.2.24.RELEASE
    • 5.2.25.RELEASE
    • 5.3.0
    • 5.3.1
    • 5.3.2
    • 5.3.3
    • 5.3.4
    • 5.3.5
    • 5.3.6
    • 5.3.7
    • 5.3.8
    • 5.3.9
    • 5.3.10
    • 5.3.11
    • 5.3.12
    • 5.3.13
    • 5.3.14
    • 5.3.15
    • 5.3.16
    • 5.3.17
    • 5.3.18
    • 5.3.19
    • 5.3.20
    • 5.3.21
    • 5.3.22
    • 5.3.23
    • 5.3.24
    • 5.3.25
    • 5.3.26
    • 5.3.27
    • 5.3.28
    • 5.3.29
    • 5.3.30
    • 5.3.31
    • Compatible Java Version: 17+
    • 6.0.0
    • 6.0.1
    • 6.0.2
    • 6.0.3
    • 6.0.4
    • 6.0.5
    • 6.0.6
    • 6.0.7
    • 6.0.8
    • 6.0.9
    • 6.0.10
    • 6.0.11
    • 6.0.12
    • 6.0.13
    • 6.0.14
    • 6.0.15
    • 6.1.0
    • 6.1.1
    • 6.1.2

    Versions in green have been tested.

  • JDK 17
  • Maven 3.8.1

AsyncListenableTaskExecutor/ListenableFutureCallback Example Select All Download
  • spring-async-listenable-task-executor-example
    • src
      • main
        • java
          • com
            • logicbig
              • example
                • AsyncListableTaskExecutorExample.java

    See Also