日志,注解切入点

时间:2022-09-26 09:47:53

1.创建注解

/**
 * 自定义注解
 *
 * 1. @interface
 * 2.元注解 注解注解的注解
 *     @Target  定义当前注解的使用范围  METHOD 只能在方法上使用
 *     @Retention 定义当前注解的保留时间 RUNTIME意味着不管编译,测试还是打包一直保留  一般都是这个
 *
 * 2.注解的属性(方法) 可以给默认值 default
 */
@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
public @interface LogAnnotation {
    String value() default "";
}

2.定义aop日志类

/**
 * 1.定义当前类为切面类
 */
@Configuration
@Aspect
public class LogAspect {
    private Logger logger = LoggerFactory.getLogger(LogAspect.class);

    @Autowired
    private CmfzLogDao cmfzLogDao;

    /**
     * 1.定义增强方法
     */
    @After("logPoint()")
    public void logAfter(JoinPoint joinPoint){
        logger.debug("开始执行增强方法");
//        1.得到要添加的数据
        CmfzLog cmfzLog = new CmfzLog();
//        获取当前时间
        cmfzLog.setLogDate(new Date());

        /**
         * 获取用户名 从session中
         * 1.怎么拿到session?  不敢保证只有一个 装配不行  传参不行
         *
         *  通过RequestContextHolder 中的方法 可以获取的是当前请求
          */
        ServletRequestAttributes requestAttributes = (ServletRequestAttributes)RequestContextHolder.getRequestAttributes();
        HttpServletRequest request = requestAttributes.getRequest();
        /**
         * 通过当前请求 获取的一定是当前用户对应的session 参照session原理
         */
        HttpSession session = request.getSession();
//        从session中获取管理员信息
        CmfzAdmin cmfzAdmin = (CmfzAdmin) session.getAttribute("admin");
        cmfzLog.setUserName(cmfzAdmin.getUsername());

//        获取ip地址
        String ipAddrByRequest = IPKit.getIpAddrByRequest(request);
        cmfzLog.setLogIp(ipAddrByRequest);

        /**
         * 获取操作内容  执行不同的方法 需要获取到不同的操作内容
         * 如果执行 菜单的 SelectAll  获取到的应该是:查询全部菜单信息
         * 如果执行的是用户的添加  获取到的应该是:成功添加一个用户
         * 写死  不行
         * 传参  不行
         * 通过自定义注解
         * 1.在自定义注解里面可以写入操作内容
         * 2.可以获取到被执行方法的注解
         * 3.进而获取注解的内容  也就是操作内容
         */
//        1.获取方法签名对象 joinPoint 连接点对象 得到切点相关的信息
        MethodSignature signature = (MethodSignature) joinPoint.getSignature();
//        2.获取方法对象(当前正在执行的方法) 因为注解加在了方法上  所以需要得到方法对象
        Method method = signature.getMethod();
//        3.通过方法对象得到注解 参数:注解的类对象
        LogAnnotation annotation = method.getAnnotation(LogAnnotation.class);
//        4.通过注解可以得到注解中的值  也就是操作的内容
        String value = annotation.value();

        cmfzLog.setLogContent(value);

//        2.将数据添加到数据库
        cmfzLogDao.insert(cmfzLog);

        logger.debug("增加方法执行结束,添加日志信息为:{}",cmfzLog);
    }

    /**
     * 2.定义切点
     * 切在什么地方  方法  注解
     * 例如事务 切方法 统一处理简单 切注解 灵活
     */
    @Pointcut("@annotation(com.baizhi.Annotation.LogAnnotation)")
    public void logPoint(){}
}

3.使用

在需要使用日志的地方,加上自定义的注解@LogAnnotation("自定义注解"),在方法执行时,会自动增强,加入日志aop进行日志的处理。


4. 导入的依赖

 

        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-aop</artifactId>
        </dependency>