使用Grails的Pre/Post Spring-Security注释

Gle*_*nnn 7 grails spring-security

我正在使用Grails Spring-Security插件开发Grails(版本1.3.3)Web应用程序,Spring-Security-Core-1.0.1(反过来,它使用spring-security-3.0.2.RELEASE).

我想为控制器中的操作提供基于Spring-Security注释的访问控制.

我已经能够使用以下注释成功进行基本身份验证:

@Secured("hasAnyRole('ROLE_USER')")
def list = {
...  
}
Run Code Online (Sandbox Code Playgroud)

这样做 - 只向具有ROLE_USER角色的人提供对列表操作/视图的访问.

但是,允许执行某些控制器操作的角色集可能会随时间而变化,并且是系统整体状态的函数.也就是说,允许执行给定操作的角色集可能由服务或域对象方法返回.

我可以做这样的事情的一种方法是使用Spring-Security的"基于表达式的访问控制"(@Pre和@Post注释),类似于Spring Security Documentation中的示例:

 @PreAuthorize("hasPermission(#contact, 'admin')")
 public void deletePermission(Contact contact, Sid recipient, Permission permission);
Run Code Online (Sandbox Code Playgroud)

在用于访问控制决策的该示例中,可以使用#contact语法访问发送到该方法的对象(例如,联系人).

但是,我无法获得@PreAuthorize(或@RolesAllowed)注释来处理Grails控制器操作.如果我用@PreAuthorize(而不是@Secured,如上所述)注释列表操作,我会收到以下错误:

元素FIELD上不允许使用注释@ org.springframework.security.access.prepost.PreAuthorize

这并不奇怪 - 该操作是Groovy闭包(具有可执行代码的字段),而不是方法.但是,我也尝试使用从闭包中调用的方法的注释,如:

  def list = {
    testMethod()
    ....
  }

  @PreAuthorize("hasRole('ROLE_USER')")
  public boolean testMethod(){
    println "testMethod succeess"
    return true;
  }
Run Code Online (Sandbox Code Playgroud)

虽然这不会引发任何错误,但它似乎也没有提供任何访问控制.(无论用户是否具有ROLE_USER,都会打印"testMethod success").

所以,我尝试了一些不同的东西(并阅读了文档),但是还没有能够找到一种使用Grails控制器动作使用@PreAuthorize注释的好方法.这可能吗?在Grails应用程序中是否有更好的方法来使用Spring-Security-Annotations来提供访问控制,这是系统状态的一个功能?

Bur*_*ith 5

您需要使用ACL插件来使用这些注释,但由于您指出的原因,它们不能用于控制器操作.@Secured有效,因为我创建了一个Spring Security注释的副本,允许将它放在字段以及方法和类上,然后我查找它们并明确地将它们连接起来.您需要使用从控制器调用的带注释的服务.