【问题标题】:Can't get any output from the <spring:hasBindErrors> taglib无法从 <spring:hasBindErrors> 标签库获得任何输出
【发布时间】:2011-07-12 15:58:17
【问题描述】:

我正在编写一个基于 Spring 3 MVC 的 Web 应用程序,将 JSP 用于我的视图层。我在尝试报告 JSP 中特定模型对象的 BindingResult 错误的特定区域上苦苦挣扎。这可能最好用适当的代码来解释:

这是我的 Spring Controller 方法:

@RequestMapping(value = "/**", method = RequestMethod.GET)
public ModelAndView get(@ModelAttribute("xApiRequest") @Valid final XAPIRequest xApiRequest,
                       final BindingResult xapiBindingResult,
                       final HttpServletResponse response,
                       Model model) throws EntityNotFoundException {
  String viewName = "/WEB-INF/views/get-single-entity.jsp";
  /* 
   * Create a MAV passing in the original Model object which contains:
   * 1: The 'xApiRequest' @ModelAttribute object.
   * 2: The BindingResult for the 'xApiRequest' object.
   */
  final ModelAndView mav = new ModelAndView(viewName, model.asMap());
  final XAPIResponse<Resource> xApiResponse = buildXAPIResponse(false, 200, xApiRequest, null);
  response.setStatus(200);
  mav.addObject("xApiResponse", xApiResponse);
  return mav;
}

当我执行这个方法时,我可以看到以下内容:

  • xApiRequest 对象是从 HttpServletRequest 正确创建的(我有一个单独的方法来执行此操作)
  • 由 @Valid 注释引起的 JSR-303 验证已经发生,并发现了 2 个验证错误,正如我所料,这些错误表示为 BindingResult 对象。
  • BindingResult 对象存在于 Model 方法参数中。
  • xApiRequest 和 BindingResult 对象已成功从 Model 方法参数传递到该方法返回的 ModelAndView 对象中。

而且我可以确认 BindingResult 的内容确实正确地将 xApiRequest 对象识别为验证错误的来源:

{xApiRequest=com.stretchr.xapi.entity.request.XAPIRequest@1e28608, org.springframework.validation.BindingResult.xApiRequest=org.springframework.validation.BeanPropertyBindingResult: 2 errors
Field error in object 'xApiRequest' on field 'userId': rejected value [null]; codes [NotEmpty.xApiRequest.userId,NotEmpty.userId,NotEmpty.java.lang.String,NotEmpty]; arguments [org.springframework.context.support.DefaultMessageSourceResolvable: codes [xApiRequest.userId,userId]; arguments []; default message [userId]]; default message [may not be empty]
Field error in object 'xApiRequest' on field 'projectId': rejected value [null]; codes [NotEmpty.xApiRequest.projectId,NotEmpty.projectId,NotEmpty.java.lang.String,NotEmpty]; arguments [org.springframework.context.support.DefaultMessageSourceResolvable: codes [xApiRequest.projectId,projectId]; arguments []; default message [projectId]]; default message [may not be empty]}

JSP 看起来像这样:

<%@ page contentType="application/json; charset=UTF-8" %>
<%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %>
<%@ taglib prefix="json" uri="http://www.atg.com/taglibs/json" %>
<%@ page session="false" %>
<spring:hasBindErrors name="xApiRequest">
</spring:hasBindErrors>
<c:if test="${errors}">
  <json:object name="exceptions">
    <json:property name="exceptionCount" value="${errors.errorCount}" />
    <json:property name="globalExceptionCount" value="${errors.globalErrorCount}" />
    <c:forEach var="error" items="${errors.allErrors}" varStatus="index">
      <json:property name="${index}" value="${error.defaultMessage}" />
    </c:forEach>
  </json:object>
</c:if>

无论我做什么,我似乎都无法识别 xApiRequest 模型对象有绑定错误,因此 JSP 输出不包含 异常 em> 包含错误详细信息的对象:

