【转】一个关于用AOP实现权限控制的问题,不知道大家怎么想?

遇到一个权限验证的问题。就是说,对于任何一个操作,需要判断这个人对于这份资源是否有权进行这项操作。这是一个典型的AOP场景,但是试图横切的时候遇到了困难。

“权限验证”这个aspect需要三项信息:操作者(userId)、被操作对象(departmentId、resourceFamilyId……)、操作(组件名+方法名)。“操作”的信息是可以在aspect中直接获得的;“操作者”的信息无法直接获得,但也可以在web层先用filter做一次拦截,将 userId放进ThreadLocal,然后在aspect中取出。最麻烦的就是“被操作对象”的信息。譬如“删除部门”操作,被操作对象就是部门的 ID;“修改portlet”操作,被操作对象就是portlet的注册ID。对于各种各样不同的service方法,如何在aspect中拦截出被操作对象的信息?

一种办法是约定将被操作对象ID放在参数列表的特定位置,譬如每个service方法的第一个参数就是被操作对象的ID,然后aspect始终到这个位置去拿到这个ID,判断是否有权限进行此操作。但这就等于给service方法加上了另一层约束,而且这种约束还无法在类型系统中体现出来,一则容易犯错(譬如忘了这个约定,把ID放到第二个参数了),二则多个aspect的约定还有可能冲突或者混淆。

有没有办法清晰地描述这种“aspect对组件的约束”?或者还有没有更好的办法?要不然,还真是不太敢多用AOP。

aspectj和jboss aop都对切入点提供了精细的控制,相对于spring aop.你可以考虑它们是否适合你的需求。不过如果你“不敢”使用aop,你用传统的oo设计难道就可以做的更好吗?事实上我觉的应该是aop+oo,而不是分开来说

建议你先全面了解一下ACL技术,下面这套源码是使用基于容器实现的ACL,当然如果使用JBoss 4.0容器,那么JBoss 4.0底层是使用AOP实现的。看看这个应用也许对你的思路整理有些帮助。
http://www.jdon.com/jdonframework/news.htm

spring中,实现org.springframework.oap.MethodBeforeAdvice的before方法后,在xml文件可以配置实现aop的。


雨魂--qq19563120