【问题标题】:Spring Security 4.0.4 @Secured not securing controller method callSpring Security 4.0.4 @Secured 不保护控制器方法调用
【发布时间】:2016-10-18 23:31:32
【问题描述】:

我没有例外,但是即使用户没有指定角色,也会调用标有@Secured 的方法。我在 pom.xml 中使用 spring-boot-starter-security 1.3.5 但没有 Spring Boot autoconfig 或其他注释。

@RequestMapping(value={"/l"}, method=RequestMethod.GET)
@Secured({"ROLE_TORZSMOD"})
public String list() {
    return "partnerList";
}

我的安全配置:

@Configuration
@EnableWebSecurity
@EnableGlobalMethodSecurity(securedEnabled=true)
public class SecurityConfig extends WebSecurityConfigurerAdapter {
    @Autowired
    DataSource dataSource;

    @Autowired
    protected void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {
        PasswordEncoder encoder = new StandardPasswordEncoder();
        auth.jdbcAuthentication()
            .dataSource(dataSource)
            .passwordEncoder(encoder);
    }

    @Bean
    @Override
    public AuthenticationManager authenticationManagerBean() throws Exception {
        return super.authenticationManagerBean();
    }

    @Override
    protected void configure(HttpSecurity http) throws Exception {
        http
            .formLogin().loginPage("/login").permitAll()
        .and()
            .logout().logoutSuccessUrl("/login?logout").permitAll()
        .and()
            .authorizeRequests()
                .antMatchers("/resources/**").permitAll()
                .anyRequest().authenticated();
    }
}

来自调试日志的登录信息(ROLE_TORZSMOD 不在权限列表中):

2016-06-17 09:55:10,378 DEBUG o.s.s.w.a.i.FilterSecurityInterceptor - Previously Authenticated: org.springframework.security.authentication.UsernamePasswordAuthenticationToken@d78c39df:
Principal: org.springframework.security.core.userdetails.User@65812e3: Username: pappt; Password: [PROTECTED]; Enabled: true; AccountNonExpired: true; credentialsNonExpired: true; 
AccountNonLocked: true; Granted Authorities: ROLE_BIZMOD; Credentials: [PROTECTED]; Authenticated: true; Details: org.springframework.security.web.authentication.WebAuthenticationDetails@0:
RemoteIpAddress: 0:0:0:0:0:0:0:1; SessionId: 7CE797647B43DEDCED00AF439F446FA1; Granted Authorities: ROLE_BIZMOD

【问题讨论】:

  • 试试@PreAuthorize(hasRole('ROLE_TORZSMOD'))
  • 因为这个 ROLE_ 前缀混乱而尝试了 hasAuthority。结果相同。 <security:authorize access="hasAuthority('ROLE_TORZSMOD')"> 在 JSP 中工作。 @PreAuthorize("hasAuthority('ROLE_TORZSMOD')") 没有。还将注解修改为@EnableGlobalMethodSecurity(prePostEnabled=true, securedEnabled=true)
  • tyr @EnableGlobalMethodSecurity(prePostEnabled=true)hasRole 而不是 hasAuthority
  • 试过了,没区别。

标签: spring-security


【解决方案1】:

在这里找到答案:spring @PreAuthorize not working with @EnableGlobalMethodSecurity(prePostEnabled = true)

解决方案 1:

将注释移动到另一个配置类。现在@Secured 和@PreAuthorize 都可以工作了。

@Configuration
@ComponentScan("name.gmail.nsomlai.sawmill.controller")
@EnableWebMvc
@EnableGlobalMethodSecurity(prePostEnabled=true, securedEnabled=true)
public class WebConfig extends WebMvcConfigurerAdapter {
...
}

解决方案 2:

将注释保留在原处并将安全配置类添加到主配置(不确定这是否有任何副作用,但它有效):

public class MasterConfig extends AbstractAnnotationConfigDispatcherServletInitializer {
    ...
    @Override
    protected Class<?>[] getServletConfigClasses() {
        return new Class<?>[] { WebConfig.class, SecurityConfig.class };
    }
    ...
}    

由于我花了 3 天时间来实现一个简单的自定义登录页面和 URL 安全性,如果我想按时完成,我发现使用 Spring Security 风险太大。我可能会实现我自己的简单的基于拦截器的安全性。这对于简单的访问控制来说太复杂了,有太多不同的版本、相互冲突的教程和庞大的文档。

【讨论】:

    猜你喜欢
    • 2016-01-20
    • 1970-01-01
    • 1970-01-01
    • 2015-01-28
    • 1970-01-01
    • 2019-06-17
    • 2018-01-10
    • 2014-08-03
    • 2012-01-12
    相关资源
    最近更新 更多