Shiro学习2----spring boot整合(自定义Realm)

1.数据库设计

#用户信息表
create table tb_users(
	id int primary key auto_increment,
	username varchar(60) not null,
	password varchar(20) not null,
	password_salt varchar(60)
);
insert into tb_users(username,password) values("zhagnsan","123456");
insert into tb_users(username,password) values("lisi","123456");
insert into tb_users(username,password) values("wangwu","123456");
insert into tb_users(username,password) values("zhaoliu","123456");
insert into tb_users(username,password) values("chenqi","123456");
#角色信息表
create table tb_roles(
	role_id int primary key auto_increment,
	role_name varchar(60) not null
);
insert into tb_roles(role_name) values("admin");
insert into tb_roles(role_name) values("cmanager");
insert into tb_roles(role_name) values("xmanager");
insert into tb_roles(role_name) values("kmanager");
insert into tb_roles(role_name) values("zmanager");
#权限信息表
create table tb_permissions(
	permission_id int primary key auto_increment,
	permission_code varchar(60) not null,
	permission_name varchar(60)
);
insert into tb_permissions(permission_code,permission_name) values("sys:c:save","入库");
insert into tb_permissions(permission_code,permission_name) values("sys:c:delete","入库");
insert into tb_permissions(permission_code,permission_name) values("sys:c:update","修改");
insert into tb_permissions(permission_code,permission_name) values("sys:c:find","查询");

insert into tb_permissions(permission_code,permission_name) values("sys:x:save","新增订单");
insert into tb_permissions(permission_code,permission_name) values("sys:x:delete","删除订单");
insert into tb_permissions(permission_code,permission_name) values("sys:x:update","修改订单");
insert into tb_permissions(permission_code,permission_name) values("sys:x:find","查询订单");

insert into tb_permissions(permission_code,permission_name) values("sys:k:save","新增客户");
insert into tb_permissions(permission_code,permission_name) values("sys:k:delete","删除客户");
insert into tb_permissions(permission_code,permission_name) values("sys:k:update","修改客户");
insert into tb_permissions(permission_code,permission_name) values("sys:k:find","查询客户");
#用户角色表
create table tb_urs(
	uid int not null,
	rid int not null
);
insert into tb_urs(uid,rid) values(1,1);
insert into tb_urs(uid,rid) values(1,2);
insert into tb_urs(uid,rid) values(1,3);
insert into tb_urs(uid,rid) values(1,4);
insert into tb_urs(uid,rid) values(1,5);
insert into tb_urs(uid,rid) values(2,2);
insert into tb_urs(uid,rid) values(3,3);
insert into tb_urs(uid,rid) values(4,4);
insert into tb_urs(uid,rid) values(5,5);
#角色权限表
create table tb_rps(
	rid int not null,
	pid int not null
);
insert into tb_rps(rid,pid) values(2,1);
insert into tb_rps(rid,pid) values(2,2);
insert into tb_rps(rid,pid) values(2,3);
insert into tb_rps(rid,pid) values(2,4);

insert into tb_rps(rid,pid) values(3,5);
insert into tb_rps(rid,pid) values(3,4);
insert into tb_rps(rid,pid) values(3,6);
insert into tb_rps(rid,pid) values(3,7);
insert into tb_rps(rid,pid) values(3,8);
insert into tb_rps(rid,pid) values(3,9);
insert into tb_rps(rid,pid) values(3,10);
insert into tb_rps(rid,pid) values(3,11);
insert into tb_rps(rid,pid) values(3,12);

insert into tb_rps(rid,pid) values(4,11);
insert into tb_rps(rid,pid) values(4,12);

insert into tb_rps(rid,pid) values(5,4);
insert into tb_rps(rid,pid) values(5,8);
insert into tb_rps(rid,pid) values(5,12);

2.DAO实现

  • 根据用户名查询用户信息
  • 根据用户名查询当前用户的角色列表
  • 根据用户名查询当前用户的权限列表

2.1创建spring boot项目整合mybatis

2.2创建bean

@Data
public class User {
    private Integer userId;
    private String userName;
    private String userPwd;
    private String pwdSalt;
}

2.3创建DAO 

public interface UserDao {
    public User queryUserByUsername(String username);
}
public interface RoleDao {
    public Set<String> queryRoleNamesByUsername(String username);
}
public interface PermissionDao {
    public Set<String> queryPermissionsByUsername(String username);
}
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
        "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="com.qfedu.shiro4.dao.UserDao">
    <resultMap id="userMap" type="User">
        <id column="user_id" property="userId"></id>
        <result column="username" property="userName"/>
        <result column="password" property="userPwd"/>
        <result column="password_salt" property="pwdSalt"/>
    </resultMap>

    <select id="queryUserByUsername" resultMap="userMap">
        SELECT * FROM tb_users WHERE username=#{username}
    </select>
</mapper>

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
        "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="com.qfedu.shiro4.dao.RoleDao">

    <select id="queryRoleNamesByUsername" resultSets="java.util.Set" resultType="string">
        select role_name from tb_users inner join tb_urs
        on tb_users.id=tb_urs.uid inner join tb_roles
        on tb_urs.rid=tb_roles.role_id
        where tb_users.username=#{username}
    </select>
</mapper>

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
        "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="com.qfedu.shiro4.dao.PermissionDao">

    <select id="queryPermissionsByUsername" resultSets="java.util.Set" resultType="string">
        select tb_permissions.permission_code from tb_users
        inner join tb_urs on tb_users.id=tb_urs.uid
        inner join tb_roles on tb_urs.rid=tb_roles.role_id
        inner join tb_rps on tb_roles.role_id=tb_rps.rid
        inner join tb_permissions on tb_rps.pid=tb_permissions.permission_id
        where tb_users.username=#{username}
    </select>
