【Spring Security OAuth2】客户端授权模式(client credentials)~资源服务配置

例子基于Spring Boot 2.1.7.RELEASE ,使用mysql数据库
本例中资源服务为独立的应用

参考资源: Resource Server Configuration

  • 添加一个实现了ResourceServerConfigurer接口的实现类且使用@EnableResourceServer注解进行标注

ResourceServerConfigurer接口有一个实现类ResourceServerConfigurerAdapter,这里我们继承这个类


/**
 * Created by liuquan on 2019/8/13.
 */
@Configuration
@EnableResourceServer
public class CustomResourceServerConfigurer extends ResourceServerConfigurerAdapter {

    @Override
    public void configure(ResourceServerSecurityConfigurer resources) throws Exception {
    
    }

    @Override
    public void configure(HttpSecurity http) throws Exception {
    
    }
}

@EnableResourceServer注解会导入一个配置类ResourceServerConfiguration

protected void configure(HttpSecurity http) throws Exception {
	ResourceServerSecurityConfigurer resources = new ResourceServerSecurityConfigurer();
	ResourceServerTokenServices services = resolveTokenServices();
	if (services != null) {
		resources.tokenServices(services);
	}
	else {
		if (tokenStore != null) {
			resources.tokenStore(tokenStore);
		}
		else if (endpoints != null) {
			resources.tokenStore(endpoints.getEndpointsConfigurer().getTokenStore());
		}
	}
	if (eventPublisher != null) {
		resources.eventPublisher(eventPublisher);
	}
	for (ResourceServerConfigurer configurer : configurers) {
		configurer.configure(resources);
	}
	// @formatter:off
	http.authenticationProvider(new AnonymousAuthenticationProvider("default"))
	// N.B. exceptionHandling is duplicated in resources.configure() so that
	// it works
	.exceptionHandling()
			.accessDeniedHandler(resources.getAccessDeniedHandler()).and()
			.sessionManagement()
			.sessionCreationPolicy(SessionCreationPolicy.STATELESS).and()
			.csrf().disable();
	// @formatter:on
	http.apply(resources);
	if (endpoints != null) {
		// Assume we are in an Authorization Server
		http.requestMatcher(new NotOAuthRequestMatcher(endpoints.oauth2EndpointHandlerMapping()));
	}
	for (ResourceServerConfigurer configurer : configurers) {
		// Delegates can add authorizeRequests() here
		configurer.configure(http);
	}
	if (configurers.isEmpty()) {
		// Add anyRequest() last as a fall back. Spring Security would
		// replace an existing anyRequest() matcher with this one, so to
		// avoid that we only add it if the user hasn't configured anything.
		http.authorizeRequests().anyRequest().authenticated();
	}

第二行,在创建ResourceServerSecurityConfigurer对象时会默认设置resourceId属性值为oauth2-resource
第三行,从系统中获取ResourceServerTokenServices对象,系统提供了两个实现类(DefaultTokenServicesRemoteTokenServices),本例中采用RemoteTokenServices
第十八行,循环调用ResourceServerConfigurer对象中的configure(ResourceServerSecurityConfigurer resources)方法
第三十六行,循环调用ResourceServerConfigurer对象中的configure(HttpSecurity http)方法

创建两个服务接口

@Controller
public class ApiController {

    @RequestMapping(value = "/serverA")
    @ResponseBody
    public Map<String,String> serverA(){
        Map<String,String> resourceInfo = new HashMap<>();
        resourceInfo.put("serverName","serverA");
        return resourceInfo;
    }

    @RequestMapping(value = "/serverB")
    @ResponseBody
    public Map<String,String> serverB(){
        Map<String,String> resourceInfo = new HashMap<>();
        resourceInfo.put("serverName","serverB");
        return resourceInfo;
    }

}
@Configuration
@EnableResourceServer
public class CustomResourceServerConfigurer extends ResourceServerConfigurerAdapter {

    @Override
    public void configure(ResourceServerSecurityConfigurer resources) throws Exception {
        resources.resourceId("resource");//每个资源服务都有一个唯一的ID
    }

    @Override
    public void configure(HttpSecurity http) throws Exception {
        http.authorizeRequests()
                .antMatchers("/serverA").permitAll()//不需要验证
                .antMatchers("/serverB").authenticated();//需要通过验证
    }
}
/**
 * Created by liuquan on 2019/8/14.
 */
@Configuration
public class RemoteTokenService {

    @Autowired
    private Environment environment;

    @Bean
    public ResourceServerTokenServices tokenServices(){
        RemoteTokenServices remoteTokenServices = new RemoteTokenServices();
        remoteTokenServices.setCheckTokenEndpointUrl(environment.getProperty("security.oauth2.checkTokenAccess"));
        remoteTokenServices.setClientId(environment.getProperty("security.oauth2.client.clientid"));
        remoteTokenServices.setClientSecret(environment.getProperty("security.oauth2.client.clientSecret"));
        return remoteTokenServices;
    }

}
server.port=8082

spring.datasource.url=jdbc:mysql://localhost:3306/part01?useUnicode=true&characterEncoding=utf-8&useSSL=false
spring.datasource.username=root
spring.datasource.password=123456
spring.datasource.driver-class-name=com.mysql.jdbc.Driver

security.oauth2.client.clientid=app
security.oauth2.client.clientSecret=app
security.oauth2.checkTokenAccess=http://localhost:8081/oauth/check_token

【Spring Security OAuth2】客户端授权模式(client credentials)~资源服务配置_第1张图片
【Spring Security OAuth2】客户端授权模式(client credentials)~资源服务配置_第2张图片

你可能感兴趣的:(spring,boot)