SpringMVC详解@SessionAttributes

一、@ModelAttribute

在默认情况下,ModelMap 中的属性作用域是 request 级别是,也就是说,当本次请求结束后,ModelMap 中的属性将销毁。如果希望在多个请求中共享 ModelMap 中的属性,必须将其属性转存到 session 中,这样 ModelMap 的属性才可以被跨请求访问。

spring 允许我们有选择地指定 ModelMap 中的哪些属性需要转存到 session 中,以便下一个请求属对应的 ModelMap 的属性列表中还能访问到这些属性。这一功能是通过类定义处标注 @SessionAttributes 注解来实现的。

使模型对象的特定属性具有 Session 范围的作用域

import org.springframework.ui.ModelMap;  
import org.springframework.web.bind.annotation.SessionAttributes;  

@Controller
@RequestMapping("/bbtForum")
@SessionAttributes("currUser") // ①将ModelMap中属性名为currUser的属性放到Session属性列表中,以便这个属性可以跨请求访问
public class BbtForumController {
    @RequestMapping(params = "method=listBoardTopic")
    public String listBoardTopic(@RequestParam("id")int topicId, User user, ModelMap model) {
        bbtForumService.getBoardTopics(topicId);
        System.out.println("topicId:" + topicId);
        System.out.println("user:" + user);
        model.addAttribute("currUser",user); //②向ModelMap中添加一个属性
        return "listTopic";  
    }
}

我们在 ② 处添加了一个 ModelMap 属性,其属性名为 currUser,而 ① 处通过 @SessionAttributes 注解将 ModelMap 中名为 currUser 的属性放置到 Session 中,所以我们不但可以在 listBoardTopic() 请求所对应的 JSP 视图页面中通过 request.getAttribute(“currUser”) 和 session.getAttribute(“currUser”) 获取 user 对象,还可以在下一个请求所对应的 JSP 视图页面中通过 session.getAttribute(“currUser”) 或 ModelMap#get(“currUser”) 访问到这个属性。

这里我们仅将一个 ModelMap 的属性放入 Session 中,其实 @SessionAttributes 允许指定多个属性。你可以通过字符串数组的方式指定多个属性,如 @SessionAttributes({“attr1”,”attr2”})。此外,@SessionAttributes 还可以通过属性类型指定要 session 化的 ModelMap 属性,如 @SessionAttributes(types = User.class),当然也可以指定多个类,如 @SessionAttributes(types = {User.class,Dept.class}),还可以联合使用属性名和属性类型指定:@SessionAttributes(types = {User.class,Dept.class},value={“attr1”,”attr2”})。

二、@ModelAttribute

我们可以在需要访问 Session 属性的 controller 上加上 @SessionAttributes,然后在 action 需要的 User 参数上加上 @ModelAttribute,并保证两者的属性名称一致。SpringMVC 就会自动将 @SessionAttributes 定义的属性注入到 ModelMap 对象,在 setup action 的参数列表时,去 ModelMap 中取到这样的对象,再添加到参数列表。只要我们不去调用 SessionStatus 的 setComplete() 方法,这个对象就会一直保留在 Session 中,从而实现 Session 信息的共享。

@Controller  
@SessionAttributes("currentUser")
public class GreetingController{
    @RequestMapping
    public void hello(@ModelAttribute("currentUser") User user){
        //user.sayHello();
    }
}


摘录范文:http://blog.sina.com.cn/s/blog_6d3c1ec601018cx1.html

@SessionAttributes

属性

String[] value : 存储在会话中的会话属性名称。

注意,这里指定的模型属性名称。会话属性名称不一定匹配模型属性名称。应用程序不应该依赖会话属性名称。

Class[] types : 存储在会话中的会话属性类型。这种类型的所有模型属性都将存储在会话中,无论属性名称是什么。

范例1:通过Model绑定

Spring允许我们有选择地指定Model中的哪些属性需要转存到session中,以便下一个请求可通过Session来访问到这些属性。这一功能是通过类定义处标注@SessionAttributes注解来实现的。

@Controller

@RequestMapping(value = "login")

@SessionAttributes("mysession")  //定义把Model中的mysession属性的值绑定到Session中

public class LoginController {


    @RequestMapping(method = RequestMethod.POST)

    public String login(@ModelAttribute User user, ModelMap model) {

       String viewName = "";

       boolean check = true;

       if (check) {

           model.addAttribute("mysession", "123");

           viewName = "redirect:/home";

       } else {

           viewName = "redirect:/";

       }

       return viewName;

    }


}

这样我们不但可以在请求所对应的JSP视图页面中通过request.getAttribute()和session.getAttribute()获取mysession,还可以在下一个请求所对应的JSP视图页面中通过session.getAttribute()或ModelMap#get()访问到这个属性。

这里我们仅将一个ModelMap的属性放入Session中,其实@SessionAttributes允许指定多个属性。你可以通过字符串数组的方式指定多个属性,如 @SessionAttributes({“attr1”,”attr2”})。此外,@SessionAttributes还可以通过属性类型指定要 session化的ModelMap属性,如@SessionAttributes(types=User.class),当然也可以指定多个类,如 @SessionAttributes(types = {User.class,Dept.class}),还可以联合使用属性名和属性类型指定:@SessionAttributes(types = {User.class,Dept.class},value={“attr1”,”attr2”})。

范例2:通过@ModelAttribute绑定

我们使用@ModelAttribute把表单自动绑定到对象上,那这个对象也可以通过@ModelAttribute(“”)绑定到Session中。

@Controller

@RequestMapping(value = "login")

@SessionAttributes("user") //此处定义需要绑定到session中的model名称

public class LoginController {


@RequestMapping(method = RequestMethod.POST)

public String login(@ModelAttribute("user") User user, ModelMap model){

       //@ModelAttribute将绑定到session中

       String viewName = "";

       boolean check = true;

       if (check) {

           viewName = "redirect:/home";

       } else {

           viewName = "redirect:/";

       }

       return viewName;

    }


}

范例3:@SessionAttributes清除

@SessionAttributes需要清除时,使用SessionStatus.setComplete();来清除。注意,它只清除@SessionAttributes的session,不会清除HttpSession的数据。故如用户身份验证对象的session一般不同它来实现,还是用session.setAttribute等传统的方式实现。

@Controller

@RequestMapping(value = "login")

@SessionAttributes("mysession") // 定义把Model中的mysession属性的值绑定到Session中

public class LoginController {


    @RequestMapping(method = RequestMethod.POST)

    public String login(@ModelAttribute User user, ModelMap model, SessionStatus sessionStatus) {

       String viewName = "";

       boolean check = true;

       if (check) {

           model.addAttribute("mysession", "1233");

           viewName = "redirect:/home";

       } else {

           viewName = "redirect:/";

       }

       sessionStatus.setComplete();

       return viewName;

    }


}


赞(52) 打赏
未经允许不得转载:优客志 » JAVA开发
分享到:

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

微信扫一扫打赏