Beans do VRaptor no Spring

Bom dia!!

Eu li o changelog do vraptor 3.3.0 e vi que os beans agora se enxergam…

era algo que eu necessitava no final do ano passado e acabei resolvendo junto com o Douglas via requisicoes http do spring para o controller do vraptor…

O Douglas Campos que me falou que essa junção de beans seria feito…

e agora os beans se enxergam… como eu faço para no bean do spring poder utilizar um bean do vraptor??

Sendo que meus DAOs no vraptor são acessador via injeção da interface repository

public class VerificaLogados {

	private final SessionFactoryCreator sessionFactoryCreator;
	private final WatchDogReseter watchDogReseter;

	@Autowired
	public VerificaLogados(SessionFactoryCreator sessionFactoryCreator,
			WatchDogReseter watchDogReseter) {
		this.sessionFactoryCreator = sessionFactoryCreator;
		this.watchDogReseter = watchDogReseter;
	}
	
	 
	 
	public void check() {
		sessionFactoryCreator.create();
		Session session = sessionFactoryCreator.getInstance().openSession();
		HistoricoLoginDAO historicoLoginDAO = new HistoricoLoginDAO(session);
		boolean haAlguemLogado = historicoLoginDAO.existeAlguemLogado();        <---- não queria utilizar assim... queria chamar a interface repository para usar o DAO
		if (!haAlguemLogado) {
		SystemConfigDAO systemConfigDAO = new SystemConfigDAO(session);
			SystemConfig systemConfig = systemConfigDAO.getConfig();
			String supSeg = systemConfig.getEmailSupSeg();
			if (!((supSeg == null) || (supSeg.equals("")))) {
				enviaEmail(supSeg);
			}
			acionaGiroFlex();
		}
		session.close();
		sessionFactoryCreator.destroy();
	}

}

funciona, mas vc precisa marcar as dependências como optional no bean do spring (pq o vraptor dá um reload no contexto pra registrar suas próprias classes)

Oi Lucas, valeu pela ajuda mais uma vez…

Então… eu coloquei no bean “class VerificaLogado” assim…


private HistoricoLoginRepository historicoLoginRepository;

	@Autowired(required = false)
	public void setHistoricoLoginRepository(
			HistoricoLoginRepository historicoLoginRepository) {
		this.historicoLoginRepository = historicoLoginRepository;
	}

O que me gerou o erro abaixo… lembrando que eu tenho um @Configuration que seta as dependencias do contrutor…

E estou usando dependencia por setter para esse DAO… que tem por padrao scope de request certo?

Até por isso deve ter me gerado o codigo abaixo…


GRAVE: Exception starting filter vraptor
org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'verificaLogados': Injection of autowired dependencies failed; nested exception is org.springframework.beans.factory.BeanCreationException: Could not autowire method: public void br.com.evertical.cftv.manager.service.VerificaLogados.setHistoricoLoginRepository(br.com.evertical.cftv.manager.repository.HistoricoLoginRepository); nested exception is org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'historicoLoginDAO': Scope 'request' is not active for the current thread; consider defining a scoped proxy for this bean if you intend to refer to it from a singleton; nested exception is java.lang.IllegalStateException: No thread-bound request found: Are you referring to request attributes outside of an actual web request, or processing a request outside of the originally receiving thread? If you are actually operating within a web request and still receive this message, your code is probably running outside of DispatcherServlet/DispatcherPortlet: In this case, use RequestContextListener or RequestContextFilter to expose the current request.
	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 br.com.caelum.vraptor.ioc.spring.SpringBasedContainer.start(SpringBasedContainer.java:106)
	at br.com.caelum.vraptor.ioc.spring.SpringProvider.start(SpringProvider.java:87)
	at br.com.caelum.vraptor.VRaptor.init(VRaptor.java:110)
	at br.com.caelum.vraptor.VRaptor.init(VRaptor.java:103)
	at org.apache.catalina.core.ApplicationFilterConfig.getFilter(ApplicationFilterConfig.java:275)
	at org.apache.catalina.core.ApplicationFilterConfig.setFilterDef(ApplicationFilterConfig.java:397)
	at org.apache.catalina.core.ApplicationFilterConfig.<init>(ApplicationFilterConfig.java:108)
	at org.apache.catalina.core.StandardContext.filterStart(StandardContext.java:3709)
	at org.apache.catalina.core.StandardContext.start(StandardContext.java:4363)
	at org.apache.catalina.core.ContainerBase.start(ContainerBase.java:1045)
	at org.apache.catalina.core.StandardHost.start(StandardHost.java:719)
	at org.apache.catalina.core.ContainerBase.start(ContainerBase.java:1045)
	at org.apache.catalina.core.StandardEngine.start(StandardEngine.java:443)
	at org.apache.catalina.core.StandardService.start(StandardService.java:516)
	at org.apache.catalina.core.StandardServer.start(StandardServer.java:710)
	at org.apache.catalina.startup.Catalina.start(Catalina.java:578)
	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.apache.catalina.startup.Bootstrap.start(Bootstrap.java:288)
	at org.apache.catalina.startup.Bootstrap.main(Bootstrap.java:413)
