返回顶部

权限管理的曲折历程,血泪史。可以拦截器实现,也可以spring security。最终解决spring security页面出现重定向问题。

拦截器和过滤器区别,面试高频点了。

  • 拦截器(Interceptor)、 过滤器(filter)

引自:https://www.cnblogs.com/panxuejun/p/7715917.html

拦截器(Interceptor)是spring的,实现很简单。

  • 拦截器代码
public class LoginHandlerInterceptor implements HandlerInterceptor {

    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
        Object user = request.getSession().getAttribute("user");
        if (user == null){
            request.setAttribute("message","没有权限,请先登录");
            request.getRequestDispatcher("/").forward(request,response);//转发
            return false;
        }else {
            return true;
        }
    }
}
  • 配置拦截器,拦截路径。
@Configuration
public class LoginConfig implements WebMvcConfigurer {
    @Override
    public void addInterceptors(InterceptorRegistry registry) {
        registry.addInterceptor(new LoginHandlerInterceptor())
                .addPathPatterns("/**")
                .excludePathPatterns("/","/login","/user/login","/images/**","/js/**","/styles/**");
        registry.addInterceptor(new AdminHandlerInterceptor())
                .addPathPatterns("/account/**","/admin/**","/cost/**","/role/**","/service/**");
    }
}

上面就实现类简单的登录拦截和权限拦截。当然还尝试了 spring security。遇到最大的问题就是重定向。

  • 这里重定向的原因是:ajax请求。不知道有没有解决方案。
  • 表单提交绝对是可以的,这里的登陆验证和登出都不用经过controller,由 spring security完成。注意请求路径。

授权

  • 这儿还有一个🕳:.hasRole("ADMIN"),数据库必须有前缀ROLE_
@Configuration
@EnableWebSecurity
public class SecurityConfig extends WebSecurityConfigurerAdapter {

    @Resource
    private UserDetailsService userDetailsService;

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

    // 认证用户的来源(数据库)
    protected void configure(AuthenticationManagerBuilder auth) throws Exception {
        auth.userDetailsService(userDetailsService).passwordEncoder(passwordEncoder());
    }

    //配置springsecurity相关信息
    protected void configure(HttpSecurity http) throws Exception {
        // 释放静态资源,指定资源拦截规则,指定自定义认证页面,指定退出认证配置,csrf配置
        http.authorizeRequests()
                .antMatchers("/","/toLogin", "/js/**", "/images/**", "/plugin/**", "/styles/**")
                .permitAll()
                .antMatchers("/account/**","/admin/**","/cost/**","/role/**","/service/**").hasRole("ADMIN")
                .anyRequest().authenticated()
                .and()
                .formLogin()
                .loginPage("/toLogin")
                .loginProcessingUrl("/login")
                .defaultSuccessUrl("/main/index")
                .permitAll()
                .and()
                .logout()
                .logoutUrl("/logout")
                .logoutSuccessUrl("/toLogin")
                .invalidateHttpSession(true)
                .permitAll()
                //禁用csrf,建议不禁用,登录和登出必须携带token
                .and()
                .csrf()
                .disable();
    }
}
  • 建议不禁用,登录和登出必须携带token,页面代码


数据库认证

@Service
public class MyUserDetailService implements UserDetailsService {

    @Resource
    private UserMapper mapper;

    @Override
    public UserDetails loadUserByUsername(String s) throws UsernameNotFoundException {
        User user = mapper.selectByTelephone(s);
        if (user == null){
            throw new UsernameNotFoundException("不存在");
        }
        System.out.println(user);
        List<GrantedAuthority> authorities = AuthorityUtils.commaSeparatedStringToAuthorityList(user.getRole());
        return new org.springframework.security.core.userdetails.User(user.getUserName(),new BCryptPasswordEncoder().encode(user.getUserPwd()),authorities);
    }
}

最后没用spring security,还是不太了解,和自己已经实现的东西不太好结合。这个还是要事先考虑好。

每天一个小技巧

posted @ 2021-12-03 17:01  凑数的园丁  阅读(683)  评论(0编辑  收藏  举报