Reputation: 51
I am trying to configure separate auth and resource servers for oauth2. I am able to configure authrization server successfully and able to authenticate and generate access tokens. Now I want to configure a resource server which can talk to auth server with api end point to validate the access tokens. Below is my resource server configuration.
@Configuration
@EnableResourceServer
@EnableWebSecurity
public class Oauth2SecurityConfiguration extends WebSecurityConfigurerAdapter {
@Override
protected void configure(HttpSecurity http) throws Exception {
System.out.println("Oauth2SecurityConfiguration before");
http
.authorizeRequests()
.antMatchers(HttpMethod.GET, "/api/v1/**").authenticated();
System.out.println("Oauth2SecurityConfiguration after");
}
@Bean
public AccessTokenConverter accessTokenConverter() {
return new DefaultAccessTokenConverter();
}
@Bean
public RemoteTokenServices remoteTokenServices() {
final RemoteTokenServices remoteTokenServices = new RemoteTokenServices();
remoteTokenServices.setCheckTokenEndpointUrl("http://localhost:9000/authserver/oauth/check_token");
remoteTokenServices.setClientId("clientId");
remoteTokenServices.setClientSecret("clientSecret");
remoteTokenServices.setAccessTokenConverter(accessTokenConverter());
return remoteTokenServices;
}
@Override
@Bean
public AuthenticationManager authenticationManager() throws Exception {
OAuth2AuthenticationManager authenticationManager = new OAuth2AuthenticationManager();
authenticationManager.setTokenServices(remoteTokenServices());
return authenticationManager;
}
}
@Configuration
@EnableResourceServer
public class ResourceServerConfig extends ResourceServerConfigurerAdapter {
@Override
public void configure(HttpSecurity http) throws Exception {
http.csrf().disable();
System.out.println("http.csrf().disable()");
http.authorizeRequests().antMatchers(HttpMethod.GET, "/api/v1/**").fullyAuthenticated();
System.out.println("http.authorizeRequests().anyRequest().authenticated()");
}
}
@Configuration
@EnableGlobalMethodSecurity(prePostEnabled = true, proxyTargetClass = true)
public class MethodSecurityConfig extends GlobalMethodSecurityConfiguration {
@Override
protected MethodSecurityExpressionHandler createExpressionHandler() {
return new OAuth2MethodSecurityExpressionHandler();
}
}
Question : 1. why I AuthenticationManager at resource server while all the authentication is delegated to auth server. (I had to add it to load application context)
Apart from this I am facing below issues.
Even though I am not passing authorization headers and access token with the request. It's going through.
http GET "http://localhost:8080/DataPlatform/api/v1/123sw/members"
HTTP/1.1 200 OK
Content-Type: application/json;charset=UTF-8
Date: Mon, 19 Oct 2015 19:45:14 GMT
Server: Apache-Coyote/1.1
Transfer-Encoding: chunked
{
"entities": [],
"errors": [],
"message": null
}
The filters are only invoked at once I don't see the logs for following requests. Does it cache authorization somewhere?
I am new to spring oauth Please let me know if I am doing anything wrong. I am using
spring-security-oauth2 : 2.0.7.RELEASE
spring-security-core : 4.0.1.RELEASE
java : 1.8
Upvotes: 5
Views: 3940
Reputation: 21
The main point make separate endpoints for auth-server and resource-server, that they can services them separately, each his own. As show bellow "/user/getEmployeesListRole/**" -access through auth-server, "/user/getEmployeesListOAuth2/**" - access through resource-server by token, which generated by aouth2-server.Also please pay attention that auth-server and oauth2-server has the same auth-manager
Configuration of spring-boot aouth2-server, resource-server, auth-server in one spring-boot app
1.Entry Point:
/*AuthApplication.java*/
@SpringBootApplication
@EnableDiscoveryClient
@EnableGlobalMethodSecurity(prePostEnabled = true)
public class AuthApplication {
public static void main(String[] args) {
SpringApplication.run(AuthApplication.class, args);
}}
2. Config of aouth2-server:2.1 aouth2-server auth-request [post with basic auth]:/*OAuth2AuthorizationConfig.java*/
@Configuration @EnableAuthorizationServer public class OAuth2AuthorizationConfig extends AuthorizationServerConfigurerAdapter {
private TokenStore tokenStore = new InMemoryTokenStore();
@Autowired @Qualifier("authenticationManagerBean") private AuthenticationManager authenticationManager;
@Autowired @Qualifier("userDetailsServiceBean") private UserDetailsService userDetailsService;
@Override public void configure(ClientDetailsServiceConfigurer clients) throws Exception { clients.inMemory() .withClient("browser") .authorizedGrantTypes("password", "refresh_token") .scopes("ui", "read:ui", "write:ui"); }@Override public void configure(AuthorizationServerEndpointsConfigurer endpoints) throws Exception { endpoints.tokenStore(tokenStore) .authenticationManager(authenticationManager) .userDetailsService(userDetailsService); }
@Override public void configure(AuthorizationServerSecurityConfigurer oauthServer) throws Exception { oauthServer.tokenKeyAccess("permitAll()") .checkTokenAccess("isAuthenticated()") .passwordEncoder(NoOpPasswordEncoder.getInstance()); }}
http://localhost:5000/uaa/oauth/token?grant_type=password&scope=ui write:ui&username=user&password=123456&client_id=browser
3.Config resource-server:4. Config auth-server:/*ResourceServer.java*/
@Configuration @EnableResourceServer class ResourceServer extends ResourceServerConfigurerAdapter { //Here we specify to allow the request to the // url /user/getEmployeesList with valid access token and scope read @Override public void configure(HttpSecurity http) throws Exception { http.requestMatchers() .antMatchers("/user/getEmployeesList/**
") .antMatchers("/user/getEmployeesListOAuth2/**
") .and().authorizeRequests().anyRequest().access("#oauth2.hasScope('ui')");
}}
/*WebSecurityConfig.java*/
@Configuration @EnableWebSecurity public class WebSecurityConfig extends WebSecurityConfigurerAdapter {@Override public void configure(WebSecurity web) throws Exception { web.ignoring().antMatchers("/resources/**"); } @Override protected void configure(HttpSecurity http) throws Exception { http .authorizeRequests() .antMatchers("/user/getEmployeesListRole/**") .access("hasAuthority('WRITE_DATA') && hasAuthority('READ_DATA')") .anyRequest().permitAll() .and().formLogin().permitAll() .and().logout().permitAll() .and().csrf().disable(); } @Override protected void configure(AuthenticationManagerBuilder auth) throws Exception { auth.inMemoryAuthentication().withUser("admin") .password("admin") .authorities("WRITE_DATA", "READ_DATA"); } @Override @Bean public AuthenticationManager authenticationManagerBean() throws Exception { return super.authenticationManagerBean(); } @Override @Bean public UserDetailsService userDetailsServiceBean() throws Exception { return super.userDetailsServiceBean(); } }
Upvotes: 1
Reputation: 759
You don't need @EnableWebSecurity
on Oauth2SecurityConfiguration
@EnableResourceServer
is enough.
You should also replace extends WebSecurityConfigurerAdapter
with extends ResourceServerConfigurerAdapter
.
If you want to use your RemoteTokenServices
instance I recommend you override ResourceServerConfigurerAdapter
public void configure(ResourceServerSecurityConfigurer resources) throws Exception
with
@Override
public void configure( ResourceServerSecurityConfigurer resources ) throws Exception
{
resources.tokenServices( serverConfig.getTokenServices() );
}
Upvotes: -1