</mapper>

2.4配置shiro

package com.qfedu.shiro4.config;

import at.pollux.thymeleaf.shiro.dialect.ShiroDialect;
import org.apache.shiro.authc.credential.HashedCredentialsMatcher;
import org.apache.shiro.spring.web.ShiroFilterFactoryBean;
import org.apache.shiro.web.mgt.DefaultWebSecurityManager;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import java.util.HashMap;
import java.util.Map;

@Configuration
public class ShiroConfig {
    //shiro方言
    @Bean
    public ShiroDialect getShiroDialect(){
        return new ShiroDialect();
    }
    @Bean
    public HashedCredentialsMatcher getHashedCredentialsMatcher(){
        HashedCredentialsMatcher matcher = new HashedCredentialsMatcher();
        //matcher就是用来指定加密规则
        //加密方式
        matcher.setHashAlgorithmName("md5");
        //hash次数
        matcher.setHashIterations(1);
        return matcher;
    }
    @Bean
    public MyRealm getMyRealm(HashedCredentialsMatcher matcher){
        MyRealm myRealm=new MyRealm();
        myRealm.setCredentialsMatcher(matcher);
        return myRealm;
    }
    @Bean
    public DefaultWebSecurityManager getDefaultWebSecurityManager(MyRealm myRealm){
        DefaultWebSecurityManager securityManager = new DefaultWebSecurityManager();
        securityManager.setRealm(myRealm);
        return securityManager;
    }
    @Bean
    public ShiroFilterFactoryBean shiroFilter(DefaultWebSecurityManager securityManager){
        ShiroFilterFactoryBean filter = new ShiroFilterFactoryBean();
        //过滤器就是shiro进行权限校验的核心,进行认证和授权是需要SecurityManager的
        filter.setSecurityManager(securityManager);

        /*设置shiro的拦截规则
        anon    匿名用户可访问
        authc   认证用户可访问
        user    使用RemeberMe的用户可访问
        perms   对应权限可访问
        role    对应角色可访问
         */
        Map<String,String> filterMap=new HashMap<>();
        filterMap.put("/", "anon");
        filterMap.put("/login.html", "anon");
        filterMap.put("/regist.html", "anon");
        filterMap.put("/user/login", "anon");
        filterMap.put("user/regist", "anon");
        filterMap.put("/static/**", "anon");
        filterMap.put("/**", "authc");

        filter.setFilterChainDefinitionMap(filterMap);
        filter.setLoginUrl("/login.html");
        //设置未授权访问的页面路径
        filter.setUnauthorizedUrl("/login.html");
        return filter;
    }
}

自定义Realm

package com.qfedu.shiro4.config;

import com.qfedu.shiro4.beans.User;
import com.qfedu.shiro4.dao.PermissionDao;
import com.qfedu.shiro4.dao.RoleDao;
import com.qfedu.shiro4.dao.UserDao;
import org.apache.shiro.authc.*;
import org.apache.shiro.authz.AuthorizationInfo;
import org.apache.shiro.authz.SimpleAuthorizationInfo;
import org.apache.shiro.realm.AuthorizingRealm;
import org.apache.shiro.subject.PrincipalCollection;

import javax.annotation.Resource;
import java.util.Set;

/**
 * 1.创建一个类继承AuthorizingRealm类(实现了Realm接口的类)
 * 2.重写doGetAuthorizationInfo和doGetAuthenticationInfo方法
 * 3.重写getName方法
 */
public class MyRealm extends AuthorizingRealm {
    @Resource
    private UserDao userDao;
    @Resource
    private RoleDao roleDao;
    @Resource
    private PermissionDao permissionDao;
    @Override
    public String getName(){
        return "myRealm";
    }
    /*获取授权数据*/
    @Override
    protected AuthorizationInfo doGetAuthorizationInfo(PrincipalCollection principalCollection) {
        String username = (String) principalCollection.iterator().next();
        Set<String> roleNames = roleDao.queryRoleNamesByUsername(username);
        Set<String> ps = permissionDao.queryPermissionsByUsername(username);
        SimpleAuthorizationInfo info = new SimpleAuthorizationInfo();
        info.setRoles(roleNames);
        info.setStringPermissions(ps);
        return info;
    }
    /*获取认证数据*/
    @Override
    protected AuthenticationInfo doGetAuthenticationInfo(AuthenticationToken authenticationToken) throws AuthenticationException {
        //参数authenticationToken就是传递的 subject.login(token)
        UsernamePasswordToken token=(UsernamePasswordToken)authenticationToken;
        String username = token.getUsername();
        User user = userDao.queryUserByUsername(username);

//        AuthenticationInfo info=new SimpleAuthenticationInfo(
//                username,
//                user.getUserPwd(),
//                getName()
//        );
        //如果数据库中用户密码是加了盐的
        AuthenticationInfo info=new SimpleAuthenticationInfo(
                username,
                user.getUserPwd(),
                ByteSource.Util.bytes(user.getPwdSalt()),
                getName()
        );
        return info;
    }
}

加密处理

    @RequestMapping("/regist")
    public String regist(String username,String userPwd){
        //注册时对密码加密处理
        Md5Hash md5Hash = new Md5Hash(userPwd);
        System.out.println(md5Hash.toHex());
        //加盐加密
        int salt=new Random().nextInt(9999);
        Md5Hash md5Hash1 = new Md5Hash(userPwd,salt+"");
        //加盐加密加多次hash
        Md5Hash md5Hash2 = new Md5Hash(userPwd,salt+"",3);

        SimpleHash hash = new SimpleHash("md5", userPwd, salt, 3);
        return "login";
    }

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

mymk01

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值