1.引入依赖
<!-- shiro -->
<dependency>
<groupId>org.apache.shiro</groupId>
<artifactId>shiro-spring</artifactId>
<version>1.4.1</version>
</dependency>
2.创建自定义realm类继承AuthorizingRealm
public class CustomRealm extends AuthorizingRealm {
//模拟数据库中账 户名 -> 密码
private final Map<String , String> userInfoMap = new HashMap<>();
{
userInfoMap.put("jack", "123");
userInfoMap.put("baixun", "123");
}
//模拟数据库中 用户 -> 权限
private final Map<String , Set<String>> permissionMap = new HashMap<>();
{
Set<String> set1 = new HashSet<>();
Set<String> set2 = new HashSet<>();
set1.add("video:find");
set1.add("video:buy");
set2.add("video:add");
set2.add("video:delete");
permissionMap.put("jack", set1);
permissionMap.put("baixun", set2);
}
//模拟数据库中 用户 -> 角色
private final Map<String , Set<String>> roleMap = new HashMap<>();
{
Set<String> set1 = new HashSet<>();
Set<String> set2 = new HashSet<>();
set1.add("role1");
set1.add("role2");
set2.add("root");
roleMap.put("jack", set1);
roleMap.put("baixun", set2);
}
//*****************************上面为模拟数据库******************************
/**
* 当进行权限校验时会调用
*/
@Override
protected AuthorizationInfo doGetAuthorizationInfo(PrincipalCollection principals) {
System.out.println("CustomRealm doGetAuthorizationInfo() 授权...");
SimpleAuthorizationInfo simpleAuthorizationInfo = new SimpleAuthorizationInfo();
//获取name
String name = (String)principals.getPrimaryPrincipal();
System.out.println("name="+name);
//从数据库中获取权限
Set<String> permissions = getPermissionsByNameFromDB(name);
System.out.println("permissions="+permissions);
//从数据库中获取角色
Set<String> roles = getRolesByNameFromDB(name);
System.out.println("roles="+roles);
simpleAuthorizationInfo.setRoles(roles);
simpleAuthorizationInfo.setStringPermissions(permissions);
return simpleAuthorizationInfo;
}
/**
* 用户登录时会调用
*/
@Override
protected AuthenticationInfo doGetAuthenticationInfo(AuthenticationToken token) throws AuthenticationException {
System.out.println("CustomRealm doGetAuthenticationInfo() 认证...");
//从token中获取身份信息
String name = (String)token.getPrincipal();
//从数据库中获取密码
String pwd = getPwdByUsernameFromDb(name);
if(pwd == null || "".equals(pwd)){
return null;
}
return new SimpleAuthenticationInfo(name, pwd, this.getName());
}
//*****************************下面为私有方法*******************************
private String getPwdByUsernameFromDb(String name) {
return userInfoMap.get(name);
}
private Set<String> getRolesByNameFromDB(String name) {
return roleMap.get(name);
}
private Set<String> getPermissionsByNameFromDB(String name) {
return permissionMap.get(name);
}
}
3.创建ShiroConfig类
@Configuration
public class ShiroConfig {
/**
* 创建ShiroFilterFactoryBean
*/
@Bean
public ShiroFilterFactoryBean getShiroFilterFactoryBean(@Qualifier("securityManager") DefaultWebSecurityManager securityManager){
ShiroFilterFactoryBean shiroFilterFactoryBean = new ShiroFilterFactoryBean();
//关联securityManager
shiroFilterFactoryBean.setSecurityManager(securityManager);
/**
* authc: 必须认证才可以访问
* anon: 无需认证(登录)可以访问
* perms: 该资源必须得到资源权限才可以访问
*/
//添加shiro内置过滤器
Map<String,String> filterMap = new LinkedHashMap<String, String>();
filterMap.put("/*","authc");
shiroFilterFactoryBean.setFilterChainDefinitionMap(filterMap);
//设置登陆页面
shiroFilterFactoryBean.setLoginUrl("/toLogin");
//设置未授权展示页面
shiroFilterFactoryBean.setUnauthorizedUrl("/noAuth");
return shiroFilterFactoryBean;
}
/**
* 创建DefaultWebSecurityManager
*/
@Bean(name = "securityManager")
public DefaultWebSecurityManager getDefaultWebSecurityManager(@Qualifier("userRealm") UserRealm userRealm){
DefaultWebSecurityManager securityManager = new DefaultWebSecurityManager();
//关联realm
securityManager.setRealm(userRealm);
return securityManager;
}
/**
* 创建Realm
*/
@Bean(name = "userRealm")
public UserRealm getRealm(){
return new UserRealm();
}
/**
* 配置ShiroDialect,用于thymeleaf和shiro标签配合使用
*/
@Bean
public ShiroDialect getShiroDialect(){
return new ShiroDialect();
}
}
4.测试
@RestController
public class UserController {
@Autowired
private IUserService userService;
//测试shiro
@RequestMapping(value = "test/login", method = RequestMethod.POST)
public String login(String username, String password){
Subject subject = SecurityUtils.getSubject();
UsernamePasswordToken token = new UsernamePasswordToken(username, password);
// 执行登录方法
// 无异常则判断为登录成功
try{
subject.login(token);
}catch (UnknownAccountException e){
return "用户名错误";
}catch (IncorrectCredentialsException e){
return "密码错误";
}
return "sucess...";
}
//测试shiro-未登陆页面
@GetMapping("/toLogin")
public String toLog(){
return "登陆页面";
}
//测试shiro-未授权页面
@GetMapping("/noAuth")
public String noAuth(){
return "没有权限访问";
}
}