基本身份验证过滤器和身份验证入口点实际上并未使用spring oauth2令牌请求

 张群羽圣文 发布于 2023-01-30 14:07

我已经使用spring的sparklr示例应用程序和我在网上找到的几个示例实现了spring oauth2的资源所有者流程.我用curl测试了令牌请求部分,以便提供客户端和用户凭据:

curl -v --data "username=user1&password=user1&client_id=client1&client_secret=client1&grant_type=password" -X POST "http://localhost:8080/samplerestspringoauth2/oauth/token"

它工作正常,但我做了以下观察:

虽然根据我看到的例子,我使用了BasicAuthentication过滤器,但这并没有真正用于安全过程.由于令牌请求不包含Authentication头,因此BasicAuthentication过滤器只会跳过任何检查.ClientCredentialsTokenEndpointFilter和authentication-server是唯一在令牌请求期间执行安全检查的人.注意到并通过调试验证后,我试图完全删除以下部分:

从配置.但后来我收到了警告:

"无法建立AuthenticationEntryPoint.请确保您具有通过命名空间配置的登录机制(例如表单登录)或指定具有'entry-point-ref'属性的自定义AuthenticationEntryPoint".

下一步,我在http命名空间中添加了entry-point-ref ="clientAuthenticationEntryPoint,并取消了警告.我测试了应用程序并正确播放.

但是,除了上述内容之外,我还在调试期间进行了以下观察:ClientCredentialsTokenEndpointFilter在私有变量中包含其自己的OAuth2AuthenticationEntryPoint入口点,并在由于错误的客户端凭据而失败时使用它.因此,无论在基本过滤器中还是在http命名空间中指定的入口点都无关紧要.最后,ClientCredentialsTokenEndpointFilter将使用自己的私有OAuth2AuthenticationEntryPoint.总结一下我的结论似乎如下:

如果我们在http命名空间中指定端点,则不使用基本过滤器并且可以将其删除.

仅在编译器停止警告时才需要在http命名空间中指定基本过滤器或端点.它们没有实际用途,所使用的端点在ClientCredentialsTokenEndpointFilter中是硬编码的.

下面我将令牌请求的http和端点配置供您参考.我跳过其余的配置以保持帖子易于阅读:


        
        
        
        
        
    


        
        
    

我还假设在令牌请求的原始sparklr应用程序(即spring oauth2示例应用程序)配置中也发生了同样的问题,这非常相似.可以在https://github.com/spring-projects/spring-security-oauth/blob/master/samples/oauth2/sparklr/src/main/webapp/WEB-INF/spring-servlet.xml中找到 ,相关部分如下:


                
                
                
                
                
                
                
                
                
        

我希望spring oauth2能更恰当地与spring spring进行交互,而不必放置不必要的误导性配置,这让我觉得我可能错过了一些东西.由于安全性是一个敏感方面,我想与您分享,并询问我的结论是否正确.

1 个回答
  • / oauth/token提供了两种不同的方法来验证请求令牌的客户端:

    使用HTTP-Basic身份验证(当存在"http-basic"元素时)

    使用org.springframework.security.web.authentication.www.BasicAuthenticationFilter处理身份验证,并处理包含客户端的base64编码凭据的"Authorization"HTTP标头.过滤器仅在存在Authorization标头时执行处理.始终首先尝试此方法.只有当用户提供了包含无效内容的"Authorization"标头时,才会调用http-basic上定义的入口点 - 这就是为什么你没有看到调试器中调用的入口点,尝试设置Authorization HTTP标头和你的断点会受到打击.

    如OAuth标准中所定义,使用client_id和client_secret HTTP参数

    这是使用org.springframework.security.oauth2.provider.client.ClientCredentialsTokenEndpointFilter处理的,默认情况下使用入口点将WWW-Authenticate标头发送回客户端.可以自定义默认入口点(有一个setAuthenticationEntryPoint方法).只有在提供client_id参数时才使用入口点.

    这两种方法都使用不同的方法来获取客户端的用户名+密码,但是针对同一个身份验证管理器进行验证.

    在取出<http-basic>元素时,您观察到的"No AuthenticationEntryPoint可以建立"错误来自Spring Security本身,而不是来自OAuth扩展.原因是Spring Security无法判断自定义过滤器ClientCredentialsTokenEndpointFilter中是否已配置了默认入口点.并且Spring Security的HTTP配置始终必须至少有一个入口点可用.

    所以,完整的逻辑如下:

    当您包含带有无效凭据的"Authorization"标头并且存在<http-basic>元素时,系统将使用<http-basic>元素上定义的入口点.如果未指定(缺少属性entry-point-ref),系统将自动为您创建BasicAuthenticationEntryPoint的默认实例并使用它.

    当您包含带有无效凭据的HTTP参数"client_id"和"client_secret"并且存在自定义过滤器clientCredentialsTokenEndpointFilter时,系统将使用clientCredentialsTokenEndpointFilter bean中定义的入口点(默认情况下为OAuth2AuthenticationEntryPoint的实例)

    如果既没有"授权"标题也没有"client_id"参数,并且端点需要认证("IS_AUTHENTICATED_FULLY"),系统将使用<http entry-point-ref ="">上定义的入口点(如果存在),否则它将使用http-basic上定义的入口点(如上所述)

    如果您既没有指定http-basic(或Spring识别的其他默认身份验证方法),也没有使用<http entry-point-ref ="">指定默认入口点,系统将失败,并且"无法建立AuthenticationIntertryPoint" ",因为它需要至少一个入口点,并且它不理解clientCredentialsTokenEndpointFilter中有一个可用的入口点.

    关于你的观察:

    >>如果我们在http命名空间中指定端点,则不使用基本过滤器并将其删除.

    >如果您使用client_id + client_secret对客户端进行身份验证,则情况属实

    >>仅在编译器停止警告时才需要在http命名空间中指定基本过滤器或端点.它们没有实际用途,所使用的端点在ClientCredentialsTokenEndpointFilter中是硬编码的.

    >部分正确,因为在缺少client_id的情况下将使用入口点.

    配置确实令人困惑(部分原因是OAuth不是Spring Security的本机部分,而是扩展),但所有这些设置都有意义并且在特定情况下使用.

    您所做的更改不会产生任何安全隐患.

    2023-01-30 14:09 回答
撰写答案
今天,你开发时遇到什么问题呢?
立即提问
热门标签
PHP1.CN | 中国最专业的PHP中文社区 | PNG素材下载 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有