一、与SpringBoot整合
①:框架整合
1. 创建SpringBoot项目
环境:
- jdk: 1.8
- SpringBoot: 2.5.14
2. 整合MyBatis根据实体类生成表
可查看文章:https://juejin.cn/post/7234324615015776315
按照以上笔记配置后在补充一下代码
- 依赖MyBatisPlus依赖
<!--mybatis-plus-->
<dependency>
<groupId>com.baomidou</groupId>
<artifactId>mybatis-plus-boot-starter</artifactId>
<version>3.0.5</version>
</dependency>
<dependency>
<groupId>org.apache.shiro</groupId>
<artifactId>shiro-spring-boot-web-starter</artifactId>
<version>1.9.0</version>
</dependency>
- 配置文件
mybatis-plus:
configuration:
log-impl: org.apache.ibatis.logging.stdout.StdOutImpl
mapper-locations: classpath:mapper/*.xml
spring:
datasource:
url: jdbc:mysql://您的IP地址:3306/shirodb?characterEncoding=UTF-8&serverTimezone=Asia/Shanghai
username: root
password: www.Coke.com
driver-class-name: com.mysql.cj.jdbc.Driver
jackson:
date-format: yyyy-MM-dd HH:mm:ss
time-zone: GMT+8
servlet:
multipart:
max-file-size: 20MB
max-request-size: 20MB
shiro:
loginUrl: /myController/login
registerUrl: /myController/register
- 注意以下位置改成自己的路径
- 启动类
@SpringBootApplication
@MapperScan("com.it.shiro_springboot.mapper")
public class Application {
public static void main (String[] args) {
SpringApplication.run(Application.class, args);
}
}
②:登录认证实现
1.创建实体
@Data
@NoArgsConstructor
@AllArgsConstructor
public class User {
private Integer id;
private String name;
private String pwd;
private Integer rid;
}
2.创建mapper
@Mapper
public interface UserMapper extends BaseMapper<User> {
@Select("select * from user where name = #{name}")
User getUserInfoByName(String name);
@Insert("insert into user(name, pwd) values(#{name},#{pwd}) ")
int userRegister(@Param("name") String name, @Param("pwd") String pwd);
}
@Data
@NoArgsConstructor
@AllArgsConstructor
@Table (name = "user", comment = "用户表") //设置表名 注释
public class User implements Serializable {
private static final long serialVersionUID = 9435278593475930L;
@IsAutoIncrement //自增
@IsKey //主键
@Column (comment = "用户ID")//字段注释
private Integer id;
/**
* 姓名
*/
@Column(name = "name", comment = "用户名", length = 100)
private String name;
/**
* 密码
*/
@Column(name = "pwd", comment = "密码", length = 100)
private String pwd;
/**
* 角色编号
*/
@Column(name = "rid", comment = "角色编号", length = 100)
private Integer rid;
}
3.创建 service
1.创建接口
public interface UserService {
// 用户登录
User getUserInfoByName (String name);
// 用户注册
int userRegister(String name, String pwd);
}
2.创建实现类
@Service
public class UserServiceImpl implements UserService {
@Autowired
private UserMapper userMapper;
@Override
public User getUserInfoByName (String name) {
User user = userMapper.getUserInfoByName(name);
return user;
}
@Override
public int userRegister (String name, String pwd) {
// md5加密
SimpleHash simpleHash = new SimpleHash("MD5", pwd, "salt", 3);
return userMapper.userRegister(name, simpleHash.toHex());
}
}
4.自定义realm
@Component
public class MyRealm extends AuthorizingRealm {
@Autowired
private UserService userService;
// 自定义授权方法
@Override
protected AuthorizationInfo doGetAuthorizationInfo (PrincipalCollection principalCollection) {
return null;
}
// 自定义登录认证方法
@Override
protected AuthenticationInfo doGetAuthenticationInfo (AuthenticationToken token) throws AuthenticationException {
// 1.获取用户身份信息
String name = token.getPrincipal().toString();
// 2. 调用业务层获取用户信息(数据库中)
User user = userService.getUserInfoByName(name);
// 判断并将数据完成封装
if (!ObjectUtils.isEmpty(user)) {
SimpleAuthenticationInfo authInfo = new SimpleAuthenticationInfo(
token.getPrincipal(),
user.getPwd(),
ByteSource.Util.bytes("salt"),
token.getPrincipal().toString()
);
return authInfo;
}
return null;
}
}
5.编写配置类
@Configuration
public class ShiroConfig {
@Autowired
private MyRealm myRealm;
@Value("${shiro.loginUrl}")
private String loginUrl;
@Value("${shiro.registerUrl}")
private String registerUrl;
// SecurityManager
@Bean
public DefaultWebSecurityManager defaultWebSecurityManager(){
// 1.创建 defaultWebSecurityManager 对象
DefaultWebSecurityManager manager = new DefaultWebSecurityManager();
// 2. 创建加密对象,并设置相关属性
HashedCredentialsMatcher matcher = new HashedCredentialsMatcher();
// 3.采用 md5 加密
matcher.setHashAlgorithmName("md5");
// 4.迭代加密次数
matcher.setHashIterations(3);
// 5. 将加密对象存储到 myRealm 中
myRealm.setCredentialsMatcher(matcher);
// 6. 将 myRealm 存入 defaultWebSecurityManager 对象
manager.setRealm(myRealm);
// 7. 返回
return manager;
}
// 配置 Shiro 内置过滤器拦截范围
@Bean
public DefaultShiroFilterChainDefinition shiroFilterChainDefinition(){
DefaultShiroFilterChainDefinition definition = new DefaultShiroFilterChainDefinition();
// 设置不认证可以访问的资源
definition.addPathDefinition(loginUrl, "anon");
definition.addPathDefinition(registerUrl, "anon");
definition.addPathDefinition("/login", "anon");
// 设置需要进行登录认证的拦截范围
definition.addPathDefinition("/**","authc");
return definition;
}
}
6.实现controller
@Controller
@Slf4j
@RequestMapping("myController")
public class MyController {
@Autowired
private UserService userService;
@GetMapping("login")
@ResponseBody
public String userLogin(String name, String pwd){
// 1 获取 Subject 对象
Subject subject = SecurityUtils.getSubject();
// 2 封装请求数据到 token 对象中
UsernamePasswordToken token = new UsernamePasswordToken(name, pwd);
//3 调用 login 方法进行登录认证
try {
subject.login(token);
return "登录成功!";
}catch (AuthenticationException e){
e.printStackTrace();
log.info("登录失败");
return "登录失败!";
}
}
@GetMapping("register")
@ResponseBody
public String register(String name, String pwd){
int i = userService.userRegister(name, pwd);
if (i > 0){
return "注册成功!";
}else {
return "注册失败!";
}
}
}
7.测试
1.启动程序前数据库中并没有表
2.启动程序(表即可创建成功)
3.注册用户
4.登录