I have a Spring 3.2.8 application in which I have a specific case where I want to start a transaction inside a context listener.
I know and understand that the listener is not a Spring bean, so I'm not quite sure how to mark my method as @Transactional. I tried labeling the bean as @Configurable, but that doesn't seem like a trick; I assume the b / c application server creates this bean before the Spring context is loaded.
I checked the status of the transaction with TransactionAspectSupport.currentTransactionStatus(), but I get a throw NoTransactionExceptionthat occurs when there is no managed open transaction.
Is there anything inside Spring that will allow me to mark this method as part of a transaction?
@Configurable
public class PatchEngineContextListener implements ServletContextListener{
private static final Logger logger = LoggerFactory.getLogger(PatchEngineContextListener.class);
private ApplicationContext appContext;
@Autowired private PatchService patchService;
@Autowired private PatchEngine patchEngine;
@Override
@Transactional
public void contextInitialized(ServletContextEvent sce) {
appContext = WebApplicationContextUtils.getWebApplicationContext(sce.getServletContext());
appContext.getAutowireCapableBeanFactory().autowireBean(this);
logger.info( TransactionAspectSupport.currentTransactionStatus().toString() );
try {
setPatchEngineUser();
patchEngine.execute();
clearPatchEngineUser();
} catch (Exception e) {
throw new RuntimeException(e);
}
}
}
Stacktrace error:
org.springframework.transaction.NoTransactionException: No transaction aspect-managed TransactionStatus in scope
at org.springframework.transaction.interceptor.TransactionAspectSupport.currentTransactionStatus(TransactionAspectSupport.java:110)
at com.ia.system.patch.engine.PatchEngineContextListener.contextInitialized(PatchEngineContextListener.java:92)
at org.apache.catalina.core.StandardContext.listenerStart(StandardContext.java:4939)
at org.apache.catalina.core.StandardContext.startInternal(StandardContext.java:5434)
at org.apache.catalina.util.LifecycleBase.start(LifecycleBase.java:150)
at org.apache.catalina.core.ContainerBase$StartChild.call(ContainerBase.java:1559)
at org.apache.catalina.core.ContainerBase$StartChild.call(ContainerBase.java:1549)
at java.util.concurrent.FutureTask.run(FutureTask.java:262)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1145)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:615)
at java.lang.Thread.run(Thread.java:724)
web.xml:
<listener>
<listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
</listener>
<listener>
<listener-class>com.ia.system.patch.engine.PatchEngineContextListener</listener-class>
</listener>
applicationContext.xml:
<context:spring-configured/>