Spring loc和AOP

1.2AOP

面向切面编程,是一种抽象化的面向对象编程,对面向对象编程的一种补充,底层使用动态代理机制来实现

打印日志

业务代码和打印日志耦合起来

image-20250327201327022

计算器方法中,日志和业务混合在一起,AOP要做的就是将日志代码全部抽象出去,统一进行处理,计算器方法中只保留核心的业务代码。

做到核心业务和非业务代码的解耦合

image-20250327201503264

1.创建切面类

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
package cn.edu.svtcc.dataconfig.aop;

import org.springframework.stereotype.Component;

@Component
public class Callmpl implements Cal{
@Override
public int add(int a,int b){
// System.out.println("add方法的参数是[" + a + "," + b + "]");
int result = a+b;

// System.out.println("add方法的返回值是"+result);
return result;
}
@Override
public int sub(int a,int b){
// System.out.println("sub方法的参数是[" + a + "," + b + "]");
int result = a-b;
// System.out.println("sub方法的返回值是"+result);
return result;

}
@Override
public int mul(int a,int b){
// System.out.println("mul方法的参数是[" + a + "," + b + "]");
int result = a*b;
// System.out.println("mul方法的返回值是"+result);
return result;
}
@Override
public int div(int a,int b){

// System.out.println("div方法的参数是[" + a + "," + b + "]");
int result = a/b;
// System.out.println("div方法的返回值是"+result);
return result;
}
}

2.实现类添加Component注解

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
package cn.edu.svtcc.dataconfig;

import org.aspectj.lang.JoinPoint;
import org.aspectj.lang.annotation.AfterReturning;
import org.aspectj.lang.annotation.Aspect;
import org.aspectj.lang.annotation.Before;
import org.springframework.stereotype.Component;

import java.util.Arrays;

@Component
@Aspect
public class LoggerAspect {
@Before("execution(public int cn.edu.svtcc.dataconfig.aop.Cal.*(..))")
public void before(JoinPoint joinPoint){
String name = joinPoint.getSignature().getName();
System.out.println(name + "方法的参数是[" + Arrays.toString(joinPoint.getArgs()));
}

@AfterReturning(value = "execution(public int cn.edu.svtcc.dataconfig.aop.Cal.*(..))",returning = "result")
public void after(JoinPoint joinPoint,Object result){
String name = joinPoint.getSignature().getName();
System.out.println(name + "方法执行完毕,结果是"+result);
}

}

3.配置自动扫包,开启自动生成代理对象

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:context="http://www.springframework.org/schema/context"
xmlns:p="http://www.springframework.org/schema/p"
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/context
http://www.springframework.org/schema/context/spring-context.xsd
http://www.springframework.org/schema/aop
http://www.springframework.org/schema/aop/spring-aop.xsd">

<!-- 自动扫包 -->
<!-- <context:component-scan base-package="cn.edu.svtcc.dataconfig.aop"></context:component-scan>-->
<!-- 修改base-package为父级包路径 -->
<context:component-scan base-package="cn.edu.svtcc.dataconfig"/>
<!-- 开启自动生成代理 -->
<aop:aspectj-autoproxy></aop:aspectj-autoproxy>
</beans>

4.使用

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
package cn.edu.svtcc.dataconfig.ioc;

import cn.edu.svtcc.dataconfig.aop.Cal;
import org.springframework.context.ApplicationContext;
import org.springframework.context.annotation.AnnotationConfigApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;

public class Test {

public static void main(String[] args) {
ApplicationContext context = new ClassPathXmlApplicationContext("spring.xml");
Cal bean=context.getBean(Cal.class);
System.out.println(bean.add(1,2));
System.out.println(bean.sub(1,2));
System.out.println(bean.mul(1,2));
System.out.println(bean.div(1,2));
// System.out.println(context.getBean(GlobalConfig.class));
}
}