使用spring aop 记录接口日志(转载)
spring配置文件中增加启用aop的配置
<!-- 增加aop 自动代理配置 --> <aop:aspectj-autoproxy />
切面类配置
1 package com.zchx.acvices; 2 3 import java.text.SimpleDateFormat; 4 5 import org.aspectj.lang.JoinPoint; 6 import org.aspectj.lang.ProceedingJoinPoint; 7 import org.aspectj.lang.annotation.After; 8 import org.aspectj.lang.annotation.AfterReturning; 9 import org.aspectj.lang.annotation.AfterThrowing; 10 import org.aspectj.lang.annotation.Around; 11 import org.aspectj.lang.annotation.Aspect; 12 import org.aspectj.lang.annotation.Before; 13 import org.aspectj.lang.annotation.Pointcut; 14 import org.slf4j.Logger; 15 import org.slf4j.LoggerFactory; 16 import org.springframework.stereotype.Component; 17 18 /** 19 * 切面日志记录 20 * 21 * @version V1.0 22 * @author songxiaotong 23 * @date 2018年2月6日 下午2:39:03 24 * @Description 25 */ 26 // 声明这是一个组件 27 @Component 28 // 声明这是一个切面Bean 29 @Aspect 30 public class Advices { 31 32 /** 33 * 日志记录工具 34 */ 35 private static final Logger LOGGER = LoggerFactory.getLogger(Advices.class); 36 37 /** 38 * 默认构造函数 39 */ 40 public Advices() { 41 LOGGER.debug("初始化日志切面"); 42 } 43 44 /** 45 * 配置切入点,该方法无方法体,主要为方便同类中其他方法使用此处配置的切入点 46 * <p> 47 * 扫描com.sixeco下面的所有类 48 * 49 * @see [类、类#方法、类#成员] 50 */ 51 @Pointcut("execution(* com.zhichenhaixin..*.*(..)) or execution(* com.zchx..*.*(..))") 52 public void aspect() { 53 } 54 55 /** 56 * 配置前置通知,使用在方法aspect()上注册的切入点 57 * <p> 58 * 同时接受JoinPoint切入点对象,可以没有该参数 59 * 60 * @param joinPoint 切入点 61 * @see [类、类#方法、类#成员] 62 */ 63 @Before("aspect()") 64 public void before(JoinPoint joinPoint) { 65 // LOGGER.debug("before {}", joinPoint.getSignature().toString()); 66 } 67 68 /** 69 * 配置后置通知,使用在方法aspect()上注册的切入点 70 * <p> 71 * </p> 72 * 73 * @param joinPoint 切入点 74 * @see [类、类#方法、类#成员] 75 */ 76 @After("aspect()") 77 public void after(JoinPoint joinPoint) { 78 // LOGGER.debug("after {}", joinPoint.getSignature().toString()); 79 } 80 81 /** 82 * 配置环绕通知,使用在方法aspect()上注册的切入点 83 * <p> 84 * 记录方法开始到结束的耗时 85 * 86 * @param joinPoint 切入点 87 * @return Object 处理结果 88 * @throws Throwable 异常 89 * @see [类、类#方法、类#成员] 90 */ 91 @Around("aspect()") 92 public Object around(JoinPoint joinPoint) throws Throwable { 93 long start = System.currentTimeMillis(); 94 Object object = null; 95 try { 96 ProceedingJoinPoint tempJoinPoint = (ProceedingJoinPoint) joinPoint; 97 object = tempJoinPoint.proceed(); 98 long end = System.currentTimeMillis(); 99 // LOGGER.debug("around {} Use time : {} ms!", 100 // joinPoint.getSignature().toString(), end - start); 101 LOGGER.debug("计时时间:{} 耗时:{}毫秒 URI: {} 最大内存: {}m 已分配内存: {}m 已分配内存中的剩余空间: {}m 最大可用内存: {}m", 102 new SimpleDateFormat("hh:mm:ss.SSS").format(start), end - start, 103 joinPoint.getSignature().toString(), Runtime.getRuntime().maxMemory() / 1024 / 1024, 104 Runtime.getRuntime().totalMemory() / 1024 / 1024, Runtime.getRuntime().freeMemory() / 1024 / 1024, 105 (Runtime.getRuntime().maxMemory() - Runtime.getRuntime().totalMemory() 106 + Runtime.getRuntime().freeMemory()) / 1024 / 1024); 107 } catch (Throwable e) { 108 long end = System.currentTimeMillis(); 109 // LOGGER.debug("around {} Use time : {} ms with exception", 110 // joinPoint.getSignature().toString(), end - start); 111 112 LOGGER.debug("计时时间:{} 耗时:{}毫秒 URI: {} 最大内存: {}m 已分配内存: {}m 已分配内存中的剩余空间: {}m 最大可用内存: {}m", 113 new SimpleDateFormat("hh:mm:ss.SSS").format(start), end - start, 114 joinPoint.getSignature().toString(), Runtime.getRuntime().maxMemory() / 1024 / 1024, 115 Runtime.getRuntime().totalMemory() / 1024 / 1024, Runtime.getRuntime().freeMemory() / 1024 / 1024, 116 (Runtime.getRuntime().maxMemory() - Runtime.getRuntime().totalMemory() 117 + Runtime.getRuntime().freeMemory()) / 1024 / 1024); 118 119 StackTraceElement[] s = e.getStackTrace(); 120 121 if (s.length >= 1) { 122 StackTraceElement parentStack = s[0]; 123 LOGGER.error("发生异常 : 类名 >> {}, 函数名 >> {},问题产生行 >> {},类型 >> {}", 124 new Object[] { parentStack.getClassName(), parentStack.getMethodName(), 125 parentStack.getLineNumber(), e.getClass().getName() }); 126 } 127 throw e; 128 } 129 return object; 130 } 131 132 /** 133 * <配置后置返回通知,使用在方法aspect()上注册的切入点 134 * <p> 135 * 136 * @param joinPoint 切入点 137 * @see [类、类#方法、类#成员] 138 */ 139 @AfterReturning("aspect()") 140 public void afterReturn(JoinPoint joinPoint) { 141 // LOGGER.debug("afterReturn {}", joinPoint.getSignature().toString()); 142 } 143 144 /** 145 * 配置抛出异常后通知,使用在方法aspect()上注册的切入点 146 * 147 * @param joinPoint 切入点 148 * @param ex 异常 149 * @see [类、类#方法、类#成员] 150 */ 151 @AfterThrowing(pointcut = "aspect()", throwing = "ex") 152 public void afterThrow(JoinPoint joinPoint, Exception ex) { 153 // LOGGER.debug("afterThrow {}", joinPoint.getSignature().toString()); 154 } 155 }