2017-09-24 11 views
0

カスタムConstraintValidator内で@Autowiredアノテーションを取得しようとしています。Validation.xmlにSpringWebConstraintValidatorFactoryを追加するときのStackOverflowError

私はこのためにいくつかのソリューションを読んだが、どれも私がautowired ConstraintValidatorのインスタンスを作成するためのバネのorg.springframework.web.bind.support.SpringWebConstraintValidatorFactory を使用して休止状態を強制しようとして作業していません。

これは、ドキュメントが言うまさにだ:

パブリッククラスSpringWebConstraintValidatorFactory:

JSR-303 ConstraintValidatorFactory実装をautowired ConstraintValidatorのインスタンスを作成するための現行の春WebApplicationContextに委任していること。 SpringConstraintValidatorFactoryとは対照的に、このバリエーションは、標準のvalidation.xmlファイルで宣言的に使用するためのものです。 JAX-RSまたはJAX-WSと組み合わせて使用​​できます。

だから私はMETA-INF/validation.xmlに

<validation-config 
     xmlns="http://jboss.org/xml/ns/javax/validation/configuration" 
     xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
     xsi:schemaLocation="http://jboss.org/xml/ns/javax/validation/configuration" version="1.1"> 

    <constraint-validator-factory> 
     org.springframework.web.bind.support.SpringWebConstraintValidatorFactory 
    </constraint-validator-factory> 

</validation-config> 

を提供してきましたが、データが検証されたときに、私はここでjava.lang.StackOverflowErrorを

は、スタックトレースで取得:

org.springframework.web.util.NestedServletException: Handler dispatch failed; nested exception is java.lang.StackOverflowError 
    org.springframework.web.servlet.DispatcherServlet.doDispatch(DispatcherServlet.java:982) 
    org.springframework.web.servlet.DispatcherServlet.doService(DispatcherServlet.java:901) 
    org.springframework.web.servlet.FrameworkServlet.processRequest(FrameworkServlet.java:970) 
    org.springframework.web.servlet.FrameworkServlet.doPost(FrameworkServlet.java:872) 
    javax.servlet.http.HttpServlet.service(HttpServlet.java:661) 
    org.springframework.web.servlet.FrameworkServlet.service(FrameworkServlet.java:846) 
    javax.servlet.http.HttpServlet.service(HttpServlet.java:742) 
    org.apache.tomcat.websocket.server.WsFilter.doFilter(WsFilter.java:52) 
    org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:317) 
    org.springframework.security.web.access.intercept.FilterSecurityInterceptor.invoke(FilterSecurityInterceptor.java:127) 
    org.springframework.security.web.access.intercept.FilterSecurityInterceptor.doFilter(FilterSecurityInterceptor.java:91) 
    org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:331) 
    org.springframework.security.web.access.ExceptionTranslationFilter.doFilter(ExceptionTranslationFilter.java:114) 
    org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:331) 
    org.springframework.security.web.session.SessionManagementFilter.doFilter(SessionManagementFilter.java:137) 
    org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:331) 
    org.springframework.security.web.authentication.AnonymousAuthenticationFilter.doFilter(AnonymousAuthenticationFilter.java:111) 
    org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:331) 
    org.springframework.security.web.authentication.rememberme.RememberMeAuthenticationFilter.doFilter(RememberMeAuthenticationFilter.java:150) 
    org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:331) 
    org.springframework.security.web.servletapi.SecurityContextHolderAwareRequestFilter.doFilter(SecurityContextHolderAwareRequestFilter.java:170) 
    org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:331) 
    org.springframework.security.web.savedrequest.RequestCacheAwareFilter.doFilter(RequestCacheAwareFilter.java:63) 
    org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:331) 
    org.springframework.security.web.authentication.www.BasicAuthenticationFilter.doFilterInternal(BasicAuthenticationFilter.java:158) 
    org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107) 
    org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:331) 
    org.springframework.security.web.authentication.AbstractAuthenticationProcessingFilter.doFilter(AbstractAuthenticationProcessingFilter.java:200) 
    org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:331) 
    org.springframework.security.web.authentication.logout.LogoutFilter.doFilter(LogoutFilter.java:116) 
    org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:331) 
    org.springframework.security.web.header.HeaderWriterFilter.doFilterInternal(HeaderWriterFilter.java:64) 
    org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107) 
    org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:331) 
    org.springframework.security.web.context.request.async.WebAsyncManagerIntegrationFilter.doFilterInternal(WebAsyncManagerIntegrationFilter.java:56) 
    org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107) 
    org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:331) 
    org.springframework.security.web.context.SecurityContextPersistenceFilter.doFilter(SecurityContextPersistenceFilter.java:105) 
    org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:331) 
    org.springframework.security.web.FilterChainProxy.doFilterInternal(FilterChainProxy.java:214) 
    org.springframework.security.web.FilterChainProxy.doFilter(FilterChainProxy.java:177) 
    org.springframework.web.filter.DelegatingFilterProxy.invokeDelegate(DelegatingFilterProxy.java:346) 
    org.springframework.web.filter.DelegatingFilterProxy.doFilter(DelegatingFilterProxy.java:262) 
    org.springframework.web.filter.CharacterEncodingFilter.doFilterInternal(CharacterEncodingFilter.java:197) 
    org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107) 

