Spring AOP系列之四:前置通知

通过实现[color=red]org.springframework.aop.MethodBeforeAdvice[/color]来完成前置通知:


public class CarBeforeAdvice implements MethodBeforeAdvice {

@Override
// method 目标类方法,args 方法参数,target 目标对象
public void before(Method method, Object[] args, Object target) throws Throwable {
System.out.println("Welcome to the car shop");
}
}


Spring配置文件beans-before-advice.xml

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd"
default-autowire="byName">

<bean id="car" class="com.john.spring.aop.Car">
<property name="name" value="Superb" />
<property name="price" value="220000" />
</bean>

<bean id="carBeforeAdvice" class="com.john.spring.aop.CarBeforeAdvice" />

<bean id="proxyBean" class="org.springframework.aop.framework.ProxyFactoryBean">
<property name="proxyInterfaces">
<value>com.john.spring.aop.Vehicle</value>
</property>
<property name="interceptorNames">
<list>
<value>carBeforeAdvice</value>
</list>
</property>
<property name="target">
<ref bean="car" />
</property>
</bean>
</beans>


测试:

public static void main(String[] args) {
ApplicationContext ctx = new ClassPathXmlApplicationContext(new String[] { "beans-before-advice.xml" });
Vehicle vehicle = (Vehicle) ctx.getBean("proxyBean");
vehicle.info();
}


输出:
Welcome to the car shop
Car name: Superb, price: 220000


附:
info()调用的时候,调用org.springframework.aop.framework.adapter.MethodBeforeAdviceAdapter类的getInterceptor方法:

class MethodBeforeAdviceAdapter implements AdvisorAdapter, Serializable {

public boolean supportsAdvice(Advice advice) { // 是否支持指定通知
return (advice instanceof MethodBeforeAdvice);
}

public MethodInterceptor getInterceptor(Advisor advisor) {
MethodBeforeAdvice advice = (MethodBeforeAdvice) advisor.getAdvice(); // 获取通知
return new MethodBeforeAdviceInterceptor(advice);
}
}


然后调用org.springframework.aop.framework.adapter.MethodBeforeAdviceInterceptor的invoke方法:

public Object invoke(MethodInvocation mi) throws Throwable {
this.advice.before(mi.getMethod(), mi.getArguments(), mi.getThis() ); // 前置通知实现类的before方法。这里是CarBeforeAdvice类的实例
return mi.proceed(); // 目标类方法的执行。这里是info()。
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
好的,根据你的问题,我理解你需要一个使用Spring AOP技术完成的程序,其中切面以方法为基本单位,在调用bean.Student.show()方法时执行前置通知、环绕通知、后置通知和最终通知。下面是一个示例代码: ```java // Student.java package bean; public class Student { private String name; private int age; public void show() { System.out.println("Name: " + name + ", Age: " + age); } // getters and setters } // LogXML.java package aop; import org.aspectj.lang.ProceedingJoinPoint; public class LogXML { public void before() { System.out.println("前置通知运行"); } public void afterReturning() { System.out.println("后置通知运行"); } public void afterThrowing() { System.out.println("异常通知运行"); } public void after() { System.out.println("最终通知运行"); } public Object around(ProceedingJoinPoint jp) throws Throwable { System.out.println("环绕通知开始运行"); Object result = jp.proceed(); System.out.println("环绕通知结束运行"); return result; } } // SpringAopTest.java package test; import org.springframework.context.ApplicationContext; import org.springframework.context.support.ClassPathXmlApplicationContext; import bean.Student; public class SpringAopTest { public static void main(String[] args) { ApplicationContext context = new ClassPathXmlApplicationContext("applicationContext.xml"); Student student = (Student) context.getBean("student"); student.show(); } } // applicationContext.xml <?xml version="1.0" encoding="UTF-8"?> <beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:aop="http://www.springframework.org/schema/aop" xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop.xsd"> <bean id="student" class="bean.Student"> <property name="name" value="zhangsan" /> <property name="age" value="30" /> </bean> <bean id="log" class="aop.LogXML" /> <aop:config> <aop:aspect ref="log"> <aop:pointcut id="showPointcut" expression="execution(* bean.Student.show())" /> <aop:before pointcut-ref="showPointcut" method="before" /> <aop:around pointcut-ref="showPointcut" method="around" /> <aop:after-returning pointcut-ref="showPointcut" method="afterReturning" /> <aop:after-throwing pointcut-ref="showPointcut" method="afterThrowing" /> <aop:after pointcut-ref="showPointcut" method="after" /> </aop:aspect> </aop:config> </beans> ``` 你可以将以上代码保存到对应的文件中,并使用Maven或Gradle等构建工具进行编译运行。在程序运行时,会输出以下信息: ``` 前置通知运行 环绕通知开始运行 Name: zhangsan, Age: 30 环绕通知结束运行 后置通知运行 最终通知运行 ```

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值