Spring Boot Keycloak- Bearer-only - for backend service not working

Mahesh_Loya picture Mahesh_Loya · Feb 3, 2018 · Viewed 9.5k times · Source

I am trying to secure my rest api and frontend using Keycloak.

Frontend is based on Angular 4.

Backend is rest api built using Spring boot.

I have created two client in keycloak admin console,in same realm(testRealm).

front-end client's ACCESS-TYPE is "Public".

Backend client(backendService) ACCESS-TYPE is "Bearer-only".

Front-End is working fine and displays tabs based on roles.

When I try to hit/access backend service call, it gives me below error in browser console-

Failed to load http://localhost:9099/api/transaction

Response for preflight has invalid HTTP status code 401.

Below is the config I am using to secure rest api.

application.properties

server.contextPath=/test
server.port=9090

keycloak.realm: testRealm
keycloak.bearer-only: true
keycloak.auth-server-url: http://localhost:8080/auth
keycloak.ssl-required: external
keycloak.resource: backendService
keycloak.use-resource-role-mappings: true
keycloak.confidential-port: 0
keycloak.credentials.secret=dc04c236-d2b9-560e-b6b2-efa2064b2386

ApiSecurityConfig.java(Spring boot security config for keycloak adapter)

@Configuration
@EnableWebSecurity
@ComponentScan(basePackageClasses = KeycloakSecurityComponents.class)
public class ApiSecurityConfig extends KeycloakWebSecurityConfigurerAdapter {

    @Autowired
    public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {

        KeycloakAuthenticationProvider keycloakAuthenticationProvider = keycloakAuthenticationProvider();
        keycloakAuthenticationProvider.setGrantedAuthoritiesMapper(new SimpleAuthorityMapper());
        auth.authenticationProvider(keycloakAuthenticationProvider);
    }

    @Bean
    public KeycloakSpringBootConfigResolver KeycloakConfigResolver() {
        return new KeycloakSpringBootConfigResolver();
    }

    @Bean
    @Override
    protected SessionAuthenticationStrategy sessionAuthenticationStrategy() {
        return new RegisterSessionAuthenticationStrategy(new SessionRegistryImpl());
    }

    /**
     * Api request URI and their mapping roles and access are configured in this
     * method.This is method from spring security web configuration Override this
     * method to configure the HttpSecurity.
     * 
     */
    @Override
    protected void configure(HttpSecurity http) throws Exception {
        super.configure(http);

        http
            .authorizeRequests()
            .antMatchers("/api/*")
            .hasRole("admin")
            .anyRequest()
            .permitAll();


    }
}

I have verified the keclaok properties in application.properties file,by cross checking the installation JSON file from Keycloak server,which looks like below.

Installation JSON file taken from the Keycloak server

{
  "realm": "testRealm",
  "bearer-only": true,
  "auth-server-url": "http://localhost:8080/auth",
  "ssl-required": "external",
  "resource": "backendService",
  "use-resource-role-mappings": true,
  "confidential-port": 0
}

I have checked keycloak.credentials.secret and its exactly the same what I am using,still it is not allowing access to backend and giving

Unauthorized, status=401

Not sure,If I am missing something,any help is much appreciated..

Answer