基于shiro自定义aop+注解实现自己想要的权限管理

前提:已经集成shiro的环境下,shiro自带的权限不足以满足需求,所以想到的这个办法。

目的:判断当前操作用户是否有权限处理这个操作,大概意思就是加入部门概念,判断该用户是否越部门去处理其他部门的数据了

第一步我们先自定义一个aop接口,放在cn.zyx.test.base.shiro.annotion包下。

/**
 * 权限注解 用于检查权限 规定访问权限
 * 主要用于只能操作自身数据范围内数据
 * 总管理员可以通过该权限
 * @example @BasicPermission
 */
@Retention(RetentionPolicy.RUNTIME)    //始终不会丢弃,运行期也保留该注解
@Target({ElementType.METHOD})          //标注方法注解
public @interface BasicPermission {

    /**
     * 需要一个标识,去确认去哪里验证是不是该登陆用户的数据范围
     */
    String key() default "";
	
}

 我们写完了之后首先哪去controller层做个简单的测试,看看@注解是否出现

    /**
     * 冻结课程
     *
     * @author zyx
     * @Date 2019年7月2日15点49分
     * 关于权限这里,只能是超级管理员/是该课程所属的门店的管理员,才能冻结或者解冻课程
     */
    @RequestMapping("/freeze")
    @BasicPermission(key="course")
    @ResponseBody
    public ResponseData freeze(@RequestParam Integer courseId) {
        if (ToolUtil.isEmpty(courseId)) {
            throw new ServiceException(BizExceptionEnum.REQUEST_NULL);
        }
 
        this.courseService.setCourseState(courseId, BasicSysState.FREEZED.getCode());
        
        return SUCCESS_TIP;
    }

 然后去实现aop切面类:

/**
 * 权限检查的aop
 *
 * @author zyx
 * @date 2019年7月2日15点52分
 */
@Aspect
@Component
@Order(200)
public class BasicPermissionAop {

    @Autowired
    private PermissionCheckService check;

    //这里annotation里放的就是上面注解所在的位置,我们要切入该注解里
    @Pointcut(value = "@annotation(cn.zyx.test.base.shiro.annotion.BasicPermission)")
    private void cutPermission() {

    }

    @Around("cutPermission()")
    public Object doPermission(ProceedingJoinPoint point) throws Throwable {
		MethodSignature ms = (MethodSignature) point.getSignature();
		Method method = ms.getMethod();
		BasicPermission BasicPermission = method.getAnnotation(BasicPermission.class);
		String aopValue = point.getArgs()[0].toString();//获取请求参数id
		String aopKey = BasicPermission.key();//获取注解里写的key
       
        //如果当前用户是管理员,则不需要去范围权限进行检查
        if(!ShiroKit.isAdmin()) {
        	//范围权限检查
            boolean result = check.checkDataScope(aopKey,aopValue);
            if (result) {
                return point.proceed();
            } else {
                throw new NoPermissionException();
            }     
        }    
        return point.proceed();
  
    }

}

到这里为止,整个流程就实现完成了,后面贴一下我详细权限检查过程,方便以后自己查看。

/**
 * 检查用接口
 */
public interface PermissionCheckService {
    
    /**
     * 检查当前登陆用户是否操作的是他所在的数据
     */
    
    boolean checkDataScope(String key,String value);
}
/**
 * 权限自定义检查
 */
@Service
@Transactional(readOnly = true)
public class PermissionCheckServiceServiceImpl implements PermissionCheckService {

	@Override
	public boolean checkDataScope(String key,String value) {
		//获取当前登陆人的部门所对应的商店/部门
		Shop shop = ShiroKit.getDeptShopDataScope();
		//根据前端传参的key与value,获取对应的shopId,如果没有,会返回-1
		Integer keyId = -1;
        /**
		 * 暂时怎么写,等以后攒多了if判断语句,统一改成策略模式
		 */
           
        //BasicPermissionConstant.COURSE="course",写在另外一个静态常量类里
		if(BasicPermissionConstant.COURSE.equals(key)) {
			Course course = new Course();
			course.setId(Integer.valueOf(value));
			course = courseMapper.selectOne(new QueryWrapper<Course>(course));
			if(ToolUtil.isNotEmpty(course) && ToolUtil.isNotEmpty(course.getShopId())) {
				keyId = course.getShopId();
			}
		}
		if(keyId.equals(shop.getId())) {
			return true;
		}
		return false;
	}

}

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值