この設定を行わないとアプリもうまく動作しません。最初からそう

は、私がautowired UserServiceのを使用するカスタム制約バリデータを持っている:

public class EmailValidator implements ConstraintValidator<ValidEmail, String> { 

    @Autowired 
    UserService userService; 

    public void initialize(ValidEmail constraint) { 
    } 

    public boolean isValid(String email, ConstraintValidatorContext context) { 
      return userService.isEmailAvailable(email); 
    } 
} 

そして、何奇妙なONLY完全に満たされた登録フォームとするときに私も触れていないテストを(実行しようとしています userServiceはautowiredできないため、nullです。たとえば、ユーザー名と電子メール、そのokey - 検証され、メッセージが定義されています。これはuserServiceが正しく呼び出されたことを意味しますが、有効なデータで完全な登録フォームを検証しようとするとuserServiceはnullです。時にはうまくいく、時にはそうでないこともある。少なくとも私が読んだように、それがautowiredされるべきではない場合、このケースでどのように検証される可能性がありますか?

私はisValid関数からreturn文をtrycatchすると、期待通りに動作しますが、テストでも正常ですが、それほどうまくありませんか?私はこれに対して通常の解決方法を提供したいと思います。だから私はConstraintValidatorFactoryを変更しようとした。しかし、多分それを修正する方法がありますか?

私はStackからすべてのソリューションを試したと思いますが、何も動作していません。

は、これは私のテストクラスが設定されている方法ですが、私はこれが事実であるとは思わない:

@RunWith(SpringJUnit4ClassRunner.class) 
@ContextConfiguration(locations = "classpath:/appTestconfig-root.xml") 
@WebAppConfiguration 
public class UserDAOTest { 
    ... 
} 

は、私が何をしないのですか?ここで

は、私は、検証の設定を変更しないときスタックトレースされています

javax.validation.ValidationException: HV000028: Unexpected exception during isValid call. 

    at org.hibernate.validator.internal.engine.constraintvalidation.ConstraintTree.validateSingleConstraint(ConstraintTree.java:449) 
    at org.hibernate.validator.internal.engine.constraintvalidation.ConstraintTree.validateConstraints(ConstraintTree.java:127) 
    at org.hibernate.validator.internal.engine.constraintvalidation.ConstraintTree.validateConstraints(ConstraintTree.java:87) 
    at org.hibernate.validator.internal.metadata.core.MetaConstraint.validateConstraint(MetaConstraint.java:73) 
    at org.hibernate.validator.internal.engine.ValidatorImpl.validateMetaConstraint(ValidatorImpl.java:616) 
    at org.hibernate.validator.internal.engine.ValidatorImpl.validateConstraint(ValidatorImpl.java:581) 
    at org.hibernate.validator.internal.engine.ValidatorImpl.validateConstraintsForSingleDefaultGroupElement(ValidatorImpl.java:527) 
    at org.hibernate.validator.internal.engine.ValidatorImpl.validateConstraintsForDefaultGroup(ValidatorImpl.java:495) 
    at org.hibernate.validator.internal.engine.ValidatorImpl.validateConstraintsForCurrentGroup(ValidatorImpl.java:460) 
    at org.hibernate.validator.internal.engine.ValidatorImpl.validateInContext(ValidatorImpl.java:410) 
    at org.hibernate.validator.internal.engine.ValidatorImpl.validate(ValidatorImpl.java:207) 
    at org.hibernate.cfg.beanvalidation.BeanValidationEventListener.validate(BeanValidationEventListener.java:116) 
    at org.hibernate.cfg.beanvalidation.BeanValidationEventListener.onPreInsert(BeanValidationEventListener.java:80) 
    at org.hibernate.action.internal.EntityInsertAction.preInsert(EntityInsertAction.java:205) 
    at org.hibernate.action.internal.EntityInsertAction.execute(EntityInsertAction.java:82) 
    at org.hibernate.engine.spi.ActionQueue.executeActions(ActionQueue.java:589) 
    at org.hibernate.engine.spi.ActionQueue.executeActions(ActionQueue.java:463) 
    at org.hibernate.event.internal.AbstractFlushingEventListener.performExecutions(AbstractFlushingEventListener.java:337) 
    at org.hibernate.event.internal.DefaultAutoFlushEventListener.onAutoFlush(DefaultAutoFlushEventListener.java:50) 
    at org.hibernate.internal.SessionImpl.autoFlushIfRequired(SessionImpl.java:1396) 
    at org.hibernate.internal.SessionImpl.list(SessionImpl.java:1481) 
    at org.hibernate.query.internal.AbstractProducedQuery.doList(AbstractProducedQuery.java:1445) 
    at org.hibernate.query.internal.AbstractProducedQuery.list(AbstractProducedQuery.java:1414) 
    at org.hibernate.query.internal.AbstractProducedQuery.uniqueResult(AbstractProducedQuery.java:1457) 
    at todolist.daos.UserDAOimpl.getUserByName(UserDAOimpl.java:25) 
    at todolist.daos.UserDAOTest.addUser(UserDAOTest.java:42) 
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) 
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62) 
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43) 
    at java.lang.reflect.Method.invoke(Method.java:498) 
    at org.junit.runners.model.FrameworkMethod$1.runReflectiveCall(FrameworkMethod.java:50) 
    at org.junit.internal.runners.model.ReflectiveCallable.run(ReflectiveCallable.java:12) 
    at org.junit.runners.model.FrameworkMethod.invokeExplosively(FrameworkMethod.java:47) 
    at org.junit.internal.runners.statements.RunBefores.evaluate(RunBefores.java:24) 
    at org.springframework.test.context.junit4.statements.RunBeforeTestMethodCallbacks.evaluate(RunBeforeTestMethodCallbacks.java:75) 
    at org.junit.internal.runners.statements.RunAfters.evaluate(RunAfters.java:27) 
    at org.springframework.test.context.junit4.statements.RunAfterTestMethodCallbacks.evaluate(RunAfterTestMethodCallbacks.java:86) 
    at org.springframework.test.context.junit4.statements.SpringRepeat.evaluate(SpringRepeat.java:84) 
    at org.junit.runners.ParentRunner.runLeaf(ParentRunner.java:325) 
    at org.springframework.test.context.junit4.SpringJUnit4ClassRunner.runChild(SpringJUnit4ClassRunner.java:252) 
    at org.springframework.test.context.junit4.SpringJUnit4ClassRunner.runChild(SpringJUnit4ClassRunner.java:94) 
    at org.junit.runners.ParentRunner$3.run(ParentRunner.java:290) 
    at org.junit.runners.ParentRunner$1.schedule(ParentRunner.java:71) 
    at org.junit.runners.ParentRunner.runChildren(ParentRunner.java:288) 
    at org.junit.runners.ParentRunner.access$000(ParentRunner.java:58) 
    at org.junit.runners.ParentRunner$2.evaluate(ParentRunner.java:268) 
    at org.springframework.test.context.junit4.statements.RunBeforeTestClassCallbacks.evaluate(RunBeforeTestClassCallbacks.java:61) 
    at org.springframework.test.context.junit4.statements.RunAfterTestClassCallbacks.evaluate(RunAfterTestClassCallbacks.java:70) 
    at org.junit.runners.ParentRunner.run(ParentRunner.java:363) 
    at org.springframework.test.context.junit4.SpringJUnit4ClassRunner.run(SpringJUnit4ClassRunner.java:191) 
    at org.junit.runner.JUnitCore.run(JUnitCore.java:137) 
    at com.intellij.junit4.JUnit4IdeaTestRunner.startRunnerWithArgs(JUnit4IdeaTestRunner.java:68) 
    at com.intellij.rt.execution.junit.IdeaTestRunner$Repeater.startRunnerWithArgs(IdeaTestRunner.java:47) 
    at com.intellij.rt.execution.junit.JUnitStarter.prepareStreamsAndStart(JUnitStarter.java:242) 
    at com.intellij.rt.execution.junit.JUnitStarter.main(JUnitStarter.java:70) 
