如何从grails过滤器中去除常见逻辑?
这是专门针对Grails1.3.7应用程序的,但希望答案也适用于较新版本。下面的代码是所需代码的简化版本。正在注入accountService。下面的代码片段做了它应该做的事情,但显然是重复的代码。这在grails app/conf中的UserFilter类中 如何从过滤器中提取公共逻辑,并保持重定向和检查会话的功能?我尝试将一个方法提取到filter类中,传入会话和flash,但重定向仍然给我带来问题如何从grails过滤器中去除常见逻辑?,grails,grails-filters,Grails,Grails Filters,这是专门针对Grails1.3.7应用程序的,但希望答案也适用于较新版本。下面的代码是所需代码的简化版本。正在注入accountService。下面的代码片段做了它应该做的事情,但显然是重复的代码。这在grails app/conf中的UserFilter类中 如何从过滤器中提取公共逻辑,并保持重定向和检查会话的功能?我尝试将一个方法提取到filter类中,传入会话和flash,但重定向仍然给我带来问题 def filters = { // ... other filters ... a
def filters = {
// ... other filters ...
adminAllCheck(controller: 'administration', action: '*') {
before = {
if(!session.isAdmin) {
if(accountService.isAdmin()) {
session.isAdmin = true
} else {
flash.message = 'Non admin'
redirect(controller: 'home', action: 'index')
return false
}
}
true
}
}
userListCheck(controller: 'user', action: 'list') {
before = {
if(!session.isAdmin) {
if(accountService.isAdmin()) {
session.isAdmin = true
} else {
flash.message = 'Non admin'
redirect(controller: 'home', action: 'index')
return false
}
}
true
}
}
}
您可以在您的代码(控制器?)中声明一个
闭包
,该闭包可以在之后调用
样本:
private def ensureSessionAdmin = {
if(!session.isAdmin) {
if(accountService.isAdmin()) {
session.isAdmin = true
} else {
flash.message = 'Non admin'
redirect(controller: 'home', action: 'index')
return false
}
}
true
}
def filters = {
// ... other filters ...
adminAllCheck(controller: 'administration', action: '*') {
before = ensureSessionAdmin
}
userListCheck(controller: 'user', action: 'list') {
before = ensureSessionAdmin
}
}
创建助手方法的一种方法是在
过滤器
闭包之外创建它,并传入实例。传入this
不起作用,因为这不是闭包,而是UserFilters
实例。而是传入闭包的委托
,该委托添加了呈现
和重定向
方法,其中参数
和控制器名
等属性为:
class UserFilters {
def filters = {
// ... other filters ...
adminAllCheck(controller: 'administration', action: '*') {
before = {
doAdminCheck(delegate)
}
}
userListCheck(controller: 'user', action: 'list') {
before = {
doAdminCheck(delegate)
}
}
}
private boolean doAdminCheck(filters) {
if (!filters.session.isAdmin) {
if (accountService.isAdmin()) {
filters.session.isAdmin = true
}
else {
filters.flash.message = 'Non admin'
filters.redirect(controller: 'home', action: 'index')
return false
}
}
true
}
}
您还可以使用控制器
和操作
参数中的|
字符跨控制器执行常见工作。它不能直接在这里工作,因为您对管理控制器使用*
,并且只应用于用户控制器中的列表
操作,但您可以对其执行显式控制器/操作名称检查:
adminCheck(controller: 'administration|user', action: '*') {
if (controllerName == 'user' && actionName != 'list') {
return true
}
// common logic here
}
您还可以将逻辑移到服务中,并将依赖项注入其中。在服务中混合这样的层和HTTP逻辑通常不是一个好主意,但这样可以将逻辑保持在一个位置。您可以对委托使用相同的技巧,或者根据需要传入会话/请求/响应等