2011-09-26 3 views
13

J'utilise Spring 3 avec Hibernate 3. J'essaie de configurer la transaction déclarative de Spring, mais peu importe ce que j'essaie, la transaction Spring ne démarre pas.Spring @Transaction ne démarre pas les transactions

Voici ma configuration

fichier: applicationContext-hibernate.xml

<tx:annotation-driven transaction-manager="txManager" /> 

<bean id="txManager" class="org.springframework.orm.hibernate3.HibernateTransactionManager"> 
<property name="sessionFactory" ref="sessionFactory" /> 
</bean> 

<bean id="mdbDataSource" class="org.apache.commons.dbcp.BasicDataSource"> 
... 
</bean> 

<bean id="sessionFactory" class="org.springframework.orm.hibernate3.annotation.AnnotationSessionFactoryBean"> 
<property name="dataSource" ref="mdbDataSource" /> 
    <property name="annotatedClasses"> 
..... 
</bean> 

J'ai un ServiceLocatorImpl de classe qui implémente l'interface ServiceLocator

@Service("serviceLocator") 
@Transactional 
public class ServiceLocatorImpl implements ApplicationContextAware, Serializable, ServletContextAware, ServiceLocator { 
public ResultObject executeService(Map objArgs) 
{ 
     if(TransactionSynchronizationManager.isActualTransactionActive()) { 
      LOGGER.debug("ServiceLocator:executeService - Active transaction found"); 
     } else { 
     LOGGER.error("No active transaction found"); 
     } 
     ...... 
} 
    .... 
} 

Il me semble que toute ma configuration est correct. Mais lorsque la méthode executeService est appelée, TransactionSynchronizationManager.isActualTransactionActive() renvoie toujours false.

S'il vous plaît aidez-moi à résoudre ce problème. Faites-moi savoir si d'autres informations sont requises.

Mise à jour: J'ai câblé la ServiceLocator dans l'une des autres classes, comme suit:

@Autowired 
private ServiceLocator serviceLocator; // ServiceLocator is interface 

J'utilise la version Spring 3.0.0. ExecuteService() executeService() est une méthode définie dans l'interface ServiceLocator.

J'ai mis à jour le code pour lancer une exception au lieu de simplement enregistrer une erreur. Voici la trace de la pile, je ne vois aucune création de proxy dans cette trace. S'il vous plaît aider.

