配置与前置通知一样
代理类
@Aspect
@Component
public class MyAspect {
/**
* 后置通知方法的规范
* 1)访问权限是public
* 2)方法没有返回值void
* 3)方法名称自定义
* 4)方法有参数(也可以没有参数,如果目标方法没有返回值,则可以写无参的方法,
* 但一旦写有参,这样可以处理无参可以处理有参),
* 这个切面的参数就是目标方法的返回值
* 5)使用@AfterReturning注解标明是后置通知
* 参数有俩
* value:指定切入点表达式
* returning:指定目标方法的返回值的名称,则名称必须与方法的参数名称一致
*
*
*/
@AfterReturning(value = "execution(* com.wzx.s02.*.*(..))",returning = "obj")
public void myAfterreturning(Object obj){
System.out.println("后置通知功能实现..............");
}
}
测试类
@Test
public void test2(){
ApplicationContext ac=new ClassPathXmlApplicationContext("s02/applicationContext.xml");
SomeService someService= (SomeService) ac.getBean("someServiceImpl");
String password = someService.doSome("asd", 21);
System.out.println("在测试方法中目标方法的返回值"+password);
}
转换类型
将小写转换为大写转换失败
@AfterReturning(value = "execution(* com.wzx.s02.*.*(..))",returning = "obj")
public void myAfterreturning(Object obj){
System.out.println("后置通知功能实现..............");
if (obj != null) {
if (obj instanceof String ) { //判断obj是不是String类型用instanceof
obj=obj.toString().toUpperCase() ;
System.out.println("在切面方法中目标方法的返回值"+obj);
}
}
}
转换类型
将张三转换为李四转换成功
新建一个Student类
public class Student {
private String name;
public Student() {
}
@Override
public String toString() {
return "Student{" +
"name='" + name + '\'' +
'}';
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public Student(String name) {
this.name = name;
}
}
更改接口
public interface SomeService {
String doSome(String name,int age);
Student change();
}
更改实现类
@Service
public class SomeServiceImpl implements SomeService{
@Override
public String doSome(String name, int age) {
System.out.println("doSome()业务方法被执行............");
return "abcd";
}
@Override
public Student change() {
System.out.println("change()方法被执行.......");
return new Student("张三");
}
}
更改代理类
@Aspect
@Component
public class MyAspect {
/**
* 后置通知方法的规范
* 1)访问权限是public
* 2)方法没有返回值void
* 3)方法名称自定义
* 4)方法有参数(也可以没有参数,如果目标方法没有返回值,则可以写无参的方法,
* 但一旦写有参,这样可以处理无参可以处理有参),
* 这个切面的参数就是目标方法的返回值
* 5)使用@AfterReturning注解标明是后置通知
* 参数有俩
* value:指定切入点表达式
* returning:指定目标方法的返回值的名称,则名称必须与方法的参数名称一致
*
*
*/
@AfterReturning(value = "execution(* com.wzx.s02.*.*(..))",returning = "obj")
public void myAfterreturning(Object obj){
System.out.println("后置通知功能实现..............");
if (obj != null) {
if (obj instanceof String ) { //判断obj是不是String类型用instanceof
obj=obj.toString().toUpperCase() ;
System.out.println("在切面方法中目标方法的返回值"+obj);
}
if(obj instanceof Student){
Student stu=(Student) obj;
stu.setName("李四");
System.out.println("在切面方法中目标方法的返回值:"+stu);
}
}
}
}
测试类
@Test
public void test3(){
ApplicationContext ac=new ClassPathXmlApplicationContext("s02/applicationContext.xml");
SomeService someService= (SomeService) ac.getBean("someServiceImpl");
Student stu=someService.change();
System.out.println("在测试方法中目标方法的返回值"+stu);
}
ps:如果目标方法的返回值是8中基本类型或String的类型,则不可改变
如果目标方法的返回值是引用类型,则可以改变