Spring AOP 实现监控方法执行的时间+统计service中方法执行的时间

本文详细介绍了如何在SpringMVC项目中配置切面(AOP),包括配置文件的设置,切面类的实现,以及如何使用切点函数execution进行方法调用时间的统计。通过具体代码示例,展示了如何利用AspectJ进行方法调用时间的日志记录。

1.配置切面

打开切面!因为项目使用的SpringMVC,项目中的配置文件就配置的 <aop:aspectj-autoproxy proxy-target-class=“true”/> ,具体的配置内容如下:

<!--自动扫描-->
<context:component-scan base-package="your package name">
		<context:exclude-filter type="annotation"
			expression="org.springframework.stereotype.Controller" />
</context:component-scan>
<!--打开切面-->
<aop:aspectj-autoproxy proxy-target-class="true"/> 
<!--支持系统能够识别相应的注解 -->
<context:annotation-config></context:annotation-config>

2.切面类

package com.aebiz.b2b2c.webinterface.cart.util;
 
import org.apache.log4j.Logger;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.Signature;
import org.aspectj.lang.annotation.Around;
import org.aspectj.lang.annotation.Aspect;
import org.springframework.stereotype.Component;
 
/**
 *  使用Aspect统计方法调用的时间
 * @author dufy
 * @Date 2016-03-02
 * @version 1.0
 *
 */
 
@Aspect
@Component
public class LoggingAspect {
	//日志记录
	public Logger log = Logger.getLogger("reqTime_logger");
	
	/**
	 * 统计Service中方法调用的时间
	 * @param joinPoint
	 * @throws Throwable
	 */
	@Around("execution(* com.dufy..*Service.*(..))")
	public Object logServiceMethodAccess(ProceedingJoinPoint joinPoint) throws Throwable {
		long start = System.currentTimeMillis();
		Object object = joinPoint.proceed();
		long end = System.currentTimeMillis();
		long t = end - start;
		if(t>=1000){
			String tmp = joinPoint.getSignature().toString();
			log.info(String.format("class:%s,invoke_time:%s",tmp,t));
		}
		return object;
	}
}


具体的execution方法

切点函数execution()的使用
@Around("execution(* (…))") : execution()是一个切点函数, * (…)是该函数的参数,其格式为:
<访问权限>? 返回值类型 包名+类名+方法名(参数类型) <throws 异常类型声明>
@Around(“execution(* * (…))”) //all
@Around(“execution(public * * (…))”) //绑定方法的访问权限
@Around(“execution(public * * (…) throws RuntimeException)”) //绑定异常类型声明
@Around(“execution(public * * (…) throws RuntimeException+)”) //+代表当前类及其子类
@Around(“execution(int * (…))”) //绑定方法的返回值
@Around(“execution(Object+ * (…))”) //绑定方法的返回值
@Around(“execution(void save* (…))”) //绑定方法名,以save开头的方法
@Around(“execution(void m (…))”) //包含m的方法
@Around(“execution(void com.dufy.spring.service.. (…))”) //绑定包名+类名+方法名
@Around(“execution(void com.dufy.spring…Service.update* (…))”) //包名以com.sxt.spring开头的类名中包含Service的类中所有以update开关的方法
@Around(“execution(void ())") //绑定方法的参数
@Around("execution(void (String))") //绑定方法的参数
@Around("execution(void (…,String,…))") //只要有一个String类型的参数即可
@Around(“args(int,String)”)
@Around("execution(
save
(…)) || execution(
update*(…))”) //切点运算 (||,or,&&,and)
@Around(“execution(* save*(…)) or execution(* update*(…))”) //切点运算

转自:https://blog.youkuaiyun.com/u010648555/article/details/50812135

### 使用 Spring AOP 实现接口调用链路中每个方法执行时间统计实现对接口调用链路中每个方法执行时间统计,可以通过 SpringAOP 功能来完成。以下是具体的实现方式: #### 1. 创建自定义注解 首先,可以创建一个自定义注解用于标记需要统计执行时间方法。 ```java import java.lang.annotation.ElementType; import java.lang.annotation.Retention; import java.lang.annotation.RetentionPolicy; import java.lang.annotation.Target; @Target(ElementType.METHOD) @Retention(RetentionPolicy.RUNTIME) public @interface TrackExecutionTime { String value() default ""; } ``` 此注解 `TrackExecutionTime` 可以附加到任何需要监控执行时间方法上[^4]。 --- #### 2. 编写切面类 接着,编写一个切面类(Aspect),利用 Spring AOP 对带有 `@TrackExecutionTime` 注解的方法进行拦截,并记录它们的执行时间。 ```java import org.aspectj.lang.ProceedingJoinPoint; import org.aspectj.lang.annotation.Around; import org.aspectj.lang.annotation.Aspect; import org.springframework.stereotype.Component; @Aspect @Component public class ExecutionTimeTracker { @Around("@annotation(TrackExecutionTime)") public Object trackExecutionTime(ProceedingJoinPoint joinPoint) throws Throwable { long startTime = System.nanoTime(); // 开始时间 try { return joinPoint.proceed(); } finally { long endTime = System.nanoTime(); // 结束时间 long duration = (endTime - startTime) / 1_000_000; // 转换为毫秒 String methodName = joinPoint.getSignature().toShortString(); System.out.println(methodName + " 执行时间为:" + duration + " ms"); } } } ``` 在这个切面类中,使用了 `@Around` 切点表达式来捕获所有被 `@TrackExecutionTime` 注解标注的方法。通过计算 `System.nanoTime()` 差值获取方法的实际运行时间,并打印出来[^5]。 --- #### 3. 配置 Spring AOP 支持 确保项目中的 Spring 配置文件启用了 AOP 支持。如果是基于 Java Config,则可以在配置类中标记 `@EnableAspectJAutoProxy`。 ```java import org.springframework.context.annotation.Configuration; import org.springframework.context.annotation.EnableAspectJAutoProxy; @Configuration @EnableAspectJAutoProxy public class AppConfig { // 其他 bean 配置... } ``` 启用自动代理功能后,Spring 将负责为目标对象生成代理实例并应用切面逻辑[^6]。 --- #### 4. 测试代码 最后,在业务层的一个服务类中添加测试方法,并为其加上 `@TrackExecutionTime` 注解。 ```java import org.springframework.stereotype.Service; @Service public class MyService { @TrackExecutionTime(value = "testMethod") public void performTask() { try { Thread.sleep(200); // 模拟耗时操作 } catch (InterruptedException e) { throw new RuntimeException(e); } } } ``` 当调用 `performTask()` 方法时,控制台将会输出类似如下日志: ``` MyService.performTask() 执行时间为:208 ms ``` --- ### 总结 以上方案展示了如何借助 Spring AOP 和自定义注解轻松实现对特定方法执行时间的跟踪和统计。这种方法不仅简单易懂,还具有高度可扩展性和灵活性,能够满足大多数实际开发需求[^7]。 ---
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值