Grails Spring Security插件在HttpSession中保存currentUser的位置

时间:2014-11-18 07:18:01

标签: grails spring-security httpsession

通过调用来获取当前用户是很有名的:

springSecurityService.currentUser ; 

Spring Ssecurity API是否在HttpSession中保存此对象。如果是,那么如何从会话中访问此对象。

即:session['currentUser']

2 个答案:

答案 0 :(得分:1)

它没有。

正如您在回答中所示,Principal存储在会话中,但那是由org.springframework.security.core.userdetails.UserDetails创建的org.springframework.security.core.userdetails.UserDetailsService实例。插件中的默认实现是grails.plugin.springsecurity.userdetails.GrailsUser,但这很容易定制。

UserDetails实例通常是一个轻量级对象,只包含用户名和散列密码,一些锁定/启用的布尔值,以及一组用于存储角色名称的GrantedAuthority实例。我经常建议用户将其扩展为包含有用但在登录会话期间不太可能改变的数据,例如:全名,以避免去数据库检索它。由于UserDetails存储在会话中并可通过springSecurityService.principal轻松访问,因此它是存储此类数据的理想之地。

但它与getCurrentUser() / currentUser返回的内容不同 - 这是由UserDetailsService加载到的GORM用户/人域类创建UserDetails实例。它可以拥有更多与之相关的数据,延迟加载有多个集合等。它通常是一个相当大的对象,应该存储在会话中。这样做会使其数据方便可用,但会影响可伸缩性,因为您浪费了服务器内存并限制了服务器可以拥有的并发会话数。它是一个断开连接的Hibernate对象,因此要将它用于大多数与持久性相关的操作,需要您重新加载实例,通常使用merge()。这会从数据库中加载整个内容,因此在UserDetails中存储所需的额外数据以及实例的ID会更加高效,因此您可以根据需要轻松检索实例。这是getCurrentUser() / currentUser所做的事情 - 如果get()调用可用,则使用该ID,或等效{{1}的用户名调用(如果用户名具有唯一索引,则应该大致相同)。

答案 1 :(得分:0)

在HttpSession检查session.getAttributeNames()之后,我想分享我的结果:

session.getAttribute('SPRING_SECURITY_CONTEXT').authentication.principal