【问题标题】:spring boot oauth2 configuration: resource server remains unprotectedspring boot oauth2配置:资源服务器保持不受保护
【发布时间】:2018-05-12 04:06:52
【问题描述】:

我已经使用spring boot实现了授权服务器和资源服务器。授权服务器工作正常,我能够获得令牌。但是我的资源服务器仍然不受保护。我的目标是资源服务器只能由拥有有效访问令牌的人访问。

我的整个代码是:

@Configuration
@EnableAuthorizationServer
public class AuthorizationServerConfig extends AuthorizationServerConfigurerAdapter {

    @Autowired
    TokenStore tokenStore;

    @Autowired
    private AuthenticationManager authenticationManager;

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

    @Override
    public void configure(ClientDetailsServiceConfigurer clients) throws Exception {
        clients
            .inMemory()
            .withClient("client")
            .scopes("read", "write")
            .authorities("ROLE_CLIENT", "ROLE_TRUSTED_CLIENT")
            .authorizedGrantTypes("password", "refresh_token")
            .secret("secret")
            .accessTokenValiditySeconds(180)
            .refreshTokenValiditySeconds(600);
    }

    @Override
    public void configure(AuthorizationServerSecurityConfigurer security) throws Exception {
        super.configure(security); //To change body of generated methods, choose Tools | Templates.
    }

}

@Configuration
@EnableResourceServer
public class ResourceServerConfig extends ResourceServerConfigurerAdapter {

    @Autowired
    private TokenStore tokenStore;

    @Override
    public void configure(ResourceServerSecurityConfigurer resources) throws Exception {
        resources
                .tokenServices(tokenServices())
                .resourceId("MY_RESOURCE");
    }

    @Override
    public void configure(HttpSecurity http) throws Exception {
        http
                .anonymous().disable()
                .requestMatchers().antMatchers("/**")
            .and()
                .authorizeRequests()
                    .antMatchers("/").access("hasRole('USER')")
                    .antMatchers("/secure/").access("hasRole('ADMIN')")
            .and()
                .exceptionHandling().accessDeniedHandler(new OAuth2AccessDeniedHandler());
    }

    @Bean
    @Primary
    public DefaultTokenServices tokenServices() {
        final DefaultTokenServices defaultTokenServices = new DefaultTokenServices();
        defaultTokenServices.setTokenStore(tokenStore);
        return defaultTokenServices;
    }

}

@Configuration
@EnableWebSecurity
public class OAuth2SecurityConfig extends WebSecurityConfigurerAdapter{

    @Override
    protected void configure(AuthenticationManagerBuilder auth) throws Exception {
        auth.inMemoryAuthentication()
        .withUser("bill").password("abc123").roles("ADMIN").and()
        .withUser("bob").password("abc123").roles("USER");
    }

    @Override
    protected void configure(HttpSecurity http) throws Exception {
        http
                .csrf().disable()
                .anonymous().disable()
                .authorizeRequests()
                    .antMatchers("/oauth/token").permitAll();
    }
}

@Configuration
@EnableGlobalMethodSecurity
public class MethodSecurityConfig extends GlobalMethodSecurityConfiguration {

    @Override
    protected MethodSecurityExpressionHandler createExpressionHandler() {
        return new OAuth2MethodSecurityExpressionHandler();
    }
}

@SpringBootApplication
@RestController
public class Application extends SpringBootServletInitializer{

    public static void main(String[] args) {
        SpringApplication.run(Application.class, args);
    }

    @Override
    protected SpringApplicationBuilder configure(SpringApplicationBuilder application) {
        return application.sources(Application.class);
    }

    @GetMapping(value = "/")
    public ResponseEntity<?> hello(){
        return ResponseEntity.ok("Hello World");
    }

    @GetMapping(value = "/secure/")
    public ResponseEntity<?> secure(){
        return ResponseEntity.ok("Secure Resorce");
    }
    @Bean
    public TokenStore tokenStore() {
        return new InMemoryTokenStore();
    }

}

<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
    <modelVersion>4.0.0</modelVersion>

    <groupId>com.example</groupId>
    <artifactId>boot-oauth2</artifactId>
    <version>1.0-SNAPSHOT</version>
    <packaging>war</packaging>

    <name>boot-oauth2</name>

    <parent>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-parent</artifactId>
        <version>1.5.2.RELEASE</version>
    </parent>

    <properties>
        <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
        <maven.compiler.source>1.8</maven.compiler.source>
        <maven.compiler.target>1.8</maven.compiler.target>
    </properties>


    <dependencies>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-security</artifactId>
        </dependency>
        <dependency>
            <groupId>org.springframework.security.oauth</groupId>
            <artifactId>spring-security-oauth2</artifactId>
        </dependency>

    </dependencies>

    <build>
        <plugins> 
            <plugin>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-maven-plugin</artifactId>
            </plugin>

        </plugins>
    </build>
</project>

我错过了什么? 感谢您的帮助。

更新: 我发现我的资源服务器由于存在OAuth2SecurityConfig 类而不受保护。如果我删除这个类并添加以下类(我已经移动了 inMemory 用户),那么资源服务器会根据需要受到保护

@Configuration
public class WebSecurityGlobalConfig extends GlobalAuthenticationConfigurerAdapter {

    @Autowired
    UserService userService;

    @Override
    public void init(AuthenticationManagerBuilder auth) throws Exception {
        auth.inMemoryAuthentication()
        .withUser("bill").password("abc123").roles("ADMIN").and()
        .withUser("bob").password("abc123").roles("USER");
    }

}

所以,我感觉到 OAuth2SecurityConfig 类中不正确的 HttpSecurity 配置与资源服务器配置冲突。 那么,我该如何配置 OAuth2SecurityConfig 的 HttpSecurity 以便它允许资源服务器路径的访问令牌保护和非资源服务器路径的正常 Web 安全

【问题讨论】:

  • 一切都在同一个应用程序中还是分开?
  • 一切尽在一个应用中

标签: spring spring-boot spring-security spring-security-oauth2


【解决方案1】:

经过大量的谷歌搜索,我终于找到了解决方案。

这是由于过滤器的顺序。在 spring-boot-1.5.1 中更改了 OAuth2 资源过滤器的顺序。正如更改日志所说

OAuth2 资源过滤器的默认顺序已从 3 更改为 SecurityProperties.ACCESS_OVERRIDE_ORDER - 1. 这将它放在 执行器端点,但在基本身份验证过滤器链之前。 可以通过设置恢复默认 security.oauth2.resource.filter-order = 3

所以,我通过在 application.properties security.oauth2.resource.filter-order = 3 中设置,将我的 OAuth2 资源服务器过滤器的顺序更改为 3,我的问题就解决了。

【讨论】:

  • 谢谢,节省了我很多时间!
  • 此属性已在启动 2.x 中删除。有什么解决办法吗?
【解决方案2】:

使用 @EnableGlobalMethodSecurity(prePostEnabled = true) 注释您的 OAuth2SecurityConfig

【讨论】:

    【解决方案3】:

    我遇到了同样的问题。

    我有另一个扩展 WebSecurityConfigurerAdapter 的类,我猜它与 AuthorizationServerConfigurerAdapter 冲突。

    我刚刚删除了 WebSecurityConfigurerAdapter 类并且它工作了。

    【讨论】:

      猜你喜欢
      • 2020-11-30
      • 2015-03-19
      • 2017-08-18
      • 2020-10-31
      • 2018-07-26
      • 1970-01-01
      • 2021-02-07
      • 2015-11-30
      • 2016-01-18
      相关资源
      最近更新 更多