Shiro

1215

shiro

Apache Shiro是一个强大且易用的Java安全框架,执行身份验证、授权、密码和会话管理。使用Shiro的易于理解的API,可以快速、轻松地获得任何应用程序,从最小的移动应用程序到最大的网络和企业应用程序。

shiro 认证流程

ShiroBasicArchitecture

  1. Subject 代表的就是当前用户,当前操作的用户

  2. SecurityManager 它是Shiro框架的核心,典型的Facade模式,Shiro通过SecurityManager来管理内部组件实例,并通过它来提供安全管理的各种服务。具体的管理参考下图

  3. Realm Realm充当了Shiro与应用安全数据间的“桥梁”或者“连接器”。也就是说,当对用户执行认证(登录)和授权(访问控制)验证时,Shiro会从应用配置的Realm中查找用户及其权限信息。(Authentication,Authorization

shiro架构图

ShiroArchitecture

Shiro基本功能

ShiroFeatures

  • Authentication:身份认证 / 登录,验证用户是不是拥有相应的身份;

  • Authorization:授权,即权限验证,验证某个已认证的用户是否拥有某个权限;即判断用户是否能做事情,常见的如:验证某个用户是否拥有某个角色。或者细粒度的验证某个用户对某个资源是否具有某个权限;

  • Session Management:会话管理,即用户登录后就是一次会话,在没有退出之前,它的所有信息都在会话中;会话可以是普通 JavaSE 环境的,也可以是如 Web 环境的;

  • Cryptography:加密,保护数据的安全性,如密码加密存储到数据库,而不是明文存储;

  • **Web Support:**Web 支持,可以非常容易的集成到 Web 环境;

  • Caching:缓存,比如用户登录后,其用户信息、拥有的角色 / 权限不必每次去查,这样可以提高效率;

  • Concurrency:shiro 支持多线程应用的并发验证,即如在一个线程中开启另一个线程,能把权限自动传播过去;

  • Testing:提供测试支持;

  • Run As:允许一个用户假装为另一个用户(如果他们允许)的身份进行访问;

  • Remember Me:记住我,这个是非常常见的功能,即一次登录后,下次再来的话不用登录了

springboot 集成 shiro

  1. 添加依赖
<dependency>
    <groupId>org.apache.shiro</groupId>
    <artifactId>shiro-spring</artifactId>
    <version>1.8.0</version>
</dependency>

  1. 配置SecurityManager Bean
@Bean
public SecurityManager securityManager(){
    DefaultWebSecurityManager defaultWebSecurityManager = new DefaultWebSecurityManager();
    defaultWebSecurityManager.setRealm(realm());
    return defaultWebSecurityManager;
}
  1. 配置Realm Bean
@Bean
public Realm realm(){
    CustomerRealm realm = new CustomerRealm();
    return realm;
}
  1. 配置Shiro 拦截器
//ShiroFilterFactoryBean
@Bean
public ShiroFilterFactoryBean shiroFilterFactoryBean(){
    ShiroFilterFactoryBean sfBean = new ShiroFilterFactoryBean();
    sfBean.setSecurityManager(securityManager());
    HashMap<String, String> map = new HashMap<>();
    //静态资源放行
    map.put("/admin/css/**","anon"); //anonymous匿名访问
    map.put("/admin/js/**","anon");
    map.put("/admin/fonts/**","anon");
    map.put("/admin/images/**","anon");
    map.put("/admin/simplemde/**","anon");
    map.put("/admin/login/exit","logout");


    map.put("/admin/**","authc"); //authc 授权访问
    sfBean.setLoginUrl("/admin/login");

    sfBean.setFilterChainDefinitionMap(map);
    return sfBean;
}
  1. 配置自定义Ream
public class CustomerRealm extends AuthorizingRealm {

    @Autowired
    Userservice userservice;

    //重写授权方法
    @Override
    protected AuthorizationInfo doGetAuthorizationInfo(PrincipalCollection principalCollection) {
        return null;
    }

    //重写认证方法
    @Override
    protected AuthenticationInfo doGetAuthenticationInfo(AuthenticationToken token) throws AuthenticationException {
        log.warn("认证!!!!!!!!");
        String username = (String) token.getPrincipal();
        if(username == null){
            return null;
        }

        User user = userservice.findByEmail(username);
        if (user == null){
            //没有这个用户
            throw new UnknownAccountException();
        }
		//检验密码,如何不符合就抛出异常
        SimpleAccount simpleAccount = new SimpleAccount(username,user.getPassword(),getName());
        
        //将用户信息保存在Shiro session中
        Subject subject = SecurityUtils.getSubject();
        Session session = subject.getSession();
        session.setAttribute("user",user);
        return simpleAccount;
    }



}

shiro拦截器

anon 匿名拦截器 不需要登录即可访问;一般用于静态资源过滤;示例“/static/**=anon
authc 认证拦截器 用户需要认证,如果没有认证,将会重定向到的登录页面。
roles 角色授权拦截器 验证用户是否拥有所有角色
perms 权限授权拦截器 验证用户是否拥有所有权限
logout 退出拦截器 主要属性:redirectUrl:退出成功后重定向的地址(默认重定向地址为 / )
ssl SSL拦截器 只有请求协议是https才能通过;否则自动跳转会https端口(443)