Как я могу сделать контроль доступа властей в весенней безопасности oauth2? - PullRequest
1 голос
/ 24 мая 2019

Я пытаюсь использовать Spring Security oauth2 для контроля доступа с помощью аннотаций, таких как @PreAuthorize ("hasAuthority ('perm2')") или конфигурации безопасности в WebSecurityConfigurerAdapter. Но я всегда получаю 403 запрета, когда пытаюсь получить доступAPI, аннотированный @PreAuthorize ("hasAuthority ('perm2')") после того, как я вхожу в систему пользователем, у которого есть полномочия 'perm2'. Я установил точку останова в ClientDetailsUserDetailsService, но загруженные UserDetails не содержали никаких прав доступа. Более того, я обнаружил,чтобы я мог извлечь полномочия, содержащие «perm2», из AuthoritiesExtractor.
Один из способов сделать это - переписать UserDetailService, чтобы я мог установить полномочия для UserDetails AuthoritiesExtractor.Но мой вопрос:

Это лучшая практика?или я просто пропускаю что-то еще?

Ниже приведен мой пробный код, за которым следует учебник по baeldung

мой код авторизации здесь

@SpringBootApplication
@EnableResourceServer
@RestController
public class App extends SpringBootServletInitializer {


    @GetMapping("/user/me")
    public Principal user(Principal principal) {
        return principal;
    }


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


    @Configuration
    @EnableAuthorizationServer
    public static class AuthServerConfig extends AuthorizationServerConfigurerAdapter {
        @Autowired
        private BCryptPasswordEncoder passwordEncoder;

        @Override
        public void configure(
                AuthorizationServerSecurityConfigurer oauthServer) throws Exception {
            oauthServer.tokenKeyAccess("permitAll()")
                    .checkTokenAccess("isAuthenticated()");
        }

        @Override
        public void configure(ClientDetailsServiceConfigurer clients) throws Exception {
            clients.inMemory()
                    .withClient("SampleClientId")
                    .secret(passwordEncoder.encode("secret"))
                    .authorizedGrantTypes("authorization_code")
                    .scopes("user_info")
                    .autoApprove(true)
                    .redirectUris("http://localhost:8082/ui/login", "http://localhost:8083/ui2/login");
        }
    }

    @Configuration
    @Order(1)
    public static class SecurityConfig extends WebSecurityConfigurerAdapter {

        @Override
        protected void configure(HttpSecurity http) throws Exception {
            http.requestMatchers()
                    .antMatchers("/login", "/oauth/authorize")
                    .and()
                    .authorizeRequests()
                    .anyRequest().authenticated()
                    .and()
                    .formLogin().permitAll();
        }

        @Override
        protected void configure(AuthenticationManagerBuilder auth) throws Exception {
            auth.inMemoryAuthentication()
                    .withUser("john")
                    .password(passwordEncoder().encode("123"))
                    .roles("USER").authorities("perm1").and()
                    .withUser("tom")
                    .password(passwordEncoder().encode("123"))
                    .roles("USER")
                    .authorities("perm1", "perm2");
        }

        @Bean
        public BCryptPasswordEncoder passwordEncoder() {
            return new BCryptPasswordEncoder();
        }
    }

моя конфигурация клиента здесь:

@Configuration
@EnableOAuth2Sso
@SpringBootApplication
@EnableGlobalMethodSecurity(securedEnabled = true,prePostEnabled =true)
public class App extends WebSecurityConfigurerAdapter {

    @Bean
    AuthoritiesExtractor authoritiesExtractor(){
        return new FixedAuthoritiesExtractor();
    }

    @Override
    public void configure(HttpSecurity http) throws Exception {
        http.antMatcher("/**")
                .authorizeRequests()
                .antMatchers("/", "/login**")
                .permitAll()
                .anyRequest()
                .hasAuthority("perm1").anyRequest()
                .authenticated();
    }

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

и это мой контроллер:

@Controller
public class MyController {

    @GetMapping("/securedPage")
    @PreAuthorize("hasAuthority('perm2')")
    public String securedPage() {
        return  "securedPage";
    }

    @GetMapping("/testPerm")
    @PreAuthorize("hasAuthority('perm3')")
    public @ResponseBody
    String testPerm() {
        return  "This could not be happened!";
    }
}

То, что я ожидаю, это:
когда я захожу с john, я получаю запрет при доступеsecuredPage.
Но когда я захожу с Томом, я могу получить доступ к securedPage.

Дело в том, что, кто бы я ни входил, я получаю запрещенную страницу ниже

Whitelabel Error Page
This application has no explicit mapping for /error, so you are seeing this as a fallback.

Fri May 24 11:29:09 CST 2019
There was an unexpected error (type=Forbidden, status=403).
Forbidden
...