Caused by: org.springframework.beans.factory.BeanCreationException: Could not autowire method: public void br.com.evertical.cftv.manager.service.VerificaLogados.setHistoricoLoginRepository(br.com.evertical.cftv.manager.repository.HistoricoLoginRepository); nested exception is org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'historicoLoginDAO': Scope 'request' is not active for the current thread; consider defining a scoped proxy for this bean if you intend to refer to it from a singleton; nested exception is java.lang.IllegalStateException: No thread-bound request found: Are you referring to request attributes outside of an actual web request, or processing a request outside of the originally receiving thread? If you are actually operating within a web request and still receive this message, your code is probably running outside of DispatcherServlet/DispatcherPortlet: In this case, use RequestContextListener or RequestContextFilter to expose the current request.
	at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredMethodElement.inject(AutowiredAnnotationBeanPostProcessor.java:589)
	at org.springframework.beans.factory.annotation.InjectionMetadata.inject(InjectionMetadata.java:84)
	at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor.postProcessPropertyValues(AutowiredAnnotationBeanPostProcessor.java:282)
	... 32 more
Caused by: org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'historicoLoginDAO': Scope 'request' is not active for the current thread; consider defining a scoped proxy for this bean if you intend to refer to it from a singleton; nested exception is java.lang.IllegalStateException: No thread-bound request found: Are you referring to request attributes outside of an actual web request, or processing a request outside of the originally receiving thread? If you are actually operating within a web request and still receive this message, your code is probably running outside of DispatcherServlet/DispatcherPortlet: In this case, use RequestContextListener or RequestContextFilter to expose the current request.
	at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:339)
	at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:190)
	at org.springframework.beans.factory.support.DefaultListableBeanFactory.findAutowireCandidates(DefaultListableBeanFactory.java:844)
	at org.springframework.beans.factory.support.DefaultListableBeanFactory.doResolveDependency(DefaultListableBeanFactory.java:786)
	at org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:703)
	at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredMethodElement.inject(AutowiredAnnotationBeanPostProcessor.java:547)
	... 34 more
Caused by: java.lang.IllegalStateException: No thread-bound request found: Are you referring to request attributes outside of an actual web request, or processing a request outside of the originally receiving thread? If you are actually operating within a web request and still receive this message, your code is probably running outside of DispatcherServlet/DispatcherPortlet: In this case, use RequestContextListener or RequestContextFilter to expose the current request.
	at org.springframework.web.context.request.RequestContextHolder.currentRequestAttributes(RequestContextHolder.java:131)
	at org.springframework.web.context.request.AbstractRequestAttributesScope.get(AbstractRequestAttributesScope.java:40)
	at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:325)
	... 39 more

Daí fui tentar um scope proxy e fiz o seguinte:

        @Autowired(required = false)
	@Scope(proxyMode = ScopedProxyMode.DEFAULT, value = "singleton")     <----
	public void setHistoricoLoginRepository(
			HistoricoLoginRepository historicoLoginRepository) {
		this.historicoLoginRepository = historicoLoginRepository;
	}

e a stack continua…


GRAVE: Exception starting filter vraptor
org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'verificaLogados': Injection of autowired dependencies failed; nested exception is org.springframework.beans.factory.BeanCreationException: Could not autowire method: public void br.com.evertical.cftv.manager.service.VerificaLogados.setHistoricoLoginRepository(br.com.evertical.cftv.manager.repository.HistoricoLoginRepository); nested exception is org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'historicoLoginDAO': Scope 'request' is not active for the current thread; consider defining a scoped proxy for this bean if you intend to refer to it from a singleton; nested exception is java.lang.IllegalStateException: No thread-bound request found: Are you referring to request attributes outside of an actual web request, or processing a request outside of the originally receiving thread? If you are actually operating within a web request and still receive this message, your code is probably running outside of DispatcherServlet/DispatcherPortlet: In this case, use RequestContextListener or RequestContextFilter to expose the current request.
	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 br.com.caelum.vraptor.ioc.spring.SpringBasedContainer.start(SpringBasedContainer.java:106)
	at br.com.caelum.vraptor.ioc.spring.SpringProvider.start(SpringProvider.java:87)
	at br.com.caelum.vraptor.VRaptor.init(VRaptor.java:110)
	at br.com.caelum.vraptor.VRaptor.init(VRaptor.java:103)
	at org.apache.catalina.core.ApplicationFilterConfig.getFilter(ApplicationFilterConfig.java:275)
	at org.apache.catalina.core.ApplicationFilterConfig.setFilterDef(ApplicationFilterConfig.java:397)
	at org.apache.catalina.core.ApplicationFilterConfig.<init>(ApplicationFilterConfig.java:108)
	at org.apache.catalina.core.StandardContext.filterStart(StandardContext.java:3709)
	at org.apache.catalina.core.StandardContext.start(StandardContext.java:4363)
	at org.apache.catalina.core.ContainerBase.start(ContainerBase.java:1045)
	at org.apache.catalina.core.StandardHost.start(StandardHost.java:719)
	at org.apache.catalina.core.ContainerBase.start(ContainerBase.java:1045)
	at org.apache.catalina.core.StandardEngine.start(StandardEngine.java:443)
	at org.apache.catalina.core.StandardService.start(StandardService.java:516)
	at org.apache.catalina.core.StandardServer.start(StandardServer.java:710)
	at org.apache.catalina.startup.Catalina.start(Catalina.java:578)
	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.apache.catalina.startup.Bootstrap.start(Bootstrap.java:288)
	at org.apache.catalina.startup.Bootstrap.main(Bootstrap.java:413)
