繁体   English   中英

如何修复 Spring Security 中的角色?

[英]How to fix role in Spring Security?

我试图在我的项目中使用 Spring Security,这是代码:

@Override
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
    // TODO Auto-generated method stub
    //super.configure(auth);
    //auth.inMemoryAuthentication().withUser("admin").password("1111").roles("USER");
    auth
        .jdbcAuthentication()
            .dataSource(dataSource)
            .usersByUsernameQuery("select username, password, 1 from users where username=?")
            .authoritiesByUsernameQuery("select users_username, roles_id  from roles_users where users_username=?")
            .rolePrefix("ROLE_");
}   

@Override
protected void configure(HttpSecurity http) throws Exception {
    http
        .csrf().disable();      
    http
        .httpBasic();
    http
        .authorizeRequests()
            .anyRequest().authenticated();
    http
        .authorizeRequests()
            .antMatchers("/users/all").hasRole("admin")
            .and()
        .formLogin();
    http
        .exceptionHandling().accessDeniedPage("/403");
}

这是问题所在:

想象一下,我们的数据库中有两个用户(一个具有user角色,另一个具有admin角色),一个是管理员,第二个是用户,问题是当我以用户身份(只有user角色)连接时,它可以访问管理资源(这不是预期的行为)。

我认为这个查询中的问题:

"select username, password, 1 from users where username=?" 

根据那个username是主键?

如果有人知道我如何解决这个问题?

您的第一个匹配器anyRequest()始终被应用,因为匹配器的顺序很重要,请参阅HttpSecurity#authorizeRequests

请注意,匹配器是按顺序考虑的。 因此,以下内容无效,因为第一个匹配器匹配每个请求并且永远不会到达第二个映射:

 http.authorizeRequests().antMatchers("/**").hasRole("USER").antMatchers("/admin/**") .hasRole("ADMIN")

您修改和简化的配置:

@Override
protected void configure(HttpSecurity http) throws Exception {
    http
        .csrf().disable()      
        .httpBasic()
            .and()
        .authorizeRequests()
            .antMatchers("/users/all").hasRole("admin")
            .anyRequest().authenticated()
            .and()
        .formLogin()
            .and()
        .exceptionHandling().accessDeniedPage("/403");
}

问题在于配置HttpSecurity时规则的顺序。 发生的事情是当请求进来并击中

authorizeRequests().anyRequest().authenticated() 

并且由于用户已通过身份验证,因此它永远不会进入

.antMatchers("/users/all").hasRole("admin")

以下是如何配置它的示例:

@Override
protected void configure(HttpSecurity http) throws Exception {
    http
        .csrf().disable()      
        .httpBasic()
        .and()
    .authorizeRequests()
        .antMatchers("/public").permitAll()
        .antMatchers("/user").hasRole("USER")
        .antMatchers("/admin").hasRole("ADMIN")
        .anyRequest().authenticated()
        .and()
    .formLogin()
        .and()
    .exceptionHandling().accessDeniedPage("/403");
}

它使用责任链模式。 它将遍历规则链,直到找到匹配的规则。 永远不会到达匹配规则之后的任何规则。 通常在为经过身份验证的请求编写规则时,更具体的规则将首先出现。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM