利用自定义注解+aop实现日志打印

利用aop来实现web项目请求中的参数,从而实现日志的记录,是很常用的功能。自己从网上找到了一些例子和自己的总结。

1.声明自定义注解

@Target(ElementType.METHOD) // 方法注解
@Retention(RetentionPolicy.RUNTIME) // 运行时可见
public @interface WebLog {
    String operateType();// 记录日志的操作类型
}

2.实现aop接口

@Aspect
@Component
public class WebLogAspect {

    private final Logger logger = LoggerFactory.getLogger(WebLogAspect.class);

    @Resource
    private LogMapper logMapper;

 
    @Around("@annotation(com.company.project.annotation.WebLog)")
    public Object   logAfterController(ProceedingJoinPoint pjp)  {
        //获取当前请求对象
        //这个RequestContextHolder是Springmvc提供来获得请求的东西
        RequestAttributes requestAttributes = RequestContextHolder.getRequestAttributes();
        HttpServletRequest request = ((ServletRequestAttributes)requestAttributes).getRequest();

        // 获取方法签名
        MethodSignature methodSignature = (MethodSignature) pjp.getSignature();

        // 请求的方法
        String methodname = methodSignature.getMethod().getName();

        //请求的类名
        String ClassName=pjp.getSignature().getDeclaringTypeName();

        //请求的参数
        String ArgsName=Arrays.toString(pjp.getArgs());

        //IP地址
        String ipdress=request.getRemoteAddr();

        //请求URL
        String URL=request.getRequestURL().toString();

        //请求方式
        String WebMethod=request.getMethod();

        // 创建一个日志对象(准备记录日志)
        Log logSys  = new Log();

        //编号
        logSys.setLognum(UUID.randomUUID().toString());

        // 获取指定方法上面的注解
        WebLog logAnno = methodSignature.getMethod().getAnnotation(WebLog.class);

        // 获取操作描述的属性值
        String operateType = logAnno.operateType();
        logSys.setContent(operateType);



        SimpleDateFormat sdf = new SimpleDateFormat("yyyy.MM.dd HH:mm:ss");
        Date d= new Date();
        String opertime = sdf.format(d);

        logSys.setCtime(new Date());

        //获取用户名  这里是使用了springSecurity 获取用户名  如果没有使用 可以删除
        Authentication authentication = SecurityContextHolder.getContext().getAuthentication();
        if (!(authentication instanceof AnonymousAuthenticationToken)) {
            //设置操作人id
            logSys.setPmid(Integer.valueOf(authentication.getName()));
        }
        else {
           logSys.setPmid(-1);
        }
        // 记录下请求内容
        logger.info("################请求地址为URL : " + URL);
        logger.info("################请求方式为 : " + WebMethod);
        logger.info("################IP地址为 : " + ipdress);
        logger.info("################传递的参数为 : " + ArgsName);
        logger.info("################调用的方法名 : " +methodname);
        logger.info("################完整类名为 : " + ClassName + "." + methodname);
        logger.info("################操作时间 : "+opertime );
        logger.info("################操作类型 : "+operateType);
        Object result =null;
        try {
            //代理方法执行
            result= pjp.proceed();
            logSys.setResult("操作成功");
            logMapper.insert(logSys);
            logger.info("################备注 : "+"操作成功");
        } catch (Throwable throwable) {
            logSys.setResult("操作失败:"+throwable.getMessage());
            logMapper.insert(logSys);
            logger.info("################备注 : "+"操作失败:"+throwable.getMessage());
            throw throwable;
        }
        return result;
    }

}

3.使用方法

在需要记录日志的方法中,使用该注解,如:登录成功,修改,删除等等。一般用在controller和service中

    /**
     * 添加广告
     * @param
     * @return
     */
    @PostMapping("/api/v1/notice/ad")

    @WebLog(operateType = "添加广告")

    public Result add(@RequestParam(value = "adName",required = true)String adNam,
                      @RequestParam(value = "adFile",required = false) MultipartFile adFile,
                      @RequestParam(value = "des",required = true)String des){

}

4.在使用了该注解的地方,可以手动抛出一些异常 , aop也能捕获到  如下

  throw  new ServiceException("广告增加失败");

5. 这样就会生成一个日志记录。使用aop实现


版权声明:本文为qq_23947467原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接和本声明。