spring的AOP之bean半自动编程

一AOP 联盟通知类型

   1、aop 联盟为通知advice定义了org.aopalliance.aop.Advice

   2 、Spring 按照通知Advice 在目标类方法中的连接点位置,可以分为5类

       前置通知   ....aop.MethodBeforeAdvice 在目标方法前实施增强

       后置通知 ...aop.AfterReturningAdvice 在目标方法执行后实施增强

      环绕通知  ......aop.MethodInterceptor    (Interceptor:[ˌɪntərˈseptə(r)] )

                           在目标方法执行前后实施增强

       异常抛出通知....aop.ThrowsAdvice  在哪方法抛出异常后实行增强

    引介通知:aop.ItroductionInterceptor 在目标类中增加方法或者属性


演示环绕通知   环绕通知必须手动执行目标方法

   try{

    //前置通知

   执行目标方法

   //后置通知

} catch(){}

二 代码演示

      1 让spring创建代理对象,从spring容器中手动的获得代理对象

      2 导入jar包

       spring核心 :4+1

       aop aop联盟规范 :com.springsource.org.aopalliance-1.0.0.jar

   3 :目标类   

//接口
public interface IUserService {
public void addUser();
public void updateUser();
public void deleteUser();
}

   //实现类

public class UseServiceImpl implements IUserService {
public void addUser() {
System.out.println("增加用户的方法");
}
public void updateUser() {
System.out.println("更改用户的方法");
}
public void deleteUser() {
System.out.println("删除用户的方法");
}

}

//代理类

/**
 * 切面类中确定通知,需要实现不同接口,接口就是规范,从而就确定方法名称。
 *  采用环绕通知 实现 MethodInterceptor 接口
 * @author dukun
 *
 */
public class MyAspectBean implements MethodInterceptor{

public Object invoke(MethodInvocation mi) throws Throwable {
System.out.println("advice前置通知");
// TODO Auto-generated method stub
//手动执行目标方法
Object obj=mi.proceed();
System.out.println("advice后置通知");
return obj;
}
}

//bean.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:p="http://www.springframework.org/schema/p"
    xmlns:context="http://www.springframework.org/schema/context"
    xsi:schemaLocation="http://www.springframework.org/schema/beans 
               http://www.springframework.org/schema/beans/spring-beans.xsd
               http://www.springframework.org/schema/context 
               http://www.springframework.org/schema/context/spring-context.xsd">


      <!-- 创建目标类 -->      
      <bean id="userService" class="com.nari.service.impl.UseServiceImpl"></bean>
        <!-- 创建切面类 --> 
      <bean id="myAspectBean" class="com.nari.bean_factory.MyAspectBean"></bean>
      
      <!--3创建代理类
         *使用工厂BEAN FactoryBean,底层调用getObject()返回特殊bean
         *ProxyFactoryBean 用于创建代理工厂bean,生成特殊的代理对象
            interfaces:确定接口门
                                          通过<array>可以设置多个值
          target:确定目标类
         **** interceptorNames:通知的切面类的名称,类型String[],如果设置一个值是value=""
           
                               一个不是必填的属性  optimize:强制使用CGLIB
           <property name="optimize" value="true"></property>
       **  底层机制 
                                          如果目标类有接口,采用Jdk动态代理
                                              如果没有接口,采用CGLIB字节码增强
                                         如果 使用<property name="optimize" value="true"></property> 都采用CGLIB字节码增强
      -->
      <bean id="proxyService" class="org.springframework.aop.framework.ProxyFactoryBean">
          <property name="interfaces" value="com.nari.service.IUserService"></property>
          <property name="target" ref="userService"></property>
          <property name="interceptorNames" value="myAspectBean"></property>
          
      </bean>

</beans>


测试:

public class FactoryBeanTest {
@Test
public void test2(){
String xmlPath = "applicationContext.xml";
ApplicationContext appliactionContext =new ClassPathXmlApplicationContext(xmlPath);
IUserService userService = (IUserService) appliactionContext.getBean("proxyService");
userService.addUser();
}
}

猜你喜欢

转载自blog.csdn.net/qq_36697880/article/details/80953085
今日推荐