您的位置:首页 > 编程语言 > Java开发

springframework(九)AOP的advices,中规中矩的使用方式

2016-03-23 12:56 489 查看
Spring的Advices

Advices实现了Aspect的真正逻辑。由于织入至Targets的实际不同,spring提供了不同的Advices,像Before Advice,After Advice,Around Advice,Throw Advice。

(1)、Before Advice

通过实现MethodBeforeAdvice来定义

(2)、After Advice

通过实现AfterReturningAdvice来定义

(3)、Around Advice

通过实现MethodInterceptor来定义

(4)、Throw Advice

通过实现ThrowsAdvice来定义

我们将使用一个代理的bean aaa,给这个代理的bean加上我们spring的advice,看看他的日志输出表现。我们通过代码示例来说明:

1、定义基本的advice Bean以及要被调用的类

(1)、beforeAdvice的Bean

[java]
view plain
copy

package com.itcast.advice;

import java.lang.reflect.Method;

import org.springframework.aop.MethodBeforeAdvice;

/**
* 调用方法之前
* */
public class LogBeforeAdvice implements MethodBeforeAdvice {
public void before(Method method, Object[] args, Object target)
throws Throwable {
System.out.println("beforeAdvice 调用方法之前被执行!...........");
}
}

(2)、afterAdvice的bean

[java]
view plain
copy

package com.itcast.advice;

import java.lang.reflect.Method;
import org.springframework.aop.AfterReturningAdvice;

public class LogAfterAdvice implements AfterReturningAdvice {
public void afterReturning(Object returnValue, Method method,
Object[] args, Object target) throws Throwable {
System.out.println("afterAdvice 调用方法之后被执行!...........");
}
}

(3)、Around advice的Bean

[java]
view plain
copy

package com.itcast.advice;

import org.aopalliance.intercept.MethodInterceptor;
import org.aopalliance.intercept.MethodInvocation;

/**
* 环绕通知
* */
public class LogAroundAdvice implements MethodInterceptor {

public Object invoke(MethodInvocation mi) throws Throwable {
Object result=null;
System.out.println("around 调用方法之前....");

result=mi.proceed();

System.out.println("around 调用方法之后...");
return result;
}
}

(4)、Throw Advice的Bean

[c-sharp]
view plain
copy

package com.itcast.advice;

import java.lang.reflect.Method;

import org.springframework.aop.ThrowsAdvice;

/**抛出异常时候的通知*/
public class ThrowAdvice implements ThrowsAdvice {

public void afterThrowing(Method method,Object[] args,Object target,Throwable subclass) {
System.out.println("ThrowAdvice 记录异常...........");
}

}

(5)、要被代理的类

[java]
view plain
copy

package com.itcast.proxy;

public class HelloSpeaker1 implements IHello {

public void hi() {
System.out.println("我在HelloSpeaker1中");
}
public void hiAAA(String aaa) {
System.out.println("我在HelloSpeaker1中---hiAAA["+aaa+"]");
}

public void hiBBB(String bbb) throws Exception {
System.out.println("我在HelloSpeaker1中---hiBBB["+bbb+"]");
throw new Exception("aaa");
}
}

package com.itcast.proxy;

/**
* 代理接口
* */
public interface IHello {

public void hi();

public void hiAAA(String aaa);

public void hiBBB(String bbb) throws Exception;

}

2、在配置文件中声明我们的bean

[xhtml]
view plain
copy

<!-- 代理 -->
<bean id="helloSpeaker1" class="com.itcast.proxy.HelloSpeaker1"></bean>

<!-- 声明四种通知类型,其实就是你想加入到其他被代理程序执行逻辑中的代码 -->
<bean id="beforeAdvice" class="com.itcast.advice.LogBeforeAdvice"/>
<bean id="afterAdvice" class="com.itcast.advice.LogAfterAdvice"></bean>
<bean id="aroundAdvice" class="com.itcast.advice.LogAroundAdvice"></bean>
<bean id="throwAdvice" class="com.itcast.advice.ThrowAdvice"></bean>
<!-- 基础的通知使用,这里强行给helloSpeaker1加上了advice通知 -->
<bean id="aaa" class="org.springframework.aop.framework.ProxyFactoryBean">
<property name="target" ref="helloSpeaker1"></property>
<property name="interceptorNames">
<list>
<value>aroundAdvice</value>
<value>beforeAdvice</value>
<value>afterAdvice</value>
<value>throwAdvice</value>
</list>
</property>
</bean>

3、在main函数中调用

[java]
view plain
copy

package com.itcast.advice;

import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;
import com.itcast.proxy.IHello;

public class AdviceMain {
/**对于给基本的spring bean强行指定一批advice方法的调用展示**/
public static void main(String[] args) {
ApplicationContext ctx = new ClassPathXmlApplicationContext("bean-config.xml");
IHello h = (IHello)ctx.getBean("aaa");
h.hiAAA("测试配置aop的adivce");

System.out.println("进行抛出异常的adivce展示-==================");
try {
h.hiBBB("测试抛出异常的advice");
} catch (Exception e) {
}
}

}

4、控制台的显示

[xhtml]
view plain
copy

around 调用方法之前....
beforeAdvice 调用方法之前被执行!...........
我在HelloSpeaker1中---hiAAA[测试配置aop的adivce]
afterAdvice 调用方法之后被执行!...........
around 调用方法之后...
进行抛出异常的adivce展示-==================
15:05:05,671 DEBUG ThrowsAdviceInterceptor:88 - Found exception handler method: public void com.itcast.advice.ThrowAdvice.afterThrowing(java.lang.reflect.Method,java.lang.Object[],java.lang.Object,java.lang.Throwable)
around 调用方法之前....
beforeAdvice 调用方法之前被执行!...........
我在HelloSpeaker1中---hiBBB[测试抛出异常的advice]
15:05:05,687 DEBUG ThrowsAdviceInterceptor:119 - Found handler for exception of type [java.lang.Throwable]: public void com.itcast.advice.ThrowAdvice.afterThrowing(java.lang.reflect.Method,java.lang.Object[],java.lang.Object,java.lang.Throwable)
ThrowAdvice 记录异常...........

上边的日志已经说明了,我们给一个bean定义一个代理的bean,然后指定他的拦截器序列,就能在bean中的方法调用的前后,以及抛出异常后进行一系列我们自己定义的操作。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: