views:

952

answers:

2

In Spring MVC, suppose I define a SessionAttribute, using the @SessionAttribute tag like so:

@SessionAttributes(value = "myModel")
public class MyController{
   ...
}

Suppose that I forget to call status.setComplete() on the SessionStatus like so:

@RequestMapping(method = RequestMethod.POST)
public void doSomething(@ModelAttribute("myModel") MyModel model, SessionStatus status){
   ...
   //status.setComplete(); <-- Never gets called
}

Will the model stay in the session forever? Will it ever get cleaned out, or will the session keep growing larger and larger as the user navigates the site?

A: 

Is there some reason why you would want to do that?

from this thread : @SessionAttribute Problem

The @SessionAttributes works in the same way as the sessionForm of the SimpleFormController. It puts the command (or for the @SessionAttributes any object) in the session for the duration between the first and the last request (most of the time the initial GET and the final POST). After that the stuff is removed.

Gandalf
"After that the stuff is removed". <-- But it seems it only gets removed if you explicitly call status.setComplete() - how else would Spring know which is the last POST? So my question asks "What if you accidentally forget to call session.setComplete()?
Daniel Alexiuc
+2  A: 

This is along the lines of what @Gandalf said.

Form controllers model a form request lifespan, from initial viewing of the form through form submission. After the form is submitted, the form controller's job is done, and it will remove the command object from the session.

So, to keep the command object in the session between form workflows you will need to manage the session manually. After a clean POST, the object is removed from session.

In short, I believe the setComplete() method is just good practice but is not necessarily required.

EDIT: I just looked in my Spring book to confirm this. I'll quote it:

When @SessionAttribute is not used, a new command object will be created on each request, even when rendering the form again due to binding errors. If this annotation is enabled, the command object will be stored in the session for subsequent uses, until the form completes successfully. Then this command object will be cleared from the session. This is usually used when the command object is a persistent object that needs to be identical across different requests for tracking changes.

Essentially that's what I was saying above. It stores it in the session until you either A) call setComplete() or B) the controller successfully completes a POST.

Alex Beardsley
Excellent answer. I assume that a "successful form completion" is defined as being when errors.hasErrors() == false?
Daniel Alexiuc
I'm not sure to be honest. Looking at Spring's documentation for @SessionAttributes (http://static.springsource.org/spring/docs/3.0.x/javadoc-api/org/springframework/web/bind/annotation/SessionAttributes.html) it says: Those attributes will be removed once the handler indicates completion of its conversational session. I'm not quite sure what that means.
Alex Beardsley