Satya
Satya

Reputation: 41

Autowired not happening for bean with @Async method

I am trying to Autowire a bean which contain a @Async method but, it failed with the exception "Injection of autowired dependencies failed"

My servlet.xml contains the declaration

<task:annotation-driven executor="executor" />
<task:executor id="executor" pool-size="7"/>

Can I get some help why this is failing to autowire ?

--- UPDATE--- Here is the stacktrace of the error.

"cancelAppointment" is the bean id where the Autowire is done for MailService bean

2013-08-14 17:06:46,488|main|DEBUG|org.springframework.beans.factory.support.DisposableBeanAdapter|Invoking destroy() on bean with name 'org.springframework.scheduling.annotation.internalScheduledAnnotationProcessor'
2013-08-14 17:06:46,488|main|DEBUG|org.springframework.beans.factory.support.DisposableBeanAdapter|Invoking destroy() on bean with name 'executor'
2013-08-14 17:06:46,488|main|INFO|org.springframework.scheduling.concurrent.ThreadPoolTaskExecutor|Shutting down ExecutorService
2013-08-14 17:06:46,492|main|ERROR|org.springframework.web.context.ContextLoader|Context initialization failed
org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'cancelAppointment': Injection of autowired dependencies failed; nested exception is org.springframework.beans.factory.BeanCreationException: Could not autowire field: private com.ge.appl.service.fs.manager.email.MailService com.ge.appl.service.fs.manager.cancel.consumer.CancelAppointmentImpl.mailService; nested exception is java.lang.IllegalArgumentException: Can not set com.ge.appl.service.fs.manager.email.MailService field com.ge.appl.service.fs.manager.cancel.consumer.CancelAppointmentImpl.mailService to $Proxy35
    at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor.postProcessPropertyValues(AutowiredAnnotationBeanPostProcessor.java:285)
    at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.populateBean(AbstractAutowireCapableBeanFactory.java:1074)
    at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:517)
    at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:456)
    at org.springframework.beans.factory.support.AbstractBeanFactory$1.getObject(AbstractBeanFactory.java:291)
    at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:222)
    at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:288)
    at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:190)
    at org.springframework.beans.factory.support.DefaultListableBeanFactory.preInstantiateSingletons(DefaultListableBeanFactory.java:580)
    at org.springframework.context.support.AbstractApplicationContext.finishBeanFactoryInitialization(AbstractApplicationContext.java:895)
    at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:425)
    at org.springframework.web.context.ContextLoader.createWebApplicationContext(ContextLoader.java:276)

------ UPDATE 2 ------------ Here is some more detail of the stack trace

Caused by: org.springframework.beans.factory.BeanCreationException: Could not autowire field: private com.ge.appl.service.fs.manager.email.MailService com.ge.appl.service.fs.manager.cancel.consumer.CancelAppointmentImpl.mailService; nested exception is java.lang.IllegalArgumentException: Can not set com.ge.appl.service.fs.manager.email.MailService field com.ge.appl.service.fs.manager.cancel.consumer.CancelAppointmentImpl.mailService to $Proxy35
    at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredFieldElement.inject(AutowiredAnnotationBeanPostProcessor.java:502)
    at org.springframework.beans.factory.annotation.InjectionMetadata.inject(InjectionMetadata.java:84)
    at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor.postProcessPropertyValues(AutowiredAnnotationBeanPostProcessor.java:282)
    ... 28 more
Caused by: java.lang.IllegalArgumentException: Can not set com.ge.appl.service.fs.manager.email.MailService field com.ge.appl.service.fs.manager.cancel.consumer.CancelAppointmentImpl.mailService to $Proxy35
    at sun.reflect.UnsafeFieldAccessorImpl.throwSetIllegalArgumentException(UnsafeFieldAccessorImpl.java:146)
    at sun.reflect.UnsafeFieldAccessorImpl.throwSetIllegalArgumentException(UnsafeFieldAccessorImpl.java:150)
    at sun.reflect.UnsafeObjectFieldAccessorImpl.set(UnsafeObjectFieldAccessorImpl.java:63)
    at java.lang.reflect.Field.set(Field.java:657)
    at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredFieldElement.inject(AutowiredAnnotationBeanPostProcessor.java:498)
    ... 30 more

The class where the autowire is done looks like

@Component("cancelAppointment")
public class CancelAppointmentImpl extends AbstractCancelAppointment implements
    CancelAppointment {


@Autowired
private MailService mailService;



@Override
public CancelAppointmentCriteria cancelAppointment(
        final CancelAppointmentCriteria criteria) throws Exception {
       // do something
       try {                      
            mailService.sendMail();
           } catch (Exception e) {
    // handle exception
 }

} }

Upvotes: 4

Views: 3669

Answers (1)

Bassem Reda Zohdy
Bassem Reda Zohdy

Reputation: 12942

I'm facing same issue, I think @EnableAsync is converting any component using @Async to proxy implementing same interfaces used by this component class, so when make autowire with concrete class will face type conflict between this concrete class and proxy, as work around you can use autowire on interface and use @Qualifier to specify bean.

Upvotes: 6

Related Questions