Caused by: org.springframework.beans.factory.BeanCreationException: Could not autowire method: public void br.com.evertical.cftv.manager.service.VerificaLogados.setHistoricoLoginRepository(br.com.evertical.cftv.manager.repository.HistoricoLoginRepository); nested exception is org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'historicoLoginDAO': Scope 'request' is not active for the current thread; consider defining a scoped proxy for this bean if you intend to refer to it from a singleton; nested exception is java.lang.IllegalStateException: No thread-bound request found: Are you referring to request attributes outside of an actual web request, or processing a request outside of the originally receiving thread? If you are actually operating within a web request and still receive this message, your code is probably running outside of DispatcherServlet/DispatcherPortlet: In this case, use RequestContextListener or RequestContextFilter to expose the current request.
	at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredMethodElement.inject(AutowiredAnnotationBeanPostProcessor.java:589)
	at org.springframework.beans.factory.annotation.InjectionMetadata.inject(InjectionMetadata.java:84)
	at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor.postProcessPropertyValues(AutowiredAnnotationBeanPostProcessor.java:282)
	... 32 more
Caused by: org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'historicoLoginDAO': Scope 'request' is not active for the current thread; consider defining a scoped proxy for this bean if you intend to refer to it from a singleton; nested exception is java.lang.IllegalStateException: No thread-bound request found: Are you referring to request attributes outside of an actual web request, or processing a request outside of the originally receiving thread? If you are actually operating within a web request and still receive this message, your code is probably running outside of DispatcherServlet/DispatcherPortlet: In this case, use RequestContextListener or RequestContextFilter to expose the current request.
	at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:339)
	at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:190)
	at org.springframework.beans.factory.support.DefaultListableBeanFactory.findAutowireCandidates(DefaultListableBeanFactory.java:844)
	at org.springframework.beans.factory.support.DefaultListableBeanFactory.doResolveDependency(DefaultListableBeanFactory.java:786)
	at org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:703)
	at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredMethodElement.inject(AutowiredAnnotationBeanPostProcessor.java:547)
	... 34 more
Caused by: java.lang.IllegalStateException: No thread-bound request found: Are you referring to request attributes outside of an actual web request, or processing a request outside of the originally receiving thread? If you are actually operating within a web request and still receive this message, your code is probably running outside of DispatcherServlet/DispatcherPortlet: In this case, use RequestContextListener or RequestContextFilter to expose the current request.
	at org.springframework.web.context.request.RequestContextHolder.currentRequestAttributes(RequestContextHolder.java:131)
	at org.springframework.web.context.request.AbstractRequestAttributesScope.get(AbstractRequestAttributesScope.java:40)
	at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:325)
	... 39 more

Any ideas?

não conheço direito essa parte do spring, mas com o scoped proxy deveria funcionar…

esse é o jeito certo? a anotação tem que estar no getter mesmo?

aparentemente existe uma anotação @ScopedProxy:
http://static.springsource.org/spring-javaconfig/docs/1.0.0.M4/reference/html/ch02s02.html
2.2.5.2
http://static.springsource.org/spring/docs/2.5.x/reference/beans.html#beans-factory-scopes-other-injection

isso tem que ser anotado na classe que vai ser proxiada, pelo que eu entendi…

enfim, o caminho é por aí :wink:

é entao… na versao 3 do spring tiraram o @ScopeProxy e parece que substituiram pelo @Scope(proxyMode = ScopedProxyMode.DEFAULT, value = “singleton”)

Tentei anotar o @Bean do @Configuration com isso… nao deu… tentei anotar no setter… tb nao foi… haha

uma hora vai… espero

É… ainda não foi… alguem conseguiu??

a classe do VRaptor que registra o bean no spring é essa:

se vc dar uma olhada no método applyScopeOn, tem uma parte onde ele gera o scopedProxy se o modo for TARGET_CLASS…

ou seja, teoricamente se vc anotar o @Component do vraptor (a classe!) com @Scope(proxyMode = ScopedProxyMode.TARGET_CLASS) deve funcionar