java.lang.RuntimeException: No active transaction found 
at com.nihilent.venice.common.service.ServiceLocatorImpl.logTransactionStatus(ServiceLocatorImpl.java:102) 
at com.nihilent.venice.common.service.ServiceLocatorImpl.executeService(ServiceLocatorImpl.java:47) 
at com.nihilent.venice.web.controller.CommonController.handleRequest(CommonController.java:184) 
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) 
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39) 
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25) 
at java.lang.reflect.Method.invoke(Method.java:597) 
at org.springframework.web.bind.annotation.support.HandlerMethodInvoker.doInvokeMethod(HandlerMethodInvoker.java:710) 
at org.springframework.web.bind.annotation.support.HandlerMethodInvoker.invokeHandlerMethod(HandlerMethodInvoker.java:167) 
at org.springframework.web.servlet.mvc.annotation.AnnotationMethodHandlerAdapter.invokeHandlerMethod(AnnotationMethodHandlerAdapter.java:414) 
at org.springframework.web.servlet.mvc.annotation.AnnotationMethodHandlerAdapter.handle(AnnotationMethodHandlerAdapter.java:402) 
at org.springframework.web.servlet.DispatcherServlet.doDispatch(DispatcherServlet.java:771) 
at org.springframework.web.servlet.DispatcherServlet.doService(DispatcherServlet.java:716) 
at org.springframework.web.servlet.FrameworkServlet.processRequest(FrameworkServlet.java:647) 
at org.springframework.web.servlet.FrameworkServlet.doGet(FrameworkServlet.java:552) 
at javax.servlet.http.HttpServlet.service(HttpServlet.java:617) 
at javax.servlet.http.HttpServlet.service(HttpServlet.java:717) 
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:290) 
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206) 
at org.tuckey.web.filters.urlrewrite.RuleChain.handleRewrite(RuleChain.java:176) 
at org.tuckey.web.filters.urlrewrite.RuleChain.doRules(RuleChain.java:145) 
at org.tuckey.web.filters.urlrewrite.UrlRewriter.processRequest(UrlRewriter.java:92) 
at org.tuckey.web.filters.urlrewrite.UrlRewriteFilter.doFilter(UrlRewriteFilter.java:381) 
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:235) 
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206) 
at org.apache.catalina.core.ApplicationDispatcher.invoke(ApplicationDispatcher.java:646) 
at org.apache.catalina.core.ApplicationDispatcher.processRequest(ApplicationDispatcher.java:436) 
at org.apache.catalina.core.ApplicationDispatcher.doForward(ApplicationDispatcher.java:374) 
at org.apache.catalina.core.ApplicationDispatcher.forward(ApplicationDispatcher.java:302) 
at org.apache.jasper.runtime.PageContextImpl.doForward(PageContextImpl.java:709) 
at org.apache.jasper.runtime.PageContextImpl.forward(PageContextImpl.java:680) 
at org.apache.jsp.index_jsp._jspService(index_jsp.java:57) 
at org.apache.jasper.runtime.HttpJspBase.service(HttpJspBase.java:70) 
at javax.servlet.http.HttpServlet.service(HttpServlet.java:717) 
at org.apache.jasper.servlet.JspServletWrapper.service(JspServletWrapper.java:386) 
at org.apache.jasper.servlet.JspServlet.serviceJspFile(JspServlet.java:313) 
at org.apache.jasper.servlet.JspServlet.service(JspServlet.java:260) 
at javax.servlet.http.HttpServlet.service(HttpServlet.java:717) 
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:290) 
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206) 
at org.tuckey.web.filters.urlrewrite.RuleChain.handleRewrite(RuleChain.java:176) 
at org.tuckey.web.filters.urlrewrite.RuleChain.doRules(RuleChain.java:145) 
at org.tuckey.web.filters.urlrewrite.UrlRewriter.processRequest(UrlRewriter.java:92) 
at org.tuckey.web.filters.urlrewrite.UrlRewriteFilter.doFilter(UrlRewriteFilter.java:381) 
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:235) 
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206) 
at com.nihilent.venice.web.filter.DyanamicResponseHeaderFilter.doFilter(DyanamicResponseHeaderFilter.java:33) 
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:235) 
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206) 
at com.opensymphony.module.sitemesh.filter.PageFilter.parsePage(PageFilter.java:118) 
at com.opensymphony.module.sitemesh.filter.PageFilter.doFilter(PageFilter.java:52) 
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:235) 
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206) 
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:343) 
at org.springframework.security.web.access.intercept.FilterSecurityInterceptor.invoke(FilterSecurityInterceptor.java:109) 
at org.springframework.security.web.access.intercept.FilterSecurityInterceptor.doFilter(FilterSecurityInterceptor.java:83) 
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:355) 
at org.springframework.security.web.access.ExceptionTranslationFilter.doFilter(ExceptionTranslationFilter.java:97) 
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:355) 
at org.springframework.security.web.session.SessionManagementFilter.doFilter(SessionManagementFilter.java:100) 
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:355) 
at org.springframework.security.web.authentication.AnonymousAuthenticationFilter.doFilter(AnonymousAuthenticationFilter.java:78) 
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:355) 
at org.springframework.security.web.servletapi.SecurityContextHolderAwareRequestFilter.doFilter(SecurityContextHolderAwareRequestFilter.java:54) 
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:355) 
at org.springframework.security.web.savedrequest.RequestCacheAwareFilter.doFilter(RequestCacheAwareFilter.java:35) 
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:355) 
at org.springframework.security.web.authentication.AbstractAuthenticationProcessingFilter.doFilter(AbstractAuthenticationProcessingFilter.java:188) 
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:355) 
at org.springframework.security.web.authentication.AbstractAuthenticationProcessingFilter.doFilter(AbstractAuthenticationProcessingFilter.java:188) 
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:355) 
at org.springframework.security.web.context.SecurityContextPersistenceFilter.doFilter(SecurityContextPersistenceFilter.java:79) 
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:355) 
at org.springframework.security.web.FilterChainProxy.doFilter(FilterChainProxy.java:149) 
at org.springframework.web.filter.DelegatingFilterProxy.invokeDelegate(DelegatingFilterProxy.java:237) 
at org.springframework.web.filter.DelegatingFilterProxy.doFilter(DelegatingFilterProxy.java:167) 
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:235) 
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206) 
at com.nihilent.venice.web.filter.RequestFilter.doFilter(RequestFilter.java:44) 
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:235) 
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206) 
at org.springframework.web.filter.CharacterEncodingFilter.doFilterInternal(CharacterEncodingFilter.java:88) 
at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:76) 
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:235) 
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206) 
at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:233) 
at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:191) 
at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:127) 
at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:102) 
at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:109) 
at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:298) 
at org.apache.coyote.http11.Http11Processor.process(Http11Processor.java:859) 
at org.apache.coyote.http11.Http11Protocol$Http11ConnectionHandler.process(Http11Protocol.java:588) 
at org.apache.tomcat.util.net.JIoEndpoint$Worker.run(JIoEndpoint.java:489) 
at java.lang.Thread.run(Thread.java:619) 

