spring top做自定义注解

来源:互联网 发布:淘宝美工是做什么的 编辑:程序博客网 时间:2024/06/05 12:14
这段时间java反将list集合中的bean内容转换为JSON,返回到浏览器前台,于是想使用注解的方式,对一些特定的需要返回数据的接口进行处理,直接调用反射写的方法,直接将结果转换成JSON,于是获取一下经验。
第一部分,做spring的aop 开发
1,spring采取两种方式来处理切入点和增强处理
@基于注解的零配置方式:使用@Aspect @Pointcut
@基于xml配置文件的管理方式:使用Spring配置文件来定义切入点和增强处理
2,在spring的配置文件使用
<context:component-scan base-package="com.zztaiwll.service,com.zztaiwll.util.annotion"> 
        <context:include-filter type="annotation" expression="org.aspectj.lang.annotation.Aspect"/>
    </context:component-scan>
或者
<aop:aspectj-autoproxy/>
开启注解
3,修改spring的配置文件,将aop所在的包定位自动扫描的包,这里我们暂定为com.zztaiwll.uitl.annotion
 <context:component-scan base-package="com.zztaiwll.service,com.zztaiwll.util.annotion"> 
        <context:include-filter type="annotation" expression="org.aspectj.lang.annotation.Aspect"/>
 </context:component-scan>  
4,本工程使用的maven,所以引入两个相关的包,分别是aspectjweaver.jar和aspectjrt.jar
    <spring.version>4.0.2.RELEASE</spring.version>
        <dependency>
            <groupId>aspectj</groupId>
            <artifactId>aspectjrt</artifactId>
            <version>1.5.4</version>
        </dependency>
    </dependencies>
    <dependency>
            <groupId>org.springframework</groupId>
            <artifactId>spring-aop</artifactId>
            <version>${spring.version}</version>
        </dependency>
        <dependency>
            <groupId>org.springframework</groupId>
            <artifactId>spring-aspects</artifactId>
            <version>${spring.version}</version>
        </dependency>
5,定义切入点
(1)所谓的定义切入点,实质就是为一个切入点表达式起一个名称,从而容许在多个增强处理中重用该名称
(2)切入点定义包含两个部分:
    [1]一个切入点表达式
    [2]一个包含名字和任意参数的方法签名
例如:
@Aspect
public class demo {
@Pointcut("execution(* com.zztaiwll.controller.*.*(..))")
public void myPointcut(){};
}
@Aspect
public class demoDesc {
//直接使用demo切面类的myPointcut切入点
    @AfterReturning(returning="rtc",pointcut="demo.myPointcut()")
    //声明 rtc时指定类型会相知目标方法必须返回指定类型的值或者您没有返回值
    public void log(Object rtc){
         System.out.println("获取该函数返回至"+rvt);
    }
}


6,切入点指示符
Spring AOP一共支持如下几种切入点指示符
【1】,execution:用于匹配方法的连接点,是springaop的最主要的切入点指示符
execution(modifiters-pattern?ret-type-pattern declaring-type-pattern ?name-pattern(param-pattern) throw-pattern)
modifiters-pattern:指定方法的修饰符,支持通配符,该部分可以省略
ret-type-pattern:指定方法的返回值类型,支持通配符,可以使用*通配符来匹配所有返回值类型
declaring-type-pattern:指定方法所属的类,支持通配符,可省略
name-pattern:指定匹配的方法名,支持通配符,可使用*指定所有方法
param-pattern:指定方法中的形参列表,支持两个通配符,即“*”和“..",其中*代表一个人以参数,..代表另个或者多个任意类型的参数
throw-pattern:制定方法声明抛出的异常,支持通配符,可省略
如execution(* com.zztaiwll.controller.*.*(..))指的是controller下所有的类中的所有方法
【2】,within:用于限定匹配特定类型的连接点,当使用Springaop的时候,智能匹配方法执行的连接点
如witnin(com.zztaiwll.controller..*)
【3】,this用于限定AOP代理必须是指定类型的实例,匹配该对象的所有连接点。当使用Spring AOP的时候,只能匹配方法的连接点
this(com.zztaiwll.controller.UserController)
【4】,target:用于限定目标对象必须是指定的类型的实例,匹配该对象所有的连接点,当使用Spring AOP的时候,只能匹配方法的连接点
target(com.zztaiwll.controller.UserController)
【5】,args:用于对连接点的类型进行限制,要求参数类型是指定类型的实例。当使用Spring AOP的时候,只能匹配方法的连接点
args(java.io.Serializable)
【6】,bean:用于限定之匹配指定Bean十里内的连接点,实际上只是用方法执行作为连接点
bean表达式是需要传入Bean的id或name,表示只匹配该bean实例内的连接点,支持使用*通配符
bean(*service)
7,织入点表达式
spring支持使用如下三个逻辑运算符来组合切入点表达式
【1】&&:要求连接点同时匹配两个切入点表达式
【2】||:满足任意一个即可
【3】!要求连接点不匹配指定的切入点表达式
  @Around(value="execution(* com.zztaiwll.controller.*.*(..))&& @annotation(json)")
