Andreas Andersen Kjaer opened SPR-15102 and commented
I am using Spring MVC for REST communication and Hibernate for handling JPA annotations.
I run local system tests with an in memory database and MockMvc
.
I have created a class similar to this:
public class BaseEntityListener {
@Autowired
private MyService myService;
private boolean springBeansLoaded = false;
@PrePersist
@PreUpdate
public void updateRowWithTransactionalFields(BaseEntity baseEntity) {
ensureSpringBeansLoaded();
.. more code
}
private void ensureSpringBeansLoaded() {
if (!springBeansLoaded) {
SpringBeanAutowiringSupport.processInjectionBasedOnCurrentContext(this);
springBeansLoaded = true;
}
}
}
And I have added the class above as an entity listener:
@MappedSuperclass
@EntityListeners(BaseEntityListener.class)
public abstract class BaseEntity {
...
}
My Entities extend BaseEntity
.
SpringBeanAutowiringSupport.processInjectionBasedOnCurrentContext(this)
works fine when I deploy to an application server. However, when using MockMvc
, it does not work. myService
will never be assigned as SpringBeanAutowiringSupport.processInjectionBasedOnCurrentContext
is not capable of finding the application context.
Is this a bug?
Affects: 4.3 GA
Issue Links: - #18264 javax.persistence.EntityListeners annotation generates 2 beans, one without autowired fields
Comment From: spring-projects-issues
Sam Brannen commented
No, this is not technically a bug.
SpringBeanAutowiringSupport
uses org.springframework.web.context.ContextLoader.getCurrentWebApplicationContext()
to look up the current WebApplicationContext
.
However, org.springframework.web.context.ContextLoader
is only used if configured via web.xml
(i.e., when running in a Servlet container). As stated in the documentation, the Spring MVC Test Framework runs out-of-container. Thus, org.springframework.web.context.ContextLoader
is not used in tests, and consequently SpringBeanAutowiringSupport
is not supported.
I have reworded the title of this JIRA issue to reflect this.
Comment From: spring-projects-issues
Sam Brannen commented
FWIW, there are alternative approaches for having Spring perform dependency injection on your entity listener, approaches that do not require that your application run in a deployed Servlet container.
For example: https://deepintojee.wordpress.com/2012/02/05/spring-managed-event-listeners-with-jpa/
See also the discussion in the comments section here: #18264
Comment From: spring-projects-issues
Andreas Andersen Kjaer commented
Thank you for the help :)
Comment From: snicoll
There has been some improvements in that area, in particular with Spring implementing BeanContainer
from Hibernate that is a more reliable way to do the above.