Spring Async not allowing use of autowired beans
Object-Oriented Design practice on Codemia
Turn requirements into classes, and defend the design, on the problems that come up in OOD rounds.
Introduction
When a Spring @Async method seems unable to use an autowired bean, the problem is usually not dependency injection itself. In most cases, the real issue is that the async method is not running through a Spring proxy, the class was created manually with new, or async support was never enabled. Once the method is invoked on a real Spring-managed bean, autowired dependencies work normally.
@Async Works Only on Spring-Managed Beans
Spring implements @Async through proxies. That means the method has to be called on a bean created by the container, not on an object you instantiated yourself.
Correct setup:
If ReportService is a real Spring bean, mailService is injected before the async method runs. There is nothing special about autowiring here.
Enable Async Support Explicitly
The next common issue is forgetting @EnableAsync. Without it, Spring never creates the async proxy layer.
If this annotation is missing, the method may still run, but it runs synchronously and none of the async behavior is applied.
Avoid Self-Invocation
Another frequent trap is calling the @Async method from another method in the same class. That bypasses the Spring proxy, so the async interceptor never gets a chance to run.
Problematic pattern:
startJob() calls runAsyncTask() directly on this, not through the proxy. Move the async method into another bean and inject that bean instead.
This is one of the most important fixes when people think @Autowired "stops working" in async code.
Do Not Instantiate Beans Manually
If you write new ReportService() anywhere, Spring cannot inject dependencies into that instance. The autowired field or constructor dependency will be missing because the object never passed through the container.
Wrong:
Right:
Once the bean comes from Spring, autowiring and async proxies can both do their jobs.
Think About Thread Safety
Autowired beans are usually singleton beans. That is fine in async code as long as they are stateless or properly synchronized. The async method runs on another thread, so shared mutable state still needs the same care it would need anywhere else.
This matters most for:
- mutable in-memory caches
- request-scoped data accessed outside the request thread
- non-thread-safe helpers stored as singletons
The injection is not the danger. Unsafe shared state is.
Return a Useful Async Type
For fire-and-forget operations, void can work, but CompletableFuture is often better because it gives the caller a way to observe completion or failure.
This makes testing and error handling much clearer than hiding all outcomes in background threads.
Common Pitfalls
- Forgetting
@EnableAsync, so the async proxy is never created. - Calling an
@Asyncmethod from another method in the same class. - Instantiating the service with
newinstead of letting Spring create it. - Assuming autowired singleton beans are unsafe by default, when the real problem is shared mutable state.
- Returning
voideverywhere and making async errors harder to observe.
Summary
- '
@Autowiredbeans work in@Asyncmethods as long as the service is a real Spring-managed bean.' - '
@EnableAsyncmust be present for async proxies to exist.' - Self-invocation bypasses the proxy and is a common reason async behavior appears broken.
- Never create Spring services manually with
new. - Treat thread safety as a separate concern from dependency injection.
Related reading
- Spring Autowired usage
- Spring Beanname name vs Bean Qualifiername
- Spring Boot - inject map from application.yml
- Spring boot - Service class calling another Service class
- Spring Async vs completable future run async
- Spring Async without xml config
- Spring Batch - Remote Partitioning in Manager - Worker Environment - CSV Files
- Spring batch. How to chain multiple itemProcessors with different types?

OOD Fundamentals
Master object-oriented design from first principles, SOLID, design patterns, and classic interview problems with hands-on coding.
View the courseTrack what you have practised
A free account saves your progress, solutions and study plan across every problem on Codemia.
Object-Oriented Design practice on Codemia
Turn requirements into classes, and defend the design, on the problems that come up in OOD rounds.