3

In Spring @Async , If i want to have multiple executor pool with different queue capacity - I get the error "Only one AsyncAnnotationBeanPostProcessor may exist within the context".

From the below links I observe that this is not feasible .

Only one AsyncAnnotationBeanPostProcessor may exist within the context

Spring's @Scheduled error : Only one AsyncAnnotationBeanPostProcessor may exist within the context

https://stackoverflow.com/questions/17367572/how-to-configure-multiple-threadpooltaskexecutors-within-the-same-application-co

http://forum.spring.io/forum/spring-projects/container/79086-multiple-executor-possible

Is there any alternative ( other than using spring-integration )

Below is my configuration

My configuration is like below

<!- Executor A -->
<task:annotation-driven executor="executor_A"/>
<task:executor id="executor_A" pool-size="100"/>

<!- Executor B -->
<task:annotation-driven executor="executor_B"/>
<task:executor id="executor_B" pool-size="100"/>

The above two configurations are defined in different xml context files and all are loaded in to same application context

From the source code , I am mapping to the specific executor

@Async("executor_A")
public void testExecutorA()
{
}



@Async("executor_B")
public void testExecutorB()
{
}

When I deploy , I get the below error

2014-07-22 09:41:26.644 [localhost-startStop-1] ERROR o.s.web.context.ContextLoader U: SC: TX: - Context initialization failed org.springframework.beans.factory.parsing.BeanDefinitionParsingException: Configuration problem: Failed to import bean definitions from URL location [classpath*:/META-INF/domainconfig/*-domain-context.xml] Offending resource: ServletContext resource [/WEB-INF/spring/root-context.xml]; nested exception is org.springframework.beans.factory.parsing.BeanDefinitionParsingException: Configuration problem: Only one AsyncAnnotationBeanPostProcessor may exist within the context. Offending resource: URL [jar:file:/D:/tomcat/apache-tomcat-7.0.29/webapps/myapp/WEB-INF/lib/myapp-domain-1.0.0.jar!/META-INF/domainconfig/my-domain-context.xml]

Thanks

Lives

Community
  • 1
  • 1
lives
  • 1,243
  • 5
  • 25
  • 61

1 Answers1

2

You haven't explained much what your configuration looks like but it's possible to have different ExecutorService in the same context. Your last link to the forum actually has a comment with the reference to the issue that implements this feature.

Just define them and qualify the @Async annotation with the service you want to use for a particular invocation, something like:

@Async("myExecutor")
public Future<Foo> handle() { ... }

When you have multiple matching candidates, you need to specify which one is going to be used if none is specified explicitly (that is define the default service to use). To do so, specify it either with the <task:annotation-driven/> element

<task:annotation-driven executor="myExecutor"

or

@EnableAsync
@Configuration
public class AppConfig implements AsyncConfigurer {

    public Executor getAsynchExecutor() { ... }
}

Check the documentation for more details.

(Note that as of Spring framework 4.1, the AsyncConfigurer has an extra method and you should prefer extending from the AsyncConfigurerSupport instead).

Stephane Nicoll
  • 31,977
  • 9
  • 97
  • 89
  • Thanks for the response . I have added the details to my main qs – lives Jul 22 '14 at 11:57
  • Well, I already replied you. You can't define the `task:annotation-driven` element twice. Just register once with the main executor you want to use and when you need a different one, just define it in the annotation. – Stephane Nicoll Jul 22 '14 at 13:31
  • Sorry - I could not follow . If I need a different executor pool and if i define it as an annotation with @Async - what would be the pool size of that executor pool ? Will it be that of the default one I define ? Or can i define the pool size as well in the annotation ? – lives Jul 22 '14 at 13:52
  • 1
    Thanks Stephane - I got it now . It should be like below – lives Jul 22 '14 at 14:48
  • how can I have different executor with using @EnableAsync? – Dejell Apr 21 '15 at 17:58
  • If I have multiple `Executor`s defined as you have in the example above, how do I get them to use the same `AsyncUncaughtExceptionHandler`. It seems like I can only define it for the default Executor in the `AsyncConfigurer.getAsyncUncaughtExceptionHandler` method I override and not for the named ones. – Eric Dec 22 '15 at 04:42
  • that's not what I see in the code. The handler is used regardless of the executor. If you can share a sample that shows the problem, feel free to create an issue. Thanks. – Stephane Nicoll Dec 22 '15 at 06:19
  • Hi @Dejell, did you get your answer? I am also looking for a solution on how to have two or more `ThreadPoolTaskExecutor` beans in an application using annotations i.e `@EnableAsync`. – horizon7 Dec 21 '18 at 19:11