mise à jour [Résolu] Je suis la question fixe. Avant de donner la réponse comme elle a été fixée, je dois fournir plus d'informations. J'utilise Spring MVC dans mon projet. Le contrôle DispatchServlet est configuré dans le fichier web.xml. Ce contrôleur frontal possède un fichier xml de configuration abc-servlet.xml (abc étant le nom du servlet dans web.xml). J'ai d'autres fichiers de configuration de ressort qui sont définis comme context-param dans web.xml. L'un des fichiers est le fichier applicationContext-hibernate.xml. J'ai défini txManager et <tx:annotation-driven /> dans le fichier applicationContext-hibernate.xml. Aujourd'hui, je me demandais si le travail @Autowired et @Transactional avec ensemble, donc je Google les informations, et trouvé ce fil

http://forum.springsource.org/showthread.php?48815-Repository-Autowired-Transaction-not-returning-proxy-and-causes-exception

Le discours de discussion sur le même problème, et cela permet de résoudre le problème.

I implemented one of the suggestion and added <tx:annotation-driven .../> to my servlet's application context xml and it fixes the problem.

pensant que j'ai aussi déplacé mon <tx:annotation-driven /> dans le fichier abc-servlet.xml et cela a fonctionné.

Mes journaux sont maintenant shoulding les messages requis:

[venice] DEBUG [http-8080-1] 27 Sep 2011 14:24:06,312 ServiceLocatorImpl.logTransactionStatus(100) | ServiceLocator:executeService - Active transaction found

Merci à tous pour aider. Peut être cette information sera utile à quelqu'un. Je voudrais toujours entendre parler de l'explication comme pourquoi cela ne fonctionnait pas plus tôt.

+0

Est-ce que 'executeService()' implémente une méthode définie dans 'ServiceLocator'? Pouvez-vous lancer une exception de cette méthode au lieu de consigner une erreur et coller la trace de la pile? Je veux voir si l'aspect de la transaction est sur la pile. Veuillez également fournir la version exacte du printemps. –

+0

Pouvez-vous montrer comment la méthode est appelée? Aussi pouvez-vous vérifier quel est le type d'instance de ServiceLocator, est-ce une instance de proxy? –

+0

J'ai mis à jour la question avec la piste de pile requise. Comme mis à jour, j'injecte l'instance 'ServiceLocator' dans le bean appelant. 'executeService()' est défini dans l'interface 'ServiceLocator'. –

Répondre

4

Je dirais que vous essayez de faire quelque chose comme:

ServiceLocator locator = new ServiceLocatorImpl(); 
... 
locator.executeService(someMap); 

et étant alors surpris qu'il n'y a pas de transaction. La gestion des transactions et tous les autres services Spring s'appliquent uniquement aux beans dans le contexte d'application *. Vous devez obtenir votre instance du contexte d'une façon ou d'une autre au lieu d'en instancier une seule. Ou bien votre localisateur de beans se trouve dans un contexte d'application distinct de celui où vous déclarez tx:annotation-driven.

* Sauf si vous utilisez AspectJ build- or load-time bytecode weaving avec Spring.

Modifier: Le problème était exactement ce que j'ai dit (la deuxième partie). Vous créez deux contextes d'application. Vous étiez en train de créer votre ServiceLocator dans le premier, mais vous avez uniquement activé les transactions basées sur des annotations dans le second. Vous semblez ne pas comprendre les limites entre les contextes. Généralement - au moins dans mon expérience - les beans "business", comme votre ServiceLocator, vivent dans le contexte racine, qui est celui qui a été démarré par le ContextLoaderListener et configuré via contextConfigLocation. Les contrôleurs et autres beans qui configurent ou sont utilisés par un DispatcherServlet vivent dans un autre contexte associé à ce servlet configuré par le fichier *-servlet.xml. Ce contexte devient un contexte enfant du contexte racine, et les beans qu'il contient peuvent être injectés avec des beans à partir du contexte racine, mais pas vice versa. De mon point de vue, vous avez encore pire que par le passé en ajoutant tx:annotation-driven au contexte enfant associé à votre DispatcherServlet. Au lieu de cela, vous devez vous assurer que ServiceLocator est créé dans le contexte racine, où les services transactionnels sont déjà disponibles et où ils appartiennent.

+0

Je n'instancie pas le ServiceLocator, mais j'injecte le bean du localisateur de service. Les informations d'appel sont mises à jour dans l'article d'origine. –

+0

@ user746528: Mise à jour de ma réponse –

1

Vous devez simplement renommer votre "txManager" en "transactionManager". De la JavaDoc de EnableTransactionManagement:

... dans le cas XML, le nom est "transactionManager". Le <tx:annotation-driven/> est câblé pour rechercher par défaut un bean nommé "transactionManager" ...

Questions connexes