8,编写相应的方法
{1}Before,After,AfterThrowing,AfterReturning
@Component
//声明这是一个切面Bean
@Aspect
public class ServiceAspect {

    private final static Log log = LogFactory.getLog(ServiceAspect.class);

    //配置切入点,该方法无方法体,主要为方便同类中其他方法使用此处配置的切入点
    @Before("execution(* com.zztaiwll.controller.*.*(..))")
    public void aspect(JoinPoint jp) throws Throwable{    
        Object []obj=jp.getArgs();//获取参数
        System.out.println("1111111111111111111111");
    }
    //(1),pointcut/value:这两个属性是一样的,他们都是用于指定该切入点对应的切入表达式
    //(2),returning:该属性制定一个形参名,用于表示Advice方法中可定义与此同名的形参,该形参用于访问目标方法的返回值,他可以用于限定切入点之匹配具体对应返回值的方法
    @AfterReturning(returning="rvt", pointcut="execution(* com.zztaiwll.controller.*.*(..))")
    public Object after(Object rvt){
        System.out.println("获取该函数返回至"+rvt);
        return rvt;
    }
    //(1),pointcut/value:这两个属性是一样的,他们都是用于指定该切入点对应的切入表达式
    //(2),throwing:该属性制定一个形参名,用于表示Advice方法中可定义与此同名的形参,该形参可用于访问目标方法抛出的异常
    @AfterThrowing(throwing="ex",pointcut="execution(* com.zztaiwll.controller.*.*(..))")
    public void throwError(Throwable ex){
        System.out.println("目标方法抛出异常"+ex);
        System.out.println("模拟Advice对异常的修复");
    }
    //AfterReturning和After的区别
    //(1),AfterReturning增强处理只有在目标方法完全成功后才被织入
    //(2),After增强处理不管目标方法如何结束,他都会被织入
    @After("execution(* com.zztaiwll.controller.*.*(..))")
    public void afterS(JoinPoint jp){
        Object []obj=jp.getArgs();//获取参数
        System.out.println("模拟方法释放资源");
    }
}
{2},Around
@Around注解用于修饰Around增强处理,它的功能比较强大,他近似等于Before增强处理和AfterReturn增强处理的总和,Around增强处理即可以在执行目标方法之前织入增强动作
也可在执行目标方法之后织入增强动作
//声明这是一个组件
@Component
//声明这是一个切面Bean
@Aspect
public class ServiceAspect {

    private final static Log log = LogFactory.getLog(ServiceAspect.class);

    //配置切入点,该方法无方法体,主要为方便同类中其他方法使用此处配置的切入点
    @Around(value="execution(* com.zztaiwll.controller.*.*(..))")
    public Object aspect(ProceedingJoinPoint pjd, json json) throws Throwable{    
        Object[] args=pjd.getArgs();//获取参数
        Object rvt=pjd.proceed();//获取返回结果
        return rvt;
    }
}
第二部分,做自定义注解,
注意关键一点要在spring-servlet.xml中配上
<context:component-scan base-package="com.zztaiwll.service,com.zztaiwll.util.annotion"> 
        <context:include-filter type="annotation" expression="org.aspectj.lang.annotation.Aspect"/>
    </context:component-scan>

【1】,配置自定义注解
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
@Retention(RetentionPolicy.RUNTIME)//
@Target({ ElementType.METHOD })//
public @interface json {
}
【2】aop实现注解
//声明这是一个组件
@Component
//声明这是一个切面Bean
@Aspect
public class ServiceAspect {

    private final static Log log = LogFactory.getLog(ServiceAspect.class);

    //配置切入点,该方法无方法体,主要为方便同类中其他方法使用此处配置的切入点
    @Around(value="execution(* com.zztaiwll.controller.*.*(..))&& @annotation(json)")
    public Object aspect(ProceedingJoinPoint pjd, json json) throws Throwable{    
        Object[] args=pjd.getArgs();
        Object rvt=pjd.proceed();
        Object objs=StringConvertJSON.toJSON(rvt);
        return objs;
    }

}
0 0
原创粉丝点击