2
votes

I have wrote my oven OAuth2 server and I can successfully retrieve access tokens from my server, however when it comes to the client it always returns 'invalid token error'.

I have searched and have read many articles, pages, and links such as the following link: Spring Security OAuth2 Resource Server Always Returning Invalid Token

Yet I cannot solve the problem, here is my code and I would be grateful I you could help me.

Configuration in authentication server :

@Configuration
public class OAuth2Config extends AuthorizationServerConfigurerAdapter {

    private static final String SERVER_RESOURCE_ID = "oauth2-server";

    private static InMemoryTokenStore tokenStore = new InMemoryTokenStore();


    @Configuration
    @EnableResourceServer
    protected static class ResourceServer extends ResourceServerConfigurerAdapter {

        @Override
        public void configure( ResourceServerSecurityConfigurer resources ) throws Exception{
            resources.tokenStore( tokenStore ).resourceId( SERVER_RESOURCE_ID );
        }

        @Override
        public void configure( HttpSecurity http ) throws Exception {
            http.requestMatchers().antMatchers("/user").and().authorizeRequests().antMatchers("/me").access("#oauth2.hasScope('read')");
        }

    } // ResourceServer


    @Configuration
    @EnableAuthorizationServer
    protected static class AuthConfig extends AuthorizationServerConfigurerAdapter {


        @Autowired
        private AuthenticationManager authenticationManager;


        @Override
        public void configure( ClientDetailsServiceConfigurer  clients ) throws Exception {
            clients.inMemory()
                    .withClient( "insert_server" ) // name of client
                    .secret( "{noop}" + "123456" )
                    .authorizedGrantTypes( "refresh_token", "password", "client_credentials" )
                    .scopes( "webclient", "mobileclient" )
                    .resourceIds( SERVER_RESOURCE_ID )
                    .and().withClient("rest_server")
                    .secret( "{noop}" + "123456" )
                    .authorizedGrantTypes( "refresh_token", "password", "client_credentials" )
                    .scopes( "webclient", "mobileclient" )
                    .resourceIds( SERVER_RESOURCE_ID );


            //System.out.println( encoder.encode("123456") );
        }


        @Override
        public void configure( AuthorizationServerEndpointsConfigurer endPoints ) throws Exception  {
           /* endPoints
                    .authenticationManager( this.authenticationManager )
                    .userDetailsService( this.userDetailsService ); */

           endPoints.authenticationManager( this.authenticationManager )
                   .tokenStore( tokenStore )
                   .approvalStoreDisabled();
        }

    } // AuthConfig

}

Web security class in authentication server:

@Configuration
public class WebSecutiryConfigurer extends WebSecurityConfigurerAdapter {

    private BCryptPasswordEncoder encoder = new BCryptPasswordEncoder();


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


    @Override
    @Bean
    public UserDetailsService userDetailsServiceBean( ) throws Exception {
        return super.userDetailsServiceBean();
    }


    @Override
    protected void configure( AuthenticationManagerBuilder auth ) throws Exception{
        auth.inMemoryAuthentication()
                .withUser( "pswin ")
                    .password( "{noop}" + "123456" )
                    .roles( "USER" )
                .and().withUser( "admin" ) // username
                    .password( "{noop}" + "123456" ) // password
                    .roles( "USER", "ADMIN" ); // roles
    }
}

Client Config:

security.oauth2.client.client-id=rest_server
security.oauth2.client.client-secret=123456
security.oauth2.client.access-token-uri=http://localhost:8989/auth/oauth/token
security.oauth2.client.user-authorization-uri=http://localhost:8989/auth/oauth/authorize
security.oauth2.resource.user-info-uri=http://localhost:8989/auth/user

and my controller:

@RestController
@RequestMapping( "/city" )
@EnableResourceServer
public class CityController {

    private CityService cityService;


    //! Constructor
    CityController( CityService cityService ){
        this.cityService = cityService;
    }



    @GetMapping( "/{city_id}" )
    public CityDTO getCityByID( @PathVariable Long city_id ){
        return new CityDTO( cityService.getByID( city_id ) );
    }


    @PreAuthorize("#oauth2.hasScope('webclient')")
    @GetMapping ( "/" )
    public PageDTO getAll( Pageable pageable ){
        Page page = this.cityService.getAll( pageable );
        return new PageDTO( page.map( ( city ) -> new CityDTO( (City)city )  ) );
    }
}

Further details:

Java version: 10 Spring-boot versuin: 2.0.4.RELEASE Spring-cloud version: Finchley.SR1

1

1 Answers

1
votes

As you posted, invalid access token usually happens either 1) token that client sent is different that what oauth2 provider issued OR 2) can be expired if token's TTL is too short. It's hard to know without specific error message but just "invalid token"... but you should be able to find more debugging log in server log ( in spring side ).

One thing you can do is, add breakpoint in OAuth2AuthenticationProcessingFilter#doFilter() since that's where oauth2 check is happening. Debuging step by step should be enough for you to figure out what's wrong with your token.