springAOP与自定义注解实现细粒度权限控制管理
IOC与AOP无疑是spring的核心,提供了非常强大的功能,这两个思想为我们开发带来了巨大的方便。
这里我们aop简单实现一些权限控制,用到的aop提供的环绕通知,至于spring提供了那些通知,大家可以自行百度。
<bean id="privilegeAspect" class="com.privilege.PrivilegeAspect"></bean> <aop:config> <!-- 切入点表达式,确认目标类 com.service.impl包中的所有类中的所有方法 --> <aop:pointcut expression="execution(* com.service.impl.*.*(..))" id="perform"/> <!-- ref指向的对象就是切面 --> <aop:aspect ref="privilegeAspect"> <!-- 环绕通知 --> <aop:around method="isAccessMethod" pointcut-ref="perform"/> </aop:aspect> </aop:config>
可以直接这样配环绕通知,然后自行实现具体类的具体方法。
我这里使用spring提供的一个接口,已经帮我们实现好了,只需要配置好,实现他就可以了,可以更好的使用一些方便的方法
<bean id="privilegeInterceptor" class="com.interceptor.PrivilegeInterceptor"></bean> <bean class="org.springframework.aop.framework.autoproxy.BeanNameAutoProxyCreator"> <property name="beanNames"> <list> <value>*Service</value> </list> </property> <property name="interceptorNames"> <list> <value><span style="font-family: Arial, Helvetica, sans-serif;">privilegeInterceptor</span></value> </list> </property> </bean>这里的意思拦截所有service类里的方法,然后执行interceptorNames的拦截器,可以配置多个拦截器,按顺序执行
package com.interceptor; import java.lang.reflect.Method; import java.util.List; import java.util.Map; import javax.servlet.http.HttpServletRequest; import org.aopalliance.intercept.MethodInterceptor; import org.aopalliance.intercept.MethodInvocation; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.core.annotation.AnnotationUtils; import org.springframework.web.servlet.ModelAndView; import org.springframework.web.servlet.View; /** * @author landong.sun * */ public class PrivilegeInterceptor implements MethodInterceptor{ @Autowired SessionProvider sessionProvider; @Override public Object invoke(MethodInvocation invocation) throws Throwable { Method method = invocation.getMethod();//获取被拦截的方法 Object[] arguments = invocation.getArguments();//获取拦截方法的参数 PrivilegeInfo privilegeInfo = AnnotationUtils.findAnnotation(method, PrivilegeInfo.class);//根据方法找到注解,这个注解是我们自定义的注解,下面会讲 if(privilegeInfo!=null) { String value = (String) AnnotationUtils.getAnnotationAttributes(privilegeInfo).get("value");//获取权限值 boolean isAccessed = false; MenuCondition isPrivilege = new MenuCondition();//这是一个权限类 //从session中获取权限 for (MenuCondition privilege : privileges) { /* * 如果目标方法没有使用PrivilegeInfo注解,则解析出来的权限字符串就为空字符串 * 则默认用户拥有这个权限 */ if ("".equals(methodAccess)) { isAccessed = true; break; } /* * 用户原有权限列表中有的权限与目标方法上PrivilegeInfo注解配置的权限进行匹配 */ String truePrivikey = privilege.getlPrivyKey()+""; if (truePrivikey!= null && StringUtils.equalsIgnoreCase(methodAccess, truePrivikey)) { isAccessed = true; isPrivilege = privilege; break; } } /* * 3.如果用户拥有权限,则调用目标方法 ,如果没有,则不调用目标方法,只给出提示 */ if (isAccessed) { /* * 特殊,某些权限需要做特殊处理 * 比如用户信息权限,在方法执行完毕返回的时候,要将电话号码与邮箱抹除 */ //环绕通知前置特殊处理 this.beforeReslove(); Object proceed = invocation.proceed();//调用目标方法 //环绕通知后置特殊处理 proceed = this.afterReslove(); return proceed; } else{ ResultUtils.throwExcepion(ResultUtils.createFail(Config.FBD_MESSAGE, 301, null)); } return null; } }
自定义注解
@Target(ElementType.METHOD) @Retention(RetentionPolicy.RUNTIME) public @interface PrivilegeInfo { String value() default ""; }
写得有点快,有点粗糙,希望大家多提意见
声明:该文观点仅代表作者本人,牛骨文系教育信息发布平台,牛骨文仅提供信息存储空间服务。
- 上一篇: 《玩转细粒度权限管理》 三,用户角色权限RBCA
- 下一篇: 权限控制案例(细粒度)