【问题标题】:How to keep variables in a JSP after (javax or hibernate) validation fails(javax或hibernate)验证失败后如何将变量保留在JSP中
【发布时间】:2014-04-01 13:31:18
【问题描述】:

因此,在 javax 或 hibernate 验证失败后,模型变量将从 JSP 中消失。

因为我从模型中加载弹簧消息的代码,如填充:

<spring:message code="${editUser.role.rolename}"/>

验证失败后我松开它们并收到以下错误:

javax.servlet.jsp.JspTagException: No message found under code '' for locale 'en_US'.

在这种情况下,editUser 是由表单操作的模型对象,rolename 属性包含 spring 消息标签使用的翻译代码。

我的实体:

@Entity
@Table(name = "User")
public class BUser {

    @Id
    @GeneratedValue
    @Column(name = "id")
    private int id;

    @NotEmpty
    @NotBlank
    @Column(name = "username")
    private String username;

    ....

    @ManyToOne
    @JoinColumn(name = "role", unique = true)
    private BRole role;
}

部分控制器:

    @Controller
    public class AccountController {

        @RequestMapping(value = "/secure/user/edit/{username}", method = RequestMethod.GET)
        public String editUser(Model model, @PathVariable String username) {
            BUser user = bUserService.getUserByUsername(username);
            if (user != null) {
                user.setPassword(null);
                model.addAttribute("editUser", user);
                model.addAttribute("roles", bUserService.getRoles(false));
                    return "editUser";
                } else {
                    return "404";
                }
        }

        @RequestMapping(value = "/secure/user/edit/{username}", method = RequestMethod.POST)
        public String editProcessUser(Model model, @PathVariable String username, @UserPrincipal BUser login, HttpSession session,
                @Valid @ModelAttribute("editUser") BUser editUser, BindingResult result) {

            if (result.hasErrors()) {
                return "editUser";
            }

        //some more code after that... never reached after validation error
        }
}

如何正确处理此类问题?

谢谢。

【问题讨论】:

  • 再添加到模型中怎么样?
  • 或者放到Session中
  • @Bart 不起作用,如果我这样做,错误消息就会消失。
  • @CodeChimp 我尝试使用&lt;c:set scope="session" var="myvar"&gt;&lt;spring:message code="${editUser.role.rolename}" /&gt;&lt;/c:set&gt;,但它不起作用。还是您的意思是将其添加到控制器中的会话中,在这种情况下,我认为 c:set 标记也应该这样做。
  • 请显示处理验证的处理程序的控制器代码。

标签: spring jsp spring-mvc jsp-tags


【解决方案1】:

应 OP 的要求发布为答案...

您可以使用“@SessionAttribute”将模型属性设置为控制器中的会话范围。每当您设置已识别模型属性的值时,它都会将其置于会话中。

例如,如果我有一个名为“myBean”的属性,您可以执行以下操作:

@Controller
@RequestMapping("/myApp")
@SessionAttribute("myBean")
public class MyController {
   // ...
   @RequestMapping("/getMyBean")
   public String getMyBean(@ModelAttribute("myBean") MyBean myBean, Model uiModel) {
      uiModel.addAttribute("myBean", new MyBean());
   }
   // ...
}

在这个简单的示例中,getMyBean() 每次都会创建一个 MyBean 的新实例。这不是您可能会做的事情,但请注意,它还会在模型中设置“myBeam”,这具有将新创建的MyBean 置于会话范围内的效果。这有几个结果:

  1. 对“myBean”所做的任何更改都将在会话范围内进行
  2. 表单不需要提交整个 bean 以防止该 bean 的属性为 null,因为 Spring 现在将更新现有会话版本,并且不会每次都创建一个空的
  3. 现在任何 JSP 或任何代码也可以获取引用并在会话中使用“myBean”。

当您需要在全局范围内提供列表等时,这特别有用,例如,当您需要驱动 &lt;select&gt; 的内容时。例如:

@Controller
@RequestMapping("/myApp")
@SessionAttribute({"myBean", "cities"})
public class MyController {
   // ...
   @RequestMapping("/getMyBean")
   public String getMyBean(@ModelAttribute("myBean") MyBean myBean, Model uiModel) {
      uiModel.addAttribute("myBean", new MyBean());
   }
   // ...
   @ModelAttribute("cities")
   private List<String> createCitiesList() {
      List<String> cities = new ArrayList<String>();
      cities.add("Jacksonville");
      cities.add("Orlando");
      cities.add("Miami");
      cities.add("Tampa");
      return cities;
   }
   // ...
}

在本例中,我们创建了两个@SessionAttributes,一个用于“myBean”,另一个用于“城市”。我们还创建了一个标有@ModelAttribute 的方法,它返回城市名称的List&lt;String&gt;。最终结果是,我们现在将在会话中自动神奇地拥有一个城市名称列表,我们可以将其放入我们的任何处理程序方法或直接在我们的 JSP 中使用。此方法可用于构建和填充您想要的任何内容,包括您的 bean(如果需要)。

您可以在这里阅读更多内容:

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2011-03-07
    • 1970-01-01
    • 2015-08-09
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-08-24
    相关资源
    最近更新 更多