{
  w: false
  s: 200
  c: ""
  r: {
    o ~path: ""
  }
}

谁能看到我在这里做错了什么?如果失败了,有什么方法可以调试 JSP 处理过程中发生的事情?我热衷于调试 Spring taglib,但不太确定如何在 taglib 和相关代码位之间建立链接。

希望我在这里提供了足够的信息,但如果需要更多信息,请不要犹豫。

非常感谢,

艾德

【问题讨论】:

    标签: jsp spring-mvc jsp-tags taglib


    【解决方案1】:

    errors 变量仅在 &lt;spring:hasBindErrors&gt; 标记内公开,因此您应该这样做(注意它也替换了 &lt;c:if&gt;):

    <spring:hasBindErrors name="xApiRequest">
    <json:object name="exceptions">
        <json:property name="exceptionCount" value="${errors.errorCount}" />
        <json:property name="globalExceptionCount" value="${errors.globalErrorCount}" />
        <c:forEach var="error" items="${errors.allErrors}" varStatus="index">
          <json:property name="${index}" value="${error.defaultMessage}" />
        </c:forEach>
      </json:object>
    </spring:hasBindErrors>
    

    【讨论】:

    • 谢谢。实际上我已经尝试过 - 当我这样做时,JSP 呈现 JSON 对象(好像是说存在 were BindErrors,但是对 ${errors.errorCount} 等的调用没有产生任何结果,就好像存在不存在错误数据。还有其他想法吗?
    • 可悲的是,它的作用完全相同。我已经确定了标签类org.springframework.web.servlet.tags.BindErrorsTag,所以我要看看我是否可以调试发生了什么。
    【解决方案2】:

    多么尴尬,在尝试调试 BindErrorsTag 类后,我意识到它根本没有被调用。这个发现让我意识到我没有在 JSP 中包含 Spring taglib 命名空间声明,包括这个解决了问题。

    <%@ taglib prefix="spring" uri="http://www.springframework.org/tags"%>
    

    诅咒自己错过了这个现在非常明显的错误,并且有点困惑为什么 JSP(和我的 IDE)没有抱怨缺少 taglib 声明。我认为缺少 taglib 声明通常会在执行标记时导致 RuntimeException,但似乎并非如此(我希望它可以为我节省几个小时的调试时间!)

    不管怎样,问题解决了。

    @axtavt - 感谢您的帮助!

    【讨论】:

      【解决方案3】:

      天哪!我有同样的问题,非常感谢你回答你自己的问题。

      在我的情况下 - 希望可以帮助其他人 - 一个简单的 JSP,调用如下方法:

      @RequestMapping(method = RequestMethod.GET)
      protected Object loadRegistrationForm(HttpSession session, Model model) {
      

      这个返回的 JSP 有一个可以提交的表单并获取到服务器 POST 方法,所以我有以下内容来捕获从表单的帖子返回的错误:

      <spring:hasBindErrors name="customerAccountFormObj">    
      
      <div class="alert alert-block pull-right alertmessage alert-warning alert-dismissible" role="alert" id="errorMsgHdr">
                          <button type='button' class='close' data-dismiss='alert' aria-label='Close'><span aria-hidden='true'>&times;</span></button>
      
                      <form:errors path="*" cssClass="errorList" element="div"/>
      </div>
      
      </spring:hasBindErrors>
      

      基本上,当出现绑定错误时,引导程序警报消息会显示错误,猜猜 GET 调用会发生什么?我收到一个空警报框...在敲了 12 个小时后,我偶然发现了你的问题,补充说

      <%@ taglib prefix="spring" uri="http://www.springframework.org/tags" %>
      

      瞧!一切都很干净,没有空警报框,即 GET 调用没有错误。这必须是 JSP/Spring 中的一个错误。如果对任何人有帮助,我会使用 Spring mvc 3.0.3.RELEASE。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 2021-11-23
        • 2019-08-29
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2020-12-29
        相关资源
        最近更新 更多