복붙노트

[SPRING] 클라이언트 비밀없이 Spring OAuth2 서버로부터 access_token을 얻을 수 있습니까?

SPRING

클라이언트 비밀없이 Spring OAuth2 서버로부터 access_token을 얻을 수 있습니까?

Spring Security의 OAuth2 서버 구현을 사용하고 있습니다. 나는 OAuth2 "암호"부여 유형을 사용하여 서버의 / oauth / token 엔드 포인트에서 access_token을 얻으려고 노력하고 있는데, 클라이언트 비밀 번호없이 사용자 이름과 비밀번호와 클라이언트 ID 만 제공합니다. 내 HTTP 요청의 Authorization 헤더에 다음과 같이 클라이언트 ID와 클라이언트 비밀을 제공하면이 작업이 정상적으로 작동합니다.

curl -u clientid:clientsecret http://myhost ... -d "grant_type=password&username=user&password=pw&client_id=OAUTH_CLIENT"

여기에 충고 한대로 Spring OAuth2는 TokenEndpoint에 대한 HTTP Basic Auth를 사용하지 못하게하고 / auth / token 엔드 포인트에 대한 HTTP 기본 인증을 비활성화 할 수있었습니다. 하지만 내가 cURL을 통해 access_token을 얻으려고 할 때 :

curl http://myhost ... -d "grant_type=password&username=user&password=pw&client_id=OAUTH_CLIENT"

BadCredentialsException있어 메시지를 볼 수 있습니다.

내 서버의 로그에. 이 시점에서 나는 약간의 짜증이났다. 왜냐하면이 메시지는 클라이언트 ID 및 / 또는 비밀 번호가 아닌 사용자 이름 및 / 또는 비밀번호에 문제가있을 때 나타납니다. 다음과 같이 cURL 명령에서 클라이언트 비밀 번호를 추가로 제공 한 후 :

 curl http://myhost ... -d "grant_type=password&username=user&password=pw&client_id=OAUTH_CLIENT&client_secret=SECRET"

모든 것이 다시 좋았습니다.

그렇다면 클라이언트 인증을 / auth / token 엔드 포인트에 액세스 할 수있는 방법으로 제공해야한다는 의미입니까?

추신 : 나는 보안에 관해서는 일반적으로 HTTP 기본 인증을 통해이 끝점을 보호하는 것이 좋지만 실제로는 할 수없는 사용 사례가 있음을 알고 있습니다.

편집하다:

나는 클라이언트 비밀을 생략하는 방법을 찾은 것 같다. 내 OAuth2 서버 구성은 다음과 같습니다 (allowFormAuthenticationForClients () 및 autoApprove (true) 호출 참고).

@Configuration
@EnableAuthorizationServer
class OAuth2Config extends AuthorizationServerConfigurerAdapter {

    private final AuthenticationManager authenticationManager;

    public OAuth2Config(AuthenticationManager authenticationManager) {
        this.authenticationManager = authenticationManager;
    }

    @Override
    public void configure(AuthorizationServerEndpointsConfigurer endpoints) throws Exception {
        endpoints.authenticationManager(this.authenticationManager);
    }

    @Override
    public void configure(AuthorizationServerSecurityConfigurer oauth) throws Exception {
        // allows access of /auth/token endpoint without HTTP Basic authentication
        oauth.allowFormAuthenticationForClients();  
    }

    @Override
    public void configure(ClientDetailsServiceConfigurer clients) throws Exception {
        clients
        .inMemory()
        .withClient("acme")
        .autoApprove(true) // <- allows for client id only
        .authorizedGrantTypes("authorization_code", "refresh_token", "password").scopes("openid");
    }

}

II 편집 :

여기에있는 질문 : Spring Security OAuth 2.0 - 인증 코드 부여에 항상 필요한 클라이언트 비밀은이 코드와 매우 밀접하게 관련되어 있지만 OAuth2 권한 부여 유형 인 "Authorization Code"를 처리하므로 권한 부여 유형으로 얻는 것과 같은 다른 워크 플로우가 발생합니다 "암호".

해결법

  1. ==============================

    1.사양 (RFC 6749)에 따르면 응용 프로그램의 클라이언트 유형이 공용 인 경우 클라이언트 비밀은 필요하지 않습니다. 반대로 클라이언트 유형이 기밀이면 클라이언트 비밀이 필요합니다.

    사양 (RFC 6749)에 따르면 응용 프로그램의 클라이언트 유형이 공용 인 경우 클라이언트 비밀은 필요하지 않습니다. 반대로 클라이언트 유형이 기밀이면 클라이언트 비밀이 필요합니다.

    Spring이 클라이언트 타입을 설정하는 API를 제공한다면, 클라이언트 타입을 public으로 설정하십시오.

  2. ==============================

    2.Spring Boot의 구현은 인증을 위해 클라이언트 - 비밀이 전달되어야합니다. 그러나 AuthorizationServerConfigurer 유형의 bean을 작성하고 직접 구성하여이를 겹쳐 쓸 수 있습니다. 이것은 문서에 대한 링크입니다 ...

    Spring Boot의 구현은 인증을 위해 클라이언트 - 비밀이 전달되어야합니다. 그러나 AuthorizationServerConfigurer 유형의 bean을 작성하고 직접 구성하여이를 겹쳐 쓸 수 있습니다. 이것은 문서에 대한 링크입니다 ...

  3. ==============================

    3.기본 인증을 사용하고 비밀번호는 비워 둡니다.

    기본 인증을 사용하고 비밀번호는 비워 둡니다.

  4. from https://stackoverflow.com/questions/43356590/is-it-possible-to-get-an-access-token-from-spring-oauth2-server-without-client-s by cc-by-sa and MIT license