2011-08-23 72 views
1

我已经尝试过并尝试过,但无法弄清楚这里发生了什么。春天mvc 3 - SessionAttributes似乎并没有工作

  1. 我有使用@Controller
  2. 我也有@SessionAttributes
  3. 我处理GET请求注解,并把一个对象到模型中注释的一个简单的控制器。
  4. 当我从窗体中取回POST时,我只返回用户填充的内容。我没有找回完整的对象。

我是新来SessionAttributes,但我认为这保留了整个对象,当读取的对象返回使用@ModelAttribute方法,它会被合并的对象(即表单改变的对象)。但是,我没有看到这种行为。

任何帮助将不胜感激。

下面是从代码中的相关部分:

@Controller 
@RequestMapping("/user") 
@SessionAttributes("user") 
public class UserController 
{ 
     // ... 

@RequestMapping(value = "/{login}", method = RequestMethod.GET) 
public String profile(Model model, @PathVariable("login") String login) 
     { 
      // ... 
      model.addAttribute("user", user); 
      // ... 
     } 

@RequestMapping(value="/{login}", method = RequestMethod.POST) 
public String saveProfile(@ModelAttribute("user") @Valid User user, BindingResult result, SessionStatus status) 
{ 
    if (result.hasErrors()) 
      { 
      return "user/index"; 
    } 
      // ... 
      status.setComplete(); 
    return "redirect:/user/"+user.getLogin(); 
} 

你看到任何东西,我可能错过了什么?我花了将近一天的时间,试图弄清楚这一点,但不能。任何帮助将非常感激。

更新:我找出了问题所在。下面发布答案。

回答

3

我想通了很多劳动后发生了什么。我希望这可以节省时间。

这里的根本问题是双重的:

  1. 对象被保存在会议上装饰着一些AspectJ的符号。正因为如此,对象的属性值才由适当的get访问器返回。
  2. 我已经进行了hibernate验证(注意处理POST的方法中的@Valid注释)。验证器注释直接在每个字段上(如下所示):

    @NotNull private String name;

这是我如何修复它。

  1. 仅出于测试目的,我删除了@Valid,并注意到即使字段本身似乎为NULL,我们仍将正确的数据保存在我们的后端存储中。这就是导致我陷入这个问题的根源的原因。
  2. 我想到验证者注释是causinI移动验证符表示法来获取方法。所以代码更改如下:

    私人字符串名称;

    @NotNull public String getName(){...}

  3. 我把@Valid注释放回去,并验证验证不再失败。

希望它可以帮助那里的人,并为他们节省一天的工作时间。 :)

1

我不希望Spring将属性表单会话和表单合并。您应该将表单提交的用户和会话中的用户分开。

0

我和Azeem有同样的问题,既然他没有明确确认sessionattribute可以用来将原始表单支持对象与提交中发布的更改“合并”,我想指出是的,表单提交的更改会合并到原始表单支持对象中。

可能有一些问题,这种方法在

Spring MVC 3.0: How do I bind to a persistent object

指出,但这种做法是非常有用的,当你有一个复杂的表单支持对象,但你只允许用户更新少数的表单中的对象图成员,并且不使用隐藏字段来维护表单元素中复杂对象的其余部分。

如果在类中使用此方法时未使用@SessionAttributes(“xxx”)注释,则返回的表单支持对象基本上为空,除了表单专门提交的那些成员。这可以使持久更新的对象非常困难,因为您必须自己将新更新合并到原始对象中。但通过使用会话属性,提交后提供的完整更新后的表单支持对象使对象图持久化变得更容易。