shiro简介以及功能描述
Shiro 是 Java 的一个安全框架。目前,使用 Apache Shiro 的人越来越多,因为它相 当简单,对比 Spring Security,可能没有 Spring Security 做的功能强大,但是在实际工作时 可能并不需要那么复杂的东西,所以使用小而简单的Shiro 就足够了。
官方的简介如下:
Apache Shiro™ is a powerful and easy-to-use Java security framework that performs authentication, authorization, cryptography, and session management. With Shiro’s easy-to-understand API, you can quickly and easily secure any application – from the smallest mobile applications to the largest web and enterprise applications.
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0modelVersion>
<parent>
<groupId>org.springframework.bootgroupId>
<artifactId>spring-boot-starter-parentartifactId>
<version>2.2.6.RELEASEversion>
<relativePath/>
parent>
<groupId>com.zhanggroupId>
<artifactId>shiro-demoartifactId>
<version>0.0.1-SNAPSHOTversion>
<name>shiro-demoname>
<description>Demo project for Spring Bootdescription>
<properties>
<java.version>1.8java.version>
properties>
<dependencies>
<dependency>
<groupId>org.springframework.bootgroupId>
<artifactId>spring-boot-starter-jdbcartifactId>
dependency>
<dependency>
<groupId>org.springframework.bootgroupId>
<artifactId>spring-boot-starter-thymeleafartifactId>
dependency>
<dependency>
<groupId>org.apache.shirogroupId>
<artifactId>shiro-springartifactId>
<version>1.4.0version>
dependency>
<dependency>
<groupId>org.springframework.bootgroupId>
<artifactId>spring-boot-devtoolsartifactId>
<version>2.0.4.RELEASEversion>
<optional>trueoptional>
dependency>
<dependency>
<groupId>org.springframework.bootgroupId>
<artifactId>spring-boot-starter-webartifactId>
dependency>
<dependency>
<groupId>org.mybatis.spring.bootgroupId>
<artifactId>mybatis-spring-boot-starterartifactId>
<version>2.1.2version>
dependency>
<dependency>
<groupId>mysqlgroupId>
<artifactId>mysql-connector-javaartifactId>
<scope>runtimescope>
dependency>
<dependency>
<groupId>org.projectlombokgroupId>
<artifactId>lombokartifactId>
<optional>trueoptional>
dependency>
<dependency>
<groupId>org.springframework.bootgroupId>
<artifactId>spring-boot-starter-testartifactId>
<scope>testscope>
<exclusions>
<exclusion>
<groupId>org.junit.vintagegroupId>
<artifactId>junit-vintage-engineartifactId>
exclusion>
exclusions>
dependency>
dependencies>
<build>
<plugins>
<plugin>
<groupId>org.springframework.bootgroupId>
<artifactId>spring-boot-maven-pluginartifactId>
plugin>
plugins>
build>
project>
spring:
#数据源
datasource:
url: jdbc:mysql://localhost/demo?characterEncoding=UTF-8&serverTimezone=UTC
driver-class-name: com.mysql.cj.jdbc.Driver
username: root
password: 123456
#静态文件路径配置
mvc:
static-path-pattern: /**
resources:
static-locations: classpath:/META-INF/resources/,classpath:/resources/, classpath:/static/,classpath:/public/
#关闭thymeleaf缓存
thymeleaf:
cache: false
#mybatis sql语句日志
mybatis:
configuration:
log-impl: org.apache.ibatis.logging.stdout.StdOutImpl
package com.zhang.pojo;
import lombok.Data;
import lombok.Getter;
import lombok.Setter;
import java.util.List;
/**
* Created with IntelliJ IDEA.
* Auther: Distance
* Date: 2020/04/24/20:07
*/
@Data
@Getter
@Setter
public class User {
public int id;
public String username;
public String password;
private List<Role> roleList;
package com.zhang.pojo;
import lombok.Data;
import lombok.Getter;
import lombok.Setter;
import java.util.List;
/**
* Created with IntelliJ IDEA.
* Auther: Distance
* Date: 2020/04/24/20:08
*/
@Data
@Getter
@Setter
public class Role {
public int id;
public String name;
public String description;
public List<Permission> permissionList;
}
package com.zhang.pojo;
import lombok.Data;
import lombok.Getter;
import lombok.Setter;
/**
* Created with IntelliJ IDEA.
* Auther: Distance
* Date: 2020/04/24/20:10
*/
@Data
@Getter
@Setter
public class Permission {
public int id;
public String name;
public String url;
public String description;
}
package com.zhang.service;
import com.zhang.mapper.RoleMapper;
import com.zhang.mapper.UserMapper;
import com.zhang.pojo.User;
import javax.annotation.Resource;
/**
* Created with IntelliJ IDEA.
* Auther: Distance
* Date: 2020/04/24/21:02
*/
public interface UserService {
//通过username查询用户所有的角色和权限
User findAllUserInfoByUsername(String username);
//通过userId查询用户的基本信息
User findSimpleUserInfoByUserId(Integer userId);
//通过username查询用户的基本信息
User findSimpleUserInfoByUsername(String username);
}
package com.zhang.mapper;
import com.zhang.pojo.Role;
import org.apache.ibatis.annotations.Many;
import org.apache.ibatis.annotations.Result;
import org.apache.ibatis.annotations.Results;
import org.apache.ibatis.annotations.Select;
import org.apache.ibatis.mapping.FetchType;
import java.util.List;
/**
* Created with IntelliJ IDEA.
* Auther: Distance
* Date: 2020/04/24/20:15
*/
public interface RoleMapper {
@Select("select r.id as id,r.name as name,r.description as description " +
"from user_role ur " +
"left join role r on r.id = ur.role_id " +
"where ur.user_id = #{userId}")
@Results(
value = {
@Result(id = true,property = "id",column = "id"),
@Result(property = "name",column = "name"),
@Result(property = "description",column = "description"),
@Result(property = "permissionList",column = "id",
many = @Many(select = "com.zhang.mapper.PermissionMapper.findPermissionListByRoleId",fetchType = FetchType.DEFAULT))
}
)
List<Role> findRoleListByUserId(Integer userId);
}
package com.zhang.mapper;
import com.zhang.pojo.Permission;
import org.apache.ibatis.annotations.Select;
import java.util.List;
/**
* Created with IntelliJ IDEA.
* Auther: Distance
* Date: 2020/04/24/20:15
*/
public interface PermissionMapper {
@Select("select p.id as id,p.name as name,p.url as url,p.description as description " +
"from role_permission rp " +
"left join permission p on p.id = rp.permission_id " +
"where rp.role_id = #{role_id}")
List<Permission> findPermissionListByRoleId(Integer role_id);
}
package com.zhang.shiro;
import com.zhang.pojo.Permission;
import com.zhang.pojo.Role;
import com.zhang.pojo.User;
import com.zhang.service.UserService;
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.ArrayList;
import java.util.List;
/**
* Created with IntelliJ IDEA.
* Auther: Distance
* Date: 2020/04/24/21:26
*/
public class UserRealm extends AuthorizingRealm {
@Resource
public UserService userService;
@Override
protected AuthorizationInfo doGetAuthorizationInfo(PrincipalCollection principalCollection) {
SimpleAuthorizationInfo simpleAuthorizationInfo = new SimpleAuthorizationInfo();
String username = (String) principalCollection.getPrimaryPrincipal();
User user = userService.findAllUserInfoByUsername(username);
List<String> stringRoleList = new ArrayList<>();
List<String> stringPermissionList = new ArrayList<>();
List<Role> roleList = user.getRoleList();
for(Role role:roleList){
stringRoleList.add(role.getName());
List<Permission> permissionList = role.getPermissionList();
for(Permission permission:permissionList){
if (permission!=null){
stringPermissionList.add(permission.getName());
}
}
}
simpleAuthorizationInfo.addRoles(stringPermissionList);
simpleAuthorizationInfo.addStringPermissions(stringPermissionList);
return simpleAuthorizationInfo;
}
@Override
protected AuthenticationInfo doGetAuthenticationInfo(AuthenticationToken authenticationToken) throws AuthenticationException {
UsernamePasswordToken token = (UsernamePasswordToken) authenticationToken;
User user = userService.findSimpleUserInfoByUsername(token.getUsername());
if (user == null){
return null;
}
return new SimpleAuthenticationInfo(user.getUsername(),user.getPassword(),"");
}
}
package com.zhang.shiro;
import org.apache.shiro.spring.web.ShiroFilterFactoryBean;
import org.apache.shiro.web.mgt.DefaultWebSecurityManager;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import java.util.LinkedHashMap;
import java.util.Map;
/**
* Created with IntelliJ IDEA.
* Auther: Distance
* Date: 2020/04/24/21:26
*/
@Configuration
public class ShiroConfig {
@Bean
public ShiroFilterFactoryBean getShiroFilterFactoryBean(@Qualifier("securityManager") DefaultWebSecurityManager securityManager){
ShiroFilterFactoryBean shiroFilterFactoryBean = new ShiroFilterFactoryBean();
shiroFilterFactoryBean.setSecurityManager(securityManager);
Map<String,String> fileterMap = new LinkedHashMap<>();
fileterMap.put("login","anon");
fileterMap.put("/demo","authc");
fileterMap.put("/operate/add","perms[add]");
fileterMap.put("/operate/update","perms[update]");
fileterMap.put("/operate/select","perms[select]");
fileterMap.put("/operate/delete","perms[delete]");
shiroFilterFactoryBean.setLoginUrl("/toLogin");
shiroFilterFactoryBean.setUnauthorizedUrl("no_per");
shiroFilterFactoryBean.setFilterChainDefinitionMap(fileterMap);
return shiroFilterFactoryBean;
}
@Bean(name = "securityManager")
public DefaultWebSecurityManager getSecurityManager(@Qualifier("userRealm")UserRealm userRealm){
DefaultWebSecurityManager securityManager = new DefaultWebSecurityManager();
securityManager.setRealm(userRealm);
return securityManager;
}
@Bean(name = "userRealm")
public UserRealm getUserRealm(){
return new UserRealm();
}
}
账号:admin
密码:123456
角色:root(超级管理员)
权限:add update delete select
账号:lisi
密码:123456
角色:customer(普通用户)
权限:add select