3

在我的 Grails 项目中,我想覆盖插件提供的过滤器,以便更好地满足我的需求。

更具体地说,定义了过滤器,因此它适用于所有控制器上的所有操作:filterName(controller:"*", action:"*") { ... },并且我想将其限制为仅某些控制器。

我试图在我的项目中创建一个与我想要覆盖的过滤器同名的过滤器类,但结果是每个请求都执行两个过滤器。

那么有谁知道如何更改/覆盖/(甚至停用)插件提供的过滤器?提前致谢!

4

2 回答 2

2

dmahapatro 的回答让我找到了解决方案:关键概念是访问filterInterceptorbean,它包含 Grails 应用程序中所有过滤器的定义。可以在BootStrap.groovy文件中访问它,以便在应用程序启动时修改可用的过滤器:

class BootStrap {
    def filterInterceptor

    def init = { servletContext ->
        // modify myPluginFilter provided by plugin so it 
        // is only applied to certain requests
        def myPluginFilterHandler = filterInterceptor.handlers.find{ it.filterConfig.name == 'myPluginFilter' }
        myPluginFilterHandler.filterConfig.scope.controller = 'myController'
        myPluginFilterHandler.filterConfig.scope.action = 'myAction'
        myPluginFilterHandler.afterPropertiesSet()

        log.info "myPluginFilter scope modified"
    }

    ...
}

此代码在应用程序启动时执行一次,它会找到过滤器myPluginFilter(例如,在插件中定义)并更改其范围(应用它的控制器和操作)。

过滤器可以通过myPluginFilterHandlerfilterInterceptor.handlers集合中删除来销毁而不是重新定义。

于 2013-05-09T13:41:09.617 回答
0

您可以在项目中尝试clearing使用handlers新过滤器类,例如:

blockPluginFilter(controller:"*", action:"*"){
    before = {
        def compInterceptor = applicationContext.getBean("filterInterceptor", CompositeInterceptor)
        compInterceptor.handlers?.clear()
    }
}

每个都有一个注册为 a 的filter已配置 spring bean ,它具有所有表示为的句柄。如果您清除新过滤器中的 您可以在项目过滤器类中创建另一个过滤器来处理您的自定义逻辑。这仅在插件的过滤器在此过滤器之后执行时才有效。您可以在任何其他地方清除,但在插件的过滤器被点击之前。filterInterceptorCompositeInterceptorfiltershandlershandlersfilterpluginhandlers

于 2013-05-08T06:18:09.087 回答