使用spring安全框架实现安全性的不同方法



我是spring安全框架的新手。我只是在编译使用spring安全注释或spring安全框架添加安全特性的各种方法。

到目前为止发现了以下内容。

  1. 整页授权示例:<intercept-url pattern="/user/**" access="hasRole('ROLE_USER')" />
  2. 页面内授权

    示例:<security:authorize access="hasRole('ROLE_ADMIN')">

  3. 方法级授权-@PreAuthorize,@PostAuthorize,@PreFilter,@PostFilter

我不确定这是否是一个详尽的列表,以确保申请。同样需要一些帮助。谢谢

此外,我正在寻找可以轻松实现和配置的安全功能,在这些功能中,开发人员不太可能犯错误,同时实现所需的安全目标。看起来注释很容易使用,而且不太含糊。注释是否仅用于方法级别的授权?spring安全性是否提供可用于保护应用程序其他部分的注释?这些注释是否可以通过参数来配置权限或特权?

我希望我的问题不要太宽泛。如有任何修改或有益的意见,我们将不胜感激。

也许您需要从确定域模型的需求开始,什么是敏感数据,什么不是敏感数据,以及如何访问这些数据(HTML/JSP与REST/JSON与直接Java调用)。然后根据需要使用授权功能。您的列表几乎包含了大多数应用程序所需的内容,但要获得更精细、更高级的授权机制,请查看Spring的ACL:

http://docs.spring.io/spring-security/site/docs/3.0.x/reference/domain-acls.html

您可能想自己回答的另一个重要问题是,哪个应用程序层将负责实施您的安全性:MVC/REST与服务(将这种问题分散到多个层通常是个坏主意)。这将直接决定您将要选择的SS功能。

您可能希望在密切反映您特定领域的SS注释之上构建自己的注释。这样,所有的复杂性都将集中在一个地方,从而减少出错的空间。

例如,可以创建自定义注释(如@AuthorizedFor),在其中可以添加各种特定于域的参数。然后,您可以使用一个SS注释来注释该注释,比如@Pre/PostAuthorize("hasAnyRole()")(在这里,您还可以使用Spring的原生EL来进一步自定义行为),并使用Pre/PostInvocationAuthorizationAdvice的自定义实现,在那里您可以根据自定义注释参数做出授权决定。这里的额外优势是,您将能够使用自定义注释来保护完整的类,而不必注释该类中的所有方法。在您的实现中,您可以获得MethodInvocation实例,从中可以询问包含该方法的类,并查看其是否已注释,然后继续操作,就像方法本身已注释一样。

有关更深入的讨论,请参阅本文:http://blog.novoj.net/2012/03/27/combining-custom-annotations-for-securing-methods-with-spring-security/

实现spring安全性基本上有两种方法。通过.xml文件中的bean配置和其他使用Annotations。基于注释的方法很容易长期使用,因为它不太含糊。

这是对spring.io的引用。这两种方法都解释得很好。

http://spring.io/blog/2013/07/03/spring-security-java-config-preview-web-security/

注释是纯基于java的配置,很可能会超过xml配置。

列表中的三个项目有不同的用途:

  1. intercept-url:在servlet层添加安全性。换句话说,你可以控制谁可以/不能访问你的应用程序中的任何url。例如,您可以仅向管理员添加访问url /admin/some_critical_operation的权限,但允许所有经过身份验证的用户访问/some_informational_page。仅凭这种授权就可以保护您的应用程序,但这是一种非常脆弱的设计。添加或更改url很容易在没有通知的情况下破坏安全。

  2. 在页面授权:这不是真正的授权,只是一个方便的标签,用于隐藏不适合当前用户的html内容。例如,非管理员用户不应该看到按钮create new user。正如我所说,这不是真正的安全措施,因为如果没有应用任何其他授权类型,用户可以在浏览器中键入url并获得访问权限。

  3. 方法级授权:为服务层添加安全性。这意味着您可以对谁可以/不能调用某个服务类的方法施加限制。它被认为更安全,更难妥协,因为它在应用层堆栈中应用得更深。它既可以与注释一起应用,也可以与安全命名空间一起应用。

通常,您首先要在服务层保护您的应用程序,然后添加一些url控件。在页面中添加授权标签是可选的。

我还不能发表评论,但关于你的问题:

是否有可配置的注释?例如,我提供了方法级安全注释,您可以在其中提供参数,比如有权访问方法或访问方法返回的元素的用户的角色

您可以自由地编写自己的注释,这些注释又使用本机Spring Security注释进行注释。这使得它们本质上是一个特定于域的扩展。也就是说,标准的SS注释允许使用SpEL,它相当灵活,甚至很难与您的特定域绑定。您可以很容易地断言用户是否具有某些角色(GrantedAuthority)等。。。

如果您想实现自己的注释,请参阅我的另一个答案中的链接以进行彻底的讨论。

我可以给你举一个我最近参与的一个项目的具体例子。我们有由外部系统管理的授权组,还有定义对某些资源的访问的内置逻辑。因此,基本上我们有两个地方可以查找授权参数。我们已经创建了授权组(通过LDAP从外部检索)和授权角色(内置的业务逻辑)的概念。这些组很简单——如果用户是该组的成员,则授予他们访问权限,否则拒绝访问。对于角色,我们有业务规则来确定用户是否具有特定角色(例如,已签署的T&C、已接受的EULA等)。所有这些都是在身份验证阶段确定的。

为了更容易解释我们的访问控制,我们创建了两个注释@AuthorisedForGroups({group1, group2, ...})@AuthorisedForRoles({role1, role2,...})。每一个都用Spring的原生@PreAuthorize("hasAnyRole()")进行了注释。注意"hasAnyRole()"的使用——这只是告诉Spring"让所有通过身份验证的人都进来","我们将自己做出授权决定"。然后在PreInvocationAuthorizationAdvice的自定义实现中做出授权决策(事实上,我们只是扩展了Spring自己的实现ExpressionBasedPreInvocationAdvice),并将决策逻辑放入#before()方法中:

    @Override
    public boolean before(Authentication authentication, MethodInvocation mi, PreInvocationAttribute attr) {
        // 1) get AuthorisedForGroups & AuthorisedForRoles for the method
        // 2) if either is missing from the method, check the enclosing class 
        // 3) if no annotations found - simply return super.before(...) 
        // 4) else, introspect the 'authentication' and see if it has the required groups/roles 
        // - here you may want to use 'ExpressionBasedAnnotationAttributeFactory' to 
        //   create your own expressions which you then pass to super.before(...). 
        //   This especially makes sense when your groups/roles 
        //   are mapped to GrantedAuthority instances - as it was the case with our code. 

    }

希望这能有所帮助。

最新更新