Caused by: java.lang.NullPointerException 
    at todolist.validators.EmailValidator.isValid(EmailValidator.java:19) 
    at todolist.validators.EmailValidator.isValid(EmailValidator.java:10) 
    at org.hibernate.validator.internal.engine.constraintvalidation.ConstraintTree.validateSingleConstraint(ConstraintTree.java:446) 
    ... 54 more 

答えて

0

うわー、私はその問題を解決しました。

実際、問題は完全に異なっていました。

Hibernateで問題が発生しました。私はすべての挿入/更新時にデータを自動的に検証するかどうかはわかりませんでした。そのような場合、@Autowiredは動作しません。これは、Hibernateがバリデーター・ファクトリの異なる実装を使用するためです。

私は以前にデータを検証していたため、すべてが有効でない場合には正常に機能しました。操作が呼び出されると、再放送に検証を休止して保存すべてが...

有効であったときに、私は

<!DOCTYPE hibernate-configuration PUBLIC 
     "-//Hibernate/Hibernate Configuration DTD//EN" 
     "http://www.hibernate.org/dtd/hibernate-configuration-3.0.dtd"> 
<hibernate-configuration> 
    <session-factory> 
     ... 

     <property name="javax.persistence.validation.mode">none</property> 

     ... 
    </session-factory> 
</hibernate-configuration> 

私の設定ファイルhibernate.cfg.xmlでそれを無効にし、今ではすべてが期待されるように動作します。

関連する問題