Spring Validation: Null ModelAndView returned to DispatcherServlet -


i pretty sure problem has not been described here before. pretty sure stupid mistake on part.

the problem in brief:

  • i have created user login form.
  • when user login information either correct or fails @ service layer, works
  • when user input validation fails, following message spring: "null modelandview returned dispatcherservlet name 'assessmentadmin': assuming handleradapter completed request handling"
  • i 400 error on web page:"the request sent client syntactically incorrect."

it seems me that:

when login info correct, model not null. can see logs (see below). when user input not meet validation requirements, aop calls validation made controller method not called (again, see logs).

jsps:

login form:

<%@ page contenttype="text/html; charset=utf-8"%>  <%@taglib uri="http://www.springframework.org/tags" prefix="spring"%>  <%@taglib uri="http://www.springframework.org/tags/form" prefix="form"%>    <html>  <head>  <title><spring:message code="label.login" /></title>  <style>  .error {  	color: red;  	font-weight: bold;  }  </style>  </head>  <body>        	<h2 align="center">  		<spring:message code="label.login" />  	</h2>  	<h2 align="center">  		<spring:message code="${loginerror}" />  	</h2>  	<form:form method="post" action="/prototype2/xz/doxzlogin" commandname="useradminform">  		<table>  			<tr>  				<td><form:label path="username" >  						<spring:message code="label.name" />  						<form:errors path="username" cssclass="error"/>  					</form:label></td>  				<td><form:input path="username" /></td>  			</tr>  			<tr>  				<td><form:label path="password">  						<spring:message code="label.password" />  						<form:errors path="password" cssclass="error"/>  					</form:label></td>  				<td><form:input path="password" /></td>  			</tr>  			<tr>  				<td><form:label path="pin">  						<spring:message code="label.pin" />  						<form:errors path="pin" cssclass="error"/>  						  					</form:label></td>  				<td><form:input path="pin" /></td>  			</tr>  			<tr>  				<td colspan="2"><input type="submit" value="submit" /></td>  			</tr>  		</table>  	</form:form>    </body>  </html>

login success form (just test page now)

<%@ page contenttype="text/html; charset=utf-8" %>  <%@taglib uri="http://www.springframework.org/tags" prefix="spring"%>  <%@taglib uri="http://www.springframework.org/tags/form" prefix="form"%>    <html>  <head>  <title><spring:message code="label.hello"/>:  ${username}</title>  </head>  <body>      <h3 align="center"><spring:message code="label.hello"/>, ${username}</h3>        <form:form method="post" action="/prototype2/performxzlogin" commandname="useradminform">     <table>      <tr>          <td><form:label path="username"><spring:message code="label.name"/></form:label></td>          <td>${username}</td>      </tr>      <tr>          <td><form:label path="password"><spring:message code="label.password"/></form:label></td>          <td>${password}</td>      </tr>      <tr>          <td><form:label path="pin"><spring:message code="label.pin"/></form:label></td>          <td>${pin}</td>      </tr>        </table>    </form:form>       </body>  </html>

controller:

  package com.prototype2.controller.user;    import javax.validation.valid;    import org.springframework.beans.factory.annotation.autowired;   import org.springframework.stereotype.controller;   import org.springframework.ui.model;   import org.springframework.validation.bindingresult;   import org.springframework.web.bind.annotation.exceptionhandler;   import org.springframework.web.bind.annotation.requestmapping;   import org.springframework.web.bind.annotation.requestmethod;    import com.prototype2.controller.welcome.ss;   import com.prototype2.controller.welcome.springexception;   import com.prototype2.model.user.useradmin;   import com.prototype2.service.user.adminuserservice;   import com.prototype2.service.user.businessservice;    @controller   public class usercontrollerimpl   {     @autowired    private adminuserservice auservice;     @autowired    private businessservice businessservice;     @requestmapping(value = "/xzlogin", method = requestmethod.get)    public string xzlogin(model model)    {      useradmin ua = new useradmin();     model.addattribute("useradminform", ua);     model.addattribute("loginerror", "label.blank");      ss.getlogger().debug("xxx: xzlogin done");     return "xzlogin";     }     @requestmapping(value = "/doxzlogin", method = requestmethod.post)    @exceptionhandler(    { springexception.class })    public string doxzlogin(@valid useradmin u, model model, bindingresult bindingresult)    {      ss.getlogger().debug("doxzlogin xxx useradmin: " + u.tostring());     ss.getlogger().debug("doxzlogin xxx model size: " + model.tostring());     if (bindingresult.haserrors())     {      model.addattribute("loginerror", "label.loginfailed");      return "xzlogin";     }     ss.getlogger().debug("doing login: listing entries if any...");      ss.getlogger().debug("user logging in:   " + u.getusername());     try     {       model.addattribute("useradminform", u);      // model.addattribute("username", u.getusername());       // model.addattribute("pin", u.getpin());       // model.addattribute("password", u.getpassword());       if (auservice.doadminlogin(u))      {        return "xzloginresult";      } else      {       model.addattribute("loginerror", "label.loginfailed");        return "xzlogin";       }     } catch (exception e)     {      ss.getlogger().error(e.getmessage(), e);      throw new springexception(e.getmessage() + "login failed: incorrect username, password, or pin");     }     }    } 

applicationcontext:

<beans xmlns="http://www.springframework.org/schema/beans"  	xmlns:context="http://www.springframework.org/schema/context"  	xmlns:mvc="http://www.springframework.org/schema/mvc"  	xmlns:xsi="http://www.w3.org/2001/xmlschema-instance"   	xmlns:tx="http://www.springframework.org/schema/tx"  	xsi:schemalocation="       http://www.springframework.org/schema/beans      http://www.springframework.org/schema/beans/spring-beans-3.2.xsd     http://www.springframework.org/schema/aop      http://www.springframework.org/schema/aop/spring-aop-3.2.xsd      http://www.springframework.org/schema/context     http://www.springframework.org/schema/context/spring-context-3.1.xsd      http://www.springframework.org/schema/tx     http://www.springframework.org/schema/tx/spring-tx-3.2.xsd      http://www.springframework.org/schema/mvc     http://www.springframework.org/schema/mvc/spring-mvc-3.2.xsd">    	<!-- i18n -->  	<bean id="messagesource"  		class="org.springframework.context.support.reloadableresourcebundlemessagesource">  		<property name="basename" value="classpath:messages" />  		<property name="defaultencoding" value="utf-8" />  	</bean>    	<bean id="localechangeinterceptor"  		class="org.springframework.web.servlet.i18n.localechangeinterceptor">  		<property name="paramname" value="lang" />  	</bean>    	<bean id="localeresolver"  		class="org.springframework.web.servlet.i18n.cookielocaleresolver">  		<property name="defaultlocale" value="en" />  	</bean>    	<bean id="handlermapping"  		class="org.springframework.web.servlet.mvc.annotation.defaultannotationhandlermapping">  		<property name="interceptors">  			<ref bean="localechangeinterceptor" />  		</property>  	</bean>    	<!-- hibernate -->  	                        ...  	  	<!--  validation -->  	<mvc:annotation-driven validator="validator" />  	  	<bean id="validator"      class="org.springframework.validation.beanvalidation.localvalidatorfactorybean"/>  </beans>

logs successful login (no bugs, no problems. model not null):

>>******controller log: successful login******      >> >> >>[debug] "jake.app" 2015-08-07 11:47:00,731: locale  en >> >>[debug] "jake.app" 2015-08-07 11:47:02,845: xxx: xzlogin done >> >>[debug] "jake.app" 2015-08-07 11:47:14,305: doxzlogin xxx useradmin: useradmin [username=jake0, password=1234, pin=1234, id=null] >> >>[debug] "jake.app" 2015-08-07 11:47:14,306: doxzlogin xxx model size: {useradmin=useradmin [username=jake0, password=1234, pin=1234, id=null], org.springframework.validation.bindingresult.useradmin=org.springframework.validation.beanpropertybindingresult: 0 errors} >> >>[debug] "jake.app" 2015-08-07 11:47:14,311: doing login: listing entries if any... >> >>[debug] "jake.app" 2015-08-07 11:47:14,313: user logging in:   jake0 >> >>[debug] "jake.app" 2015-08-07 11:47:14,503: in ua service >> >>[debug] "jake.app" 2015-08-07 11:47:14,504: logging in through dao :jake0 1234 1234 >> >>[debug] "jake.app" 2015-08-07 11:47:14,972: user admin useradmin [username=jake0, password=1234, pin=1234, id=206] >> >>[debug] "jake.app" 2015-08-07 11:47:14,974: user admin useradmin [username=jake0, password=1234, pin=1234, id=206] >> >>    ******root log (i.e., spring log): successful login****** >> >>[debug] 2015-08-07 11:47:14,297: org.springframework.web.servlet.dispatcherservlet.doservice(dispatcherservlet.java:861) dispatcherservlet name 'assessmentadmin' processing post request [/prototype2/xz/doxzlogin] >>     (cut sake of brevity) >> >>[debug] 2015-08-07 11:47:15,002: org.springframework.beans.factory.support.abstractautowirecapablebeanfactory.invokeinitmethods(abstractautowirecapablebeanfactory.java:1616) invoking afterpropertiesset() on bean name 'xzloginresult' >> >>[debug] 2015-08-07 11:47:15,003: org.springframework.beans.factory.support.abstractbeanfactory.dogetbean(abstractbeanfactory.java:248) returning cached instance of singleton bean 'org.springframework.transaction.config.internaltransactionadvisor' >> >>[debug] 2015-08-07 11:47:15,004: org.springframework.web.servlet.dispatcherservlet.render(dispatcherservlet.java:1241) rendering view [org.springframework.web.servlet.view.internalresourceview: name 'xzloginresult'; url [/web-inf/jsp/xzloginresult.jsp]] in dispatcherservlet name 'assessmentadmin' >> >>[debug] 2015-08-07 11:47:15,005: org.springframework.web.servlet.view.abstractview.exposemodelasrequestattributes(abstractview.java:432) added model object 'useradmin' of type [jake.prototype2.model.user.useradmin] request in view name 'xzloginresult' >> >>[debug] 2015-08-07 11:47:15,006: org.springframework.web.servlet.view.abstractview.exposemodelasrequestattributes(abstractview.java:432) added model object 'org.springframework.validation.bindingresult.useradmin' of type [org.springframework.validation.beanpropertybindingresult] request in view name 'xzloginresult' >> >>[debug] 2015-08-07 11:47:15,008: org.springframework.web.servlet.view.abstractview.exposemodelasrequestattributes(abstractview.java:432) added model object 'useradminform' of type [jake.prototype2.model.user.useradmin] request in view name 'xzloginresult' >> >>[debug] 2015-08-07 11:47:15,010: org.springframework.web.servlet.view.abstractview.exposemodelasrequestattributes(abstractview.java:432) added model object 'org.springframework.validation.bindingresult.useradminform' of type [org.springframework.validation.beanpropertybindingresult] request in view name 'xzloginresult' >> >>[debug] 2015-08-07 11:47:15,012: org.springframework.web.servlet.view.internalresourceview.rendermergedoutputmodel(internalresourceview.java:166) forwarding resource [/web-inf/jsp/xzloginresult.jsp] in internalresourceview 'xzloginresult' >> >>[debug] 2015-08-07 11:47:15,046: org.springframework.web.servlet.frameworkservlet.processrequest(frameworkservlet.java:996) completed request >> 

logs login validation error (model null):**

>>******controller log: failed login****** >> >> >>[debug] "jake.app" 2015-08-07 11:39:34,781: xxx: xzlogin done >> >> >> >> >>   >>root log (i.e., spring log): failed login****** >> >> >> >>[debug] 2015-08-07 11:39:42,741: org.springframework.beans.factory.support.abstractbeanfactory.dogetbean(abstractbeanfactory.java:248) returning cached instance of singleton bean 'org.springframework.transaction.config.internaltransactionadvisor' >> >>[debug] 2015-08-07 11:39:42,742: org.springframework.beans.factory.support.abstractautowirecapablebeanfactory.createbean(abstractautowirecapablebeanfactory.java:478) finished creating instance of bean 'org.hibernate.validator.internal.constraintvalidators.notnullvalidator' >> >>[debug] 2015-08-07 11:39:42,749: org.springframework.beans.factory.support.abstractautowirecapablebeanfactory.createbean(abstractautowirecapablebeanfactory.java:450) creating instance of bean 'org.hibernate.validator.internal.constraintvalidators.minvalidatorfornumber' >> >>[debug] 2015-08-07 11:39:42,755: org.springframework.beans.factory.support.abstractbeanfactory.dogetbean(abstractbeanfactory.java:248) returning cached instance of singleton bean 'org.springframework.transaction.config.internaltransactionadvisor' >> >>[debug] 2015-08-07 11:39:42,756: org.springframework.beans.factory.support.abstractautowirecapablebeanfactory.createbean(abstractautowirecapablebeanfactory.java:478) finished creating instance of bean 'org.hibernate.validator.internal.constraintvalidators.minvalidatorfornumber' >> >>[debug] 2015-08-07 11:39:42,802: org.springframework.web.servlet.handler.abstracthandlerexceptionresolver.resolveexception(abstracthandlerexceptionresolver.java:134) resolving exception handler [public java.lang.string jake.prototype2.controller.user.usercontrollerimpl.doxzlogin(jake.prototype2.model.user.useradmin,org.springframework.ui.model,org.springframework.validation.bindingresult)]: org.springframework.validation.bindexception: org.springframework.validation.beanpropertybindingresult: 1 errors >>field error in object 'useradmin' on field 'pin': rejected value [0]; codes [min.useradmin.pin,min.pin,min.int,min]; arguments [org.springframework.context.support.defaultmessagesourceresolvable: codes [useradmin.pin,pin]; arguments []; default message [pin],1000]; default message [must greater or equal 1000] >> >>[debug] 2015-08-07 11:39:42,807: org.springframework.web.servlet.handler.abstracthandlerexceptionresolver.resolveexception(abstracthandlerexceptionresolver.java:134) resolving exception handler [public java.lang.string jake.prototype2.controller.user.usercontrollerimpl.doxzlogin(jake.prototype2.model.user.useradmin,org.springframework.ui.model,org.springframework.validation.bindingresult)]: org.springframework.validation.bindexception: org.springframework.validation.beanpropertybindingresult: 1 errors >>field error in object 'useradmin' on field 'pin': rejected value [0]; codes [min.useradmin.pin,min.pin,min.int,min]; arguments [org.springframework.context.support.defaultmessagesourceresolvable: codes [useradmin.pin,pin]; arguments []; default message [pin],1000]; default message [must greater or equal 1000] >> >>[debug] 2015-08-07 11:39:42,809: org.springframework.web.servlet.handler.abstracthandlerexceptionresolver.resolveexception(abstracthandlerexceptionresolver.java:134) resolving exception handler [public java.lang.string jake.prototype2.controller.user.usercontrollerimpl.doxzlogin(jake.prototype2.model.user.useradmin,org.springframework.ui.model,org.springframework.validation.bindingresult)]: org.springframework.validation.bindexception: org.springframework.validation.beanpropertybindingresult: 1 errors >>field error in object 'useradmin' on field 'pin': rejected value [0]; codes [min.useradmin.pin,min.pin,min.int,min]; arguments [org.springframework.context.support.defaultmessagesourceresolvable: codes [useradmin.pin,pin]; arguments []; default message [pin],1000]; default message [must greater or equal 1000] >> >>[debug] 2015-08-07 11:39:42,812: org.springframework.web.servlet.handler.abstracthandlerexceptionresolver.resolveexception(abstracthandlerexceptionresolver.java:134) resolving exception handler [public java.lang.string jake.prototype2.controller.user.usercontrollerimpl.doxzlogin(jake.prototype2.model.user.useradmin,org.springframework.ui.model,org.springframework.validation.bindingresult)]: org.springframework.validation.bindexception: org.springframework.validation.beanpropertybindingresult: 1 errors >>field error in object 'useradmin' on field 'pin': rejected value [0]; codes [min.useradmin.pin,min.pin,min.int,min]; arguments [org.springframework.context.support.defaultmessagesourceresolvable: codes [useradmin.pin,pin]; arguments []; default message [pin],1000]; default message [must greater or equal 1000] >> >>[debug] 2015-08-07 11:39:42,815: org.springframework.web.servlet.handler.abstracthandlerexceptionresolver.resolveexception(abstracthandlerexceptionresolver.java:134) resolving exception handler [public java.lang.string jake.prototype2.controller.user.usercontrollerimpl.doxzlogin(jake.prototype2.model.user.useradmin,org.springframework.ui.model,org.springframework.validation.bindingresult)]: org.springframework.validation.bindexception: org.springframework.validation.beanpropertybindingresult: 1 errors >>field error in object 'useradmin' on field 'pin': rejected value [0]; codes [min.useradmin.pin,min.pin,min.int,min]; arguments [org.springframework.context.support.defaultmessagesourceresolvable: codes [useradmin.pin,pin]; arguments []; default message [pin],1000]; default message [must greater or equal 1000] >> >>[debug] 2015-08-07 11:39:42,817: org.springframework.web.servlet.dispatcherservlet.processdispatchresult(dispatcherservlet.java:1034) null modelandview returned dispatcherservlet name 'assessmentadmin': assuming handleradapter completed request handling >> >>[debug] 2015-08-07 11:39:42,818: org.springframework.web.servlet.frameworkservlet.processrequest(frameworkservlet.java:996) completed request >> >> >>******http 400 message ****** >>the request sent client syntactically incorrect. >> >> >> >> 

 the password check should part of validation via bindingresult. hence here in controller method post manually add jsr-303 error bindingresult.

if (bindingresult.haserrors()){        return "xzlogin";      }   model.addattribute("useradminform", u);   if (!auservice.doadminlogin(u)){ bindingresult.adderror(new fielderror("useradminform","password","invalid password ")); return "xzlogin";                  } 

this allows spring display them in view via fielderror  


Comments

Popular posts from this blog

yii2 - Yii 2 Running a Cron in the basic template -

asp.net - 'System.Web.HttpContext' does not contain a definition for 'GetOwinContext' Mystery -

mercurial graft feature, can it copy? -