基于 Annotation 的 Spring AOP 权限验证方法的实现
1. 配置 applicationContext
在 Spring 中支持 AOP 的配置非常的简单,只需要在 Spring 配置文件 applicationContext.xml 中添加:
<aop:aspectj-autoproxy/>
同时在 applicationContext.xml 的 schema 中配置:
清单 1
|
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
|
<beans xmlns="http://www.springframework.org/schema/beans"xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"xmlns:p="http://www.springframework.org/schema/p"xmlns:aop="http://www.springframework.org/schema/aop"xmlns:context="http://www.springframework.org/schema/context"xmlns:tx="http://www.springframework.org/schema/tx"xmlns:cache="http://www.springframework.org/schema/cache"xsi:schemaLocation=" http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/cache http://www.springframework.org/schema/cache/spring-cache.xsd http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx-3.0.xsd http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop-3.1.xsd"> |
在配置时,我们需要将引用的 jar 包放置在 WEB-INF/lib 目录下面:
需要的 jar 包有

配置这些之后 Spring AOP 就可以开始工作了。
2. 定义 Annotation
首先,我们定义一个常量来表示用户是否登录:
清单 2
|
1
2
3
4
5
6
|
package com.example.myenum; public enum ISLOGIN { YES, LOGOUT, NO } |
这里也可以选择不使用 enum,UserAccessAnnotation 中的 isLogin() 方法也可以返回整数或 String 类型,返回类型并没有限制。常量定义之后,我们再定义 Annotation,在 UserAccessAnnotation 中定义 isLogin(),表示用户是否已经登录:
清单 3
|
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
|
package com.example.annotation; import java.lang.annotation.ElementType; import java.lang.annotation.Retention; import java.lang.annotation.RetentionPolicy; import java.lang.annotation.Target; import com.example.myenum.ISLOGIN; @Retention(RetentionPolicy.RUNTIME) @Target(ElementType.METHOD) public @interface UserAccessAnnotation { /** * User has been login or not. * */ ISLOGIN isLogin(); } |
定义好之后,这个 Annoatation 将可以被放置在需要验证用户是否登录的方法前面,就像下面这样:
清单 4
|
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
|
package com.example.aspect; public class OrderAction extends BaseAction{ …… @UserAccessAnnotation(>isLogin=ISLOGIN.YES) public String Order(){ try{ Boolean result = orderService.order(Quote quote); if(result) return SUCCESS; }catch(Exception e) { logger.debug(e); this.addActionError(getText("user_no_permission_error")); } return INPUT; } …… } |
在这里我们使用 UserAccessAnnotation 来表示需要在 Order 方法执行之前判断用户是否已经登录,如果没有登录,在 struts2 中,通过下面定义的 Exception 的捕获机制,将页面转到登录页面。
3. 在 applicationContext.xml 中定义 Aspect
清单 5
|
1
2
3
|
<bean id="permission" class="com.example.aspect.PermissionAspect" scope="prototype"> <property name="authService" ref="AuthService" /> </bean> |
我们要在 Spring 中定义 PermissionAspect。在 Struts+Spring 架构中可以把 Aspect 看作是一个 Action,只不过 Aspect 是其他 Action 的前提条件或者结束动作。Aspect 定义中的 Service 属性和 Action 中的 Service 属性没有任何区别。这里我们用 AuthService 类来实现判断用户是否已经登录的逻辑。
4. 定义 PointCut
清单 6
|
1
2
3
4
5
6
7
8
9
10
|
@Aspect public class SystemArchitecture { /** * A Join Point is defined in the action layer where the method needs * a permission check. */ @Pointcut("@annotation(com.example.annotation.UserAccessAnnotation)") public void userAccess() {} } |
PointCut 即切入点,就是定义方法执行的点,before、after 或者 around。 一般情况下,我们把 PointCut 全部集中定义在 SystemArchitecture 类中,以方便修改和管理。
当实现 Aspect 时可以很方便的使用我们在 SystemArchitecture 中定义的 PointCut。
5. 实现 Aspect
清单 7
|
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
|
package com.example.aspect; import org.aspectj.lang.annotation.Aspect; import org.aspectj.lang.annotation.Before; import com.example.annotation.UserAccessAnnotation; import com.example.base.action.BaseAction; import com.example.myenum.USERTYPE; import com.example.service.AuthService; @Aspect public class PermissionAspect extends BaseAction{ …… AuthService authService = null; @Before(value="com.example.aspect.SystemArchitecture.userAccess()&&"+ "@annotation(userAccessAnnotation)",argNames="userAccessAnnotation") public void checkPermission(UserAccessAnnotation userAccessAnnotation) throws Exception{ IsLogin isLogin = userAccessAnnotation.isLogin (); if(!authService.userLogin(user).equals(isLogin.toString())){ throw new NoPermissionException(getText("user_no_permission_error")); } } ……} |
在 checkPermission 方法前,我们首先定义 PointCut:
|
1
2
|
@Before(value="com.example.aspect.SystemArchitecture.userAccess()&&"+ "@annotation(userAccessAnnotation)",argNames="userAccessAnnotation"). |
argNames="userAccessAnnotation" 的意思是把 Annotation 当做参数传递进来,并判断用户登录状态是否与 Annotation 中的定义一致。如果不一致,就要抛出 NoPermissionException,通知系统该用户没有权限。
基于 Annotation 的 Spring AOP 权限验证方法的实现的更多相关文章
- 基于 Annotation 拦截的 Spring AOP 权限验证方法
基于 Annotation 拦截的 Spring AOP 权限验证方法 转自:http://www.ibm.com/developerworks/cn/java/j-lo-springaopfilte ...
- Spring学习笔记之四----基于Annotation的Spring AOP编程
你能使用@Aspect annotation将某个Java类标注为Aspect,这个Aspect类里的所有公有方法都可以成为一个Advice,Spring提供了5个Annotation去将某个方法标注 ...
- 基于注解的Spring AOP的配置和使用
摘要: 基于注解的Spring AOP的配置和使用 AOP是OOP的延续,是Aspect Oriented Programming的缩写,意思是面向切面编程.可以通过预编译方式和运行期动态代理实现在不 ...
- 基于注解的Spring AOP示例
基于注解的Spring AOP示例 目录 在XML配置文件中开启 @AspectJ 支持 声明切面及切入点 声明通知 测试 结语 在XML配置文件中开启 @AspectJ 支持 要使用Spring的A ...
- 基于注解的Spring AOP的配置和使用--转载
AOP是OOP的延续,是Aspect Oriented Programming的缩写,意思是面向切面编程.可以通过预编译方式和运行期动态代理实现在不修改源代码的情况下给程序动态统一添加功能的一种技术. ...
- 基于@AspectJ配置Spring AOP之一--转
原文地址:http://tech.it168.com/j/2007-08-30/200708302209432.shtml 概述 在低版本Spring中定义一个切面是比较麻烦的,需要实现特定的接口,并 ...
- Spring学习总结(17)——Spring AOP权限管理
每个项目都会有权限管理系统 无论你是一个简单的企业站,还是一个复杂到爆的平台级项目,都会涉及到用户登录.权限管理这些必不可少的业务逻辑.有人说,企业站需要什么权限管理阿?那行吧,你那可能叫静态页面,就 ...
- Asp.net Mvc4 基于Authorize实现的模块权限验证方式
在MVC中,我们可以通过在action或者controller上设置Authorize[Role="xxx"] 的方式来设置用户对action的访问权限.显然,这样并不能满足我们的 ...
- Spring AOP项目应用——方法入参校验 & 日志横切
转载:https://blog.csdn.net/Daybreak1209/article/details/80591566 应用一:方法入参校验 由于系统多个方法入参均对外封装了统一的Dto,其中D ...
随机推荐
- 热更新(一) 之Lua语法的学习
热更新 如热更新果需要更换UI显示,或者修改游戏的逻辑,这个时候,如果不使用热更新,就需要重新打包,然后让玩家重新下载(浪费流量和时间,体验不好).热更新可以在不重新下载客户端的情况下,更新游戏的内容 ...
- UWP开发入门(二)——RelativePanel
RelativePanel也是Win10 UWP新增的控件,和上篇提到的SplitView一样在UWP的UI布局起到非常重要的作用.说句实在话,这货其实就是为了UWP的Adaptive UI而特意增加 ...
- [uwp]MVVM模式实战之必应壁纸查看器
最近学习MVVM,至于什么是MVVM我也在这儿不多说了,一是关于它的解释解释网上非常多,二是我怕自己讲不清,误导自己没关系,误导别人就不好了.. 好了,废话结束,看是实战...... 这个必应壁纸的d ...
- php—Smarty-2
一.注释 *注释内容* Html注释显示客户端源文件中 Smarty注释不会发给客户端 Smarty的注释主要给模板设计者来看的 二.模板中的变量 l 由php文件分配 1) 普通变量 2) 数 ...
- linux强制安装rpm包的命令
rpm -ivh *********.rpm --nodeps --force 强制安装会忽略掉所有依赖关系,强制进行安装
- Kafka入门学习--基础
Kafka是什么 Kafka是最初由Linkedin公司开发,是一个分布式.支持分区的(partition).多副本的(replica),基于zookeeper协调的分布式消息系统,它的最大的特性就可 ...
- 关于Mysql数据库查询数据大小写的问题汇总
前天在问答区看到一个童鞋对于mysql中大小写问题不熟悉,在回复他后再次汇总梳理如下: mysql中大小写问题主要有以下两种: A.表名区分大小写 ower_case_table_names 是表名区 ...
- HDU-1160-FatMouse's Speed(线性DP,LIS)
FatMouse's Speed Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 65536/32768 K (Java/Others) ...
- Oracle PL/SQL学习之基础篇(1)
1.PL/SQL,全称Procedure Language/SQL,过程化sql语言 PL/SQL的程序结构 declare --声明部分(包括变量.光标.例外声明) begin --语句序列(DML ...
- word里的字号与html字号的对应关系
在word里输入一段文字,把文字调成需要的大小,即"三号或者小三",然后把文件另存为网页,在格式里选择“html”格式,然后把word关闭,将另存的html文件用编辑工具打开,就可 ...