红色部分是个人心得
最近做的一个项目中对权限要求比较高,对系统每个模块的不同操作(CRUD)分别设置权限,当然用户还有角色,多对多的关系,默认用户继承所拥有的角色(按优先级从高到低)的权限,也可以对用户单独授权,整体采用RBAC模型,ACL的主体可以为角色也可以为用户,做完授权后,下一步的问题时:如何及时认证呢?三个参数(用户ID, 资源ID, 操作permission) ,因为UI层使用Struts,用户登陆后可以在request中获取session,进而获取用户ID,资源ID可以从request的servletPath中URL查出,剩下的就是操作了,这是最关键的一点。
系统的命名规范是(C)--->add... / (R)--->find/ (U)--->modify... / (D)--->del.. 针对每个模块编写一个Action继承BaseAction,BaseAction继承DispatchAction,
在你要拦截的DispatchAction中重写execute()方法,否则拦截不到,重写的方法我会在下面贴出来.完成用户登陆验证后交由DispatchAction根据parameter执行任务分发,说到这里就会想到用Spring的AOP来对所有的Action进行拦截,然后定义pointcut为这些Action的add..或 del...开头的方法,在根据pointcut定义不同的adviser,对应的adviser中规定好对应的permission(第三个参数),在结合从JoinPoint中获取的request,得到前两个参数完成及时认证。想法不错,然而做起来的时候,却不是那么回事,因为所有的Action都是DispatchAction,所有的方法(非execute())均为反射调用,所以根本拦截不到其他的跟业务逻辑相关的add..或 del...开头的方法,所以,现在的问题是:如何用AOP对DispatchAction中的不同方法进行拦截?
分析Struts的执行过程和DispatchAction的原理就知道,拦截DispatchAction的execute()方法,在adviser中做DispatchAction中的一些类似的处理,比如获取parameter和methodName,得到了methodName,不就可以设置permission了吗!
核心的代码贴出来,Aspect如下:
AuthImpl.java
package com.bluesun.oa.manager.impl;
/* import ... */
public class AuthImpl implements Auth {
private ACLManager aclManager;
public void authPermission(JoinPoint joinPoint) {
Object[] args = joinPoint.getArgs();
ActionMapping mapping = (ActionMapping) args[0];
ActionForm form = (ActionForm) args[1];
HttpServletRequest request = (HttpServletRequest) args[2];
HttpServletResponse response = (HttpServletResponse) args[3];
String parameter = mapping.getParameter();
if (parameter == null) { // 非DispatchAction, 无需检查权限
return;
}
String methodName = request.getParameter(parameter);
int permission = -1;
if (methodName == null) { // unspecified()方法
permission = Permission.READ;
} else if (methodName.startsWith("add")) {
permission = Permission.CREATE;
} else if (methodName.startsWith("modify")) {
permission = Permission.UPDATE;
} else if (methodName.startsWith("del")) {
permission = Permission.DELETE;
} else {
return; // 其他情况不做检查
}
User user = (User) request.getSession().getAttribute("login");
if (user == null) {
return; //用户没登陆,不检查权限,交由BaseAction处理
}
String path = request.getServletPath();
String moduleUrl = null;
if (path != null && path.length() > 1) {
moduleUrl = path.substring(1);
}
if (!aclManager.hasPermission(user.getId(), moduleUrl, permission)) {
throw new SystemException("对不起,您无权执行此操作,请联系管理员! [color=red][b]这里一定要抛异常,因为无法跳转,跳转回出错.抛出异常后,用用户自定义异常处理方式处理,在处理方法中可以让其跳到指定页面.[/b][/color]username:" + user.getUsername());
}
}
public void setAclManager(ACLManager aclManager) {
this.aclManager = aclManager;
}
}
AOP的配置:
applicationContext.xml
<bean id="auth" class="com.bluesun.oa.manager.impl.AuthImpl">
<property name="aclManager" ref="aclManager"/>
</bean>
/ * more code */
<aop:config proxy-target-class="true">
<aop:aspect id="authAspect" ref="auth">
<aop:pointcut id="authP" expression="execution(* com.bluesun.oa.web.actions.*.execute(..))"/>
<aop:before pointcut-ref="authP" method="authPermission"/>
</aop:aspect>
</aop:config>
重写execute
public ActionForward execute(ActionMapping mapping, ActionForm form,
HttpServletRequest request, HttpServletResponse response)
throws Exception{
//这里可以写一些你的处理代码,不写也可以
ActionForward af = super.execute(mapping, form, request,response);
SaveErrors(request);
return af;
分享到:
相关推荐
1. **Spring AOP** - AOP(面向切面编程)是一种编程范式,用于处理系统中的横切关注点,比如日志、事务管理等,它将这些关注点从核心业务逻辑中分离出来。 - **横切关注点**:指的是在多个类或方法中重复出现的非...
此外,Spring还提供了事务管理、AOP(面向切面编程)等功能。 ### 第四部分:Hibernate框架 Hibernate是流行的Java ORM(Object-Relational Mapping,对象关系映射)框架,它简化了数据库操作。通过Hibernate,...
5. **权限控制**:Spring AOP可以实现权限拦截,比如只有管理员才能删除留言。 6. **数据持久化**:Hibernate负责所有与数据库交互的工作,如添加、修改、删除留言。 总的来说,Struts和Hibernate的结合使得电子...
通过整合Spring,可以利用Spring的依赖注入(DI)和面向切面编程(AOP)能力,进一步提高代码的可测试性和模块化。 通过深入学习和实践Struts教程,你可以掌握构建企业级Web应用的关键技能,了解如何使用Struts实现...
- **Spring AOP的实现**:使用`@Aspect`、`@Before`、`@After`等注解实现切面编程。 - **整合Servlet** - **整合Struts 1.x** - **整合Hibernate** - **模板方法模式** - **JDBCTemplate** - **Spring对Hibernate 3...
5. **Spring框架的整合**:Spring提供依赖注入和AOP(面向切面编程),与Struts和Hibernate整合可以进一步提升应用的灵活性和可维护性。 6. **事务管理**:了解如何在J2EE环境中配置和管理事务,确保数据的一致性。 ...
- **Spring框架**:Spring框架的核心功能是依赖注入(Dependency Injection, DI)和面向切面编程(AOP),在本项目中主要用于管理bean的生命周期以及事务管理等。 - **Hibernate**:作为持久层框架,实现了对象关系映射...