Home > Software design >  Async process is not working in Springboot application
Async process is not working in Springboot application

Time:01-21

I am trying async process in my code. i written code like below. But async process is not working. Thread name '' itself not showing in logs. It looks Service class is not looking bean 'asyncExecutor'. What i am missing here.

@SpringBootApplication
@EnableAsync
public class  MyMainApplication {

    @Bean(name = "asyncExecutor")
    public Executor asyncExecutor() {
          ThreadPoolTaskExecutor executor = new ThreadPoolTaskExecutor();
            executor.setCorePoolSize(3);
            executor.setMaxPoolSize(3);
            executor.setQueueCapacity(100);
            executor.setThreadNamePrefix("AsynchThread-");
            executor.initialize();
            return executor; 
    }
    
    public static void main(String[] args) {
        SpringApplication.run(MyMainApplication.class, args);
    }

}

Service Class

public void getSampleDetails(String param1, String param2) {
    log.info("Inside - getSampleDetails");
    CompletableFuture<Map<String, String>> sampleMap1 = null;
    CompletableFuture<Map<String,  String>> sampleMap2 = null;
    CompletableFuture<Map<String,  String>> sampleMap3 = null;
    sampleMap1 = getSampleMap1(param1, param2);
    sampleMap2 = getSampleMap2(param1, param2);
    sampleMap3 = getSampleMap3(param1, param2);         
    // Wait until they are all done
    CompletableFuture.allOf(sampleMap1, sampleMap2, sampleMap3).join();         
}
@Async("asyncExecutor")
    public CompletableFuture<Map<String, String>> getSampleMap1(String param1, String param2) throws InterruptedException {
    System.out.println("Inside  Method1");
    ..
    ..
    }   

@Async("asyncExecutor")
    public CompletableFuture<Map<String, String>> getSampleMap2(String param1, String param2) throws InterruptedException {
    System.out.println("Inside  Method2");
    ..
    ..
    }

@Async("asyncExecutor")
    public CompletableFuture<Map<String, String>> getSampleMap3(String param1, String param2) throws InterruptedException {
    System.out.println("Inside  Method3");
    ..
    ..
    }   

Thread name is not displayed and async process is not happening logs:

[           main]o.s.s.concurrent.ThreadPoolTaskExecutor   Initializing ExecutorService
[           main]o.s.s.concurrent.ThreadPoolTaskExecutor   Initializing ExecutorService 'asyncExecutor1'
[           main]o.s.s.c.ThreadPoolTaskScheduler           Initializing ExecutorService 'taskScheduler'
[           main]o.s.b.w.embedded.tomcat.TomcatWebServer   Tomcat started on port(s): 32182 (http) with context path '/myapplication'
[           main]MyMainApplication  Started MyMainApplication in 46.662 seconds (JVM running for 48.024)
 [exec-1]e-myapplication]  Initializing Spring DispatcherServlet 'dispatcherServlet'
  [exec-1]o.s.web.servlet.DispatcherServlet         Initializing Servlet 'dispatcherServlet'
  [exec-1]o.s.web.servlet.DispatcherServlet         Completed initialization in 8 ms
  [exec-1]Inside - getSampleDetails
  [exec-1]Inside  Method1
  [exec-1]Inside  Method2
  [exec-1]Inside  Method3 

CodePudding user response:

When spring scans the bean, it will scan whether the @Async annotation is included on the method. If it is included, spring will dynamically generate a subclass (ie proxy class, proxy) for the bean, and the proxy class inherits the original bean. At this time, when the annotated method is called, it is actually called by the proxy class, and the proxy class adds asynchronous effects when it is called. However, if this annotated method is called by other methods in the same class, the method call does not go through the proxy class, but directly through the original bean, so there is no asynchronous effect, we see The phenomenon is that the @Async annotation is invalid.

You can try something like this:

  1. the call and task should be placed in different classes.
  2. Add annotation in startup class:@EnableAspectJAutoProxy(exposeProxy = true)
  3. In the Service Manager, use AopContext.currentProxy() to obtain the proxy class of the Service, and then call the transaction method to force through the proxy class to activate the transaction aspect.
  •  Tags:  
  • Related