(课堂作业)spring-boot集成shiro的步骤及代码解析

1.创建一个简单的Springboot项目,包含shiro和mybatis-plus。

2.集成shiro

        2.1引入依赖

 <dependency>
     <groupId>org.apache.shiro</groupId>
     <artifactId>shiro-spring-boot-web-starter</artifactId>
     <version>1.4.1</version>
 </dependency>

         2.2 将shiro主要的类对象交给spring容器,生成自定义Realm实现类Bean。再生成ShiroFilterChainDefinition对象,并配置所要过滤的请求。anon:就是不处理,针对于静态资源和能直接访问的资源;logout:登出路径,它自己有路径并导到指定实现;user:就是需要登陆验证,进入Realm验证。

yml配置:shiro.loginUrl=/login.html


    @Bean
    public Realm shiroRealm() {
        return new ShiroRealm();
    }

    @Bean
    public ShiroFilterChainDefinition shiroFilterChainDefinition(){
        DefaultShiroFilterChainDefinition dsfc = new DefaultShiroFilterChainDefinition();

        //过滤请求
        dsfc.addPathDefinition("/","anon");
        dsfc.addPathDefinition("/login","anon");
        dsfc.addPathDefinition("/css/**","anon");
        dsfc.addPathDefinition("/js/**","anon");
        dsfc.addPathDefinition("/images/**","anon");
        dsfc.addPathDefinition("/fonts/**","anon");
        dsfc.addPathDefinition("/html/**","anon");

        //登出
        dsfc.addPathDefinition("/logout","logout");

        //其他则需要验证
        dsfc.addPathDefinition("/**","user");
        return dsfc;
    }

3.如图可得  主要目标是实现Realm,自己的代码通过调用subject来整体调用。

 4.Realm实现代码(思路:登录认证【验证账号密码】,获取权限【拿着用户id,找角色id,再通过角色id集拿权限】)

        记忆点:两个方法有先后顺序,先认证authc,再授权authz

        String principal = (String) token.getPrincipal();获取用户名

         SimpleAuthenticationInfo simpleAuthentication =

newSimpleAuthenticationInfo(users.get(0),users.get(0).getPwd(),this.getName());进行认证(比对密码,若有加密则看注释代码)。

        获取权限:数据库中通过RBAC实现的表。查找数据,获取对应的值。

        SimpleAuthorizationInfo sim = new SimpleAuthorizationInfo();
        sim.setRoles(rolesnames); //对subject设置角色
        sim.setStringPermissions(new HashSet<>(premits)); //对subject设置权限

        返回sim对象

@Slf4j
public class ShiroRealm extends AuthorizingRealm {

    @Resource
    private UsersMapper usersMpaper;

    @Resource
    private RoleMapper roleMapper;

    @Resource
    private PremitMapper premitMapper;

    @Override
    protected AuthorizationInfo doGetAuthorizationInfo(PrincipalCollection principalCollection) {
        Users user = (Users) principalCollection.getPrimaryPrincipal();
        //获取角色id和角色名称
        List<Role> roles = roleMapper.getRidByUserId(user.getId());
        Set<String> rolesnames = roles.stream().map(v -> v.getRoleName()).collect(Collectors.toSet());
        log.info("rolesnames:{}",rolesnames);
        //获取角色权限
        List<String> premits = premitMapper.getPremitNamesByRoleIds(roles);
        log.info("premits:{}",premits);
        SimpleAuthorizationInfo sim = new SimpleAuthorizationInfo();
        sim.setRoles(rolesnames);
        sim.setStringPermissions(new HashSet<>(premits));
        return sim;
    }

    @Override
    protected AuthenticationInfo doGetAuthenticationInfo(AuthenticationToken token) throws AuthenticationException {
        String principal = (String) token.getPrincipal();

        QueryWrapper<Users> qw = new QueryWrapper<Users>();
        qw.eq("username",principal);
        List<Users> users = usersMpaper.selectList(qw);
        if(users.size()!=0){
            SimpleAuthenticationInfo simpleAuthentication = new SimpleAuthenticationInfo(users.get(0),users.get(0).getPwd(),this.getName());
            //MD5加密,盐
            //new SimpleAuthenticationInfo(username,pwd,ByteSource.Util.bytes(salt),this.getName());
            return simpleAuthentication;
        }
        return null;
    }
}

 查询的sql

SELECT r.id,r.role_name from users u join users_role ur on ur.users_id = u.id join role r on ur.role_id = r.id where u.id=#{userid}
SELECT p.pre_names from role_premit rp join premit p on rp.premit_id = p.id where rp.role_id in
        <foreach collection="roles" item="r" separator="," open="(" close=")">
            #{r.id}
        </foreach>

 整合的总体思路如图

结束。 

评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值