Spring-Security-Oauth2:访问此资源需要完全身份验证

时间:2014-11-12 07:17:02

标签: java oauth-2.0 unauthorized spring-security-oauth2

我正在尝试将spring-security-oauth2.0与基于Java的配置一起使用。我的配置已完成,但是当我在tomcat上部署应用程序并点击访问令牌的/oauth/token网址时,Oauth会生成以下错误:

<oauth>
<error_description>Full authentication is required to access this resource</error_description>
<error>unauthorized</error>
</oauth>

我的配置位于Git hub, please click on link

代码很大,所以请参考git。我正在使用chrome postman客户端发送请求。以下是我的要求。

POST /dummy-project-web/oauth/token HTTP/1.1
Host: localhost:8081
Cache-Control: no-cache
Content-Type: application/x-www-form-urlencoded

grant_type=client_credentials&client_id=abc%40gmail.com&client_secret=12345678 

错误就像,Oauth的URL是安全的,但在配置中,我给予访问此URL的所有权限。这个问题实际上是什么?

8 个答案:

答案 0 :(得分:20)

默认情况下,client_idclient_secret应该位于Authorization标头中,而不是form-urlencoded主体。

  1. 将您的client_idclient_secret连接起来,并在它们之间加上冒号:abc@gmail.com:12345678
  2. Base 64对结果进行编码:YWJjQGdtYWlsLmNvbToxMjM0NTY3OA==
  3. 设置授权标题:Authorization: Basic YWJjQGdtYWlsLmNvbToxMjM0NTY3OA==

答案 1 :(得分:16)

默认情况下,Spring OAuth需要基本的HTTP身份验证。如果要使用基于Java的配置将其关闭,则必须允许客户端进行表单身份验证,如下所示:

@Configuration
@EnableAuthorizationServer
protected static class OAuth2Config extends AuthorizationServerConfigurerAdapter {
  @Override
  public void configure(AuthorizationServerSecurityConfigurer oauthServer) throws Exception {
    oauthServer.allowFormAuthenticationForClients();
  }
}

答案 2 :(得分:5)

原因是默认情况下/oauth/token端点受Basic Access Authentication保护。

您需要做的就是在请求中添加Authorization标题。

您可以使用curl之类的工具轻松测试它,方法是发出以下命令:

curl.exe --user abc@gmail.com:12345678 http://localhost:8081/dummy-project-web/oauth/token?grant_type=client_credentials

答案 3 :(得分:1)

使用Spring OAuth 2.0.7-RELEASE,以下命令适用于我

curl -v -u abc@gmail.com:12345678 -d "grant_type=client_credentials" http://localhost:9999/uaa/oauth/token

它也适用于Chrome POSTMAN,只需确保客户端和秘密在&#34; Basic Auth&#34;选项卡,将方法设置为&#34; POST&#34;并在&#34;表格数据中添加授权类型&#34;标签

答案 4 :(得分:1)

您应该预先验证令牌api "/oauth/token"

扩展ResourceServerConfigurerAdapter并覆盖configure function来做到这一点。

例如:

http.sessionManagement().sessionCreationPolicy(SessionCreationPolicy.STATELESS).and().authorizeRequests().antMatchers("/oauth/token").permitAll().
anyRequest().authenticated();

答案 5 :(得分:0)

我遇到了同样的问题,但是我通过以下课程解决了这个问题:

import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.authentication.AuthenticationManager;
import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity;
import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
import org.springframework.security.crypto.password.NoOpPasswordEncoder;
import org.springframework.security.crypto.password.PasswordEncoder;

@Configuration
@EnableWebSecurity
public class OAuthSecurityConfiguration extends WebSecurityConfigurerAdapter {

    @Bean
    @Override
    public AuthenticationManager authenticationManager() throws Exception {
        return super.authenticationManager();
    }

    @Bean
    public PasswordEncoder passwordEncoder() {
        return NoOpPasswordEncoder.getInstance();
    }
}

答案 6 :(得分:0)

这令人难以置信但真实。

<块引用>

csrf 过滤器默认启用,它实际上阻止任何 POST、PUT 或不包含 de csrf 令牌的 DELETE 请求。

尝试使用 GET 而不是 POST 来确认就是这样。

如果是这样,则允许任何 HTTP 方法:

@Throws(Exception::class)
override fun configure(http: HttpSecurity) {

    /**
     * Allow POST, PUT or DELETE request
     *
     * NOTE: csrf filter is enabled by default and it actually blocks any POST, PUT or DELETE requests
     * which do not include de csrf token.
     */
    http.csrf().disable()

}

如果您获得 401,最直观的做法是认为在请求中您没有 Auth 或者您在标题中缺少有关授权的内容。

但显然有一个内部函数正在过滤使用 POST 的 HTTP 方法并返回 401。修复它后,我认为这是状态代码的缓存问题,但显然不是。

GL

答案 7 :(得分:-5)

设置lis=list(randreal) print(lis) management.security.enabled=false我解决了这个问题。