我是使用Spring Security插件的新人,用于我的grails应用程序。这是我的代码获取当前用户登录。grails - 全局获取当前用户
String username = getPrincipal().username
但事情是我在每一个行动写这行以获得当前用户。有没有办法在全球范围内获得当前用户?并在一次又一次的动作中使用它,而不是一次又一次地宣告它?
我是使用Spring Security插件的新人,用于我的grails应用程序。这是我的代码获取当前用户登录。grails - 全局获取当前用户
String username = getPrincipal().username
但事情是我在每一个行动写这行以获得当前用户。有没有办法在全球范围内获得当前用户?并在一次又一次的动作中使用它,而不是一次又一次地宣告它?
你可以做到这一点在2种方式:
1)你可以注入SpringSecurityService任何你想要的,只需在任何控制器/服务:
SpringSecurityService springSecurityService
def someMethod(){
springSecurityService.principal
}
2)可以使用SecurityContextHolder中:
def someMethod(){
SecurityContextHolder.context.authentication?.principal
}
我建议使用选项1,它使测试更容易等。
如果您需要获取用户对象,我建议您检索“新鲜”使用用户实例每次(从数据库获取)springSecurityService
之前注入:
springSecurityService.principal.username
但是如果你只需要一个用户名 - 你可以创建一个会话范围的bean,并在用户名来填充它创建时间:
resources.groovy:
...
userNameHolder(UserNameHolder) { bean ->
bean.scope = 'session'
springSecurityService = ref("springSecurityService")
}
...
和:
class UserNameHolder {
def springSecurityService
String username = springSecurityService.principal.username
String getUsername() {
username
}
}
那么你应该注入UserNameHolder
到所需要的地方,找回用户名:
class SomeService {
def userNameHolder
void someMethod() {
...
userNameHolder.username
...
}
...
}
享受!
UPD:
你可以做通过将用户名到HttpSession中几乎是相同的,但它会更可控和可测试性。所以我强烈建议你使用会话范围的bean。
'springSecurityService.currentUser?.userName'除非'userName'属性在委托人上不可用,否则会执行不必要的数据库调用。 'springSecurityService.principal.username'会更好。 –
@JamesKleeh,谢谢,考虑到了;) –
创建一个名为BaseController的类,并让每个控制器扩展它,然后在其中创建一个受保护的方法,可以从所有控制器访问。 – Raphael