Grails 提供 filters在你的 Controller 之前运行。它们在如下所示的类中定义:
class SecurityFilters {
def filters = {
myFilter(controller:'*', action:'*') { // What are those weird colons??
print "I'm filtering!"
// Code that does the filtering goes here
}
}
}
这些工作很好,但我想更好地理解语法,因为它看起来不像我以前见过的任何 Groovy 代码。特别是,上面以
myFilter
开头的行看起来很奇怪。这是一个名为 myFilter
的方法的方法定义吗? ?如果是这样,:'*'
是什么意思?每个参数之后的意思?我认为它可能是一个默认参数值,但那将是 ='*'
.我之前在方法调用中看到过使用冒号的命名参数,但这不可能是方法调用,因为我还没有定义 myFilter()
其他任何地方。如果有人能告诉我如何从普通的 Groovy 类中执行过滤代码,我想我会更好地理解。换句话说,如果我有一个包含上述行的 MyFilters.groovy 文件,我该如何完成这个 Groovy 代码以便打印“我正在过滤”?
import MyFilters
def mf = new MyFilters()
mf.filters.somethingGoesHere // Help! How do I finish this line so it calls my filtering code?
最佳答案
以下 Groovy 代码将打印“我正在过滤!”:
class SecurityFilters {
def filters = {
myFilter(controller:'*', action:'*') { // What are those weird colons??
print "I'm filtering!"
// Code that does the filtering goes here
}
}
}
class FilterDelegate {
def methodMissing(String methodName, args) {
// methodName == myFilter
// args[0] == [controller:*, action:*]
// args[1] == {print "I'm filtering!"}
args[1].call()
}
}
def sf = new SecurityFilters()
def filtersClosure = sf.filters
filtersClosure.delegate = new FilterDelegate()
filtersClosure.call()
在此示例中 过滤器 是一个调用名为 的方法的闭包我的过滤器 并传递一个 map 和一个闭包。您可以将 myFilter 视为:
myFilter([controller:'*', action:'*'], closure)
Map 可以包含 Controller 、操作或 uri 等键。当 Grails 在尝试确定要调用哪个闭包时尝试匹配来自 HTTP 请求的 URI 时,使用通配符 (*)。
我对 Grails 如何处理过滤器的理解是使用了委托(delegate)加载器类。 loader 类提供一个 methodMissing 方法,并为过滤器闭包内的每个方法调用创建一个 FilterConfig。当发出 HTTP 请求时,Grails 会查看所有 FilterConfig 对象并尝试找到匹配的范围(在映射中查找 Controller 、操作或 uri,并使用正则表达式匹配通配符)。如果找到匹配项,它会调用传递给 Filter 类方法的闭包。
关于Grails 过滤器语法,或者,如何在 Grails 之外调用 Grails 过滤器,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/1255285/