spring统计接口访问时长(转)

转自:https://blog.csdn.net/lengyue309/article/details/82020420

 接口开发完以后,对其进行统计十分必要,监控接口的访问时长可以发现哪些接口需要优化,统计接口的访问次数可以发现哪些接口最受欢迎。

下面通过使用aop实现了一个简单的统计功能

复制代码
@Slf4j
@Component
@Aspect
public class ApiVisitStatistics {

    //统计请求的处理时间,每个线程是独立的
    ThreadLocal<Long> startTime = new ThreadLocal<>();
    //整个服务是唯一的
    public static final Map<String, Long> map = new ConcurrentHashMap<>();

    /**
     * 定义切面
     * - 此处代表com.example.api.client.controller包下的所有接口都会被统计
     */
    @Pointcut("execution(* com.example.api.client.controller..*.*(..))")
    public void pointCut() {

    }

    /**
     * 在接口原有的方法执行前,将会首先执行此处的代码
     */
    @Before("pointCut()")
    public void doBefore(JoinPoint joinPoint) throws Throwable {
        startTime.set(System.currentTimeMillis());
        //获取传入目标方法的参数
        Object[] args = joinPoint.getArgs();
        String className= joinPoint.getSignature().getDeclaringType().getSimpleName();
        String methodName=joinPoint.getSignature().getName();
        String key = className + "." + methodName;
        //计数:如果不存在key,就设置为0,如果存在就在基础上加1
        map.computeIfAbsent(key, s -> 0L);
        map.computeIfPresent(key, (s, aLong) -> aLong+1);


        //接收到请求,记录请求内容
        ServletRequestAttributes attributes = (ServletRequestAttributes) RequestContextHolder.getRequestAttributes();
        HttpServletRequest request = attributes.getRequest();
        //记录请求的内容
        log.info("Aspect_URL:" + request.getRequestURL().toString());
        log.info("Aspect_Method:" + request.getMethod());
        log.info("Api访问次数:"+key+"="+map.get(key));
    }

    /**
     * 只有正常返回才会执行此方法
     * 记录接口访问时长
     */
    @AfterReturning(returning = "returnVal", pointcut = "pointCut()")
    public void doAfterReturning(JoinPoint joinPoint, Object returnVal) {
        HttpServletRequest request = ((ServletRequestAttributes) RequestContextHolder.getRequestAttributes()).getRequest();
        log.info("方法执行时间:" + (System.currentTimeMillis() - startTime.get()));
        log.info("方法返回值:" + JSON.toJSONString(returnVal));

    }

    /**
     * 当接口报错时执行此方法
     */
    @AfterThrowing(pointcut = "pointCut()")
    public void doAfterThrowing(JoinPoint joinPoint) {
        HttpServletRequest request = ((ServletRequestAttributes) RequestContextHolder.getRequestAttributes()).getRequest();
        log.info("接口访问失败,URI:[{}], 耗费时间:[{}] ms", request.getRequestURI(), System.currentTimeMillis() - startTime.get());

    }
}
复制代码

 

posted @   Mars.wang  阅读(620)  评论(0编辑  收藏  举报
编辑推荐:
· AI与.NET技术实操系列:基于图像分类模型对图像进行分类
· go语言实现终端里的倒计时
· 如何编写易于单元测试的代码
· 10年+ .NET Coder 心语,封装的思维:从隐藏、稳定开始理解其本质意义
· .NET Core 中如何实现缓存的预热?
阅读排行:
· 25岁的心里话
· 闲置电脑爆改个人服务器(超详细) #公网映射 #Vmware虚拟网络编辑器
· 零经验选手,Compose 一天开发一款小游戏!
· 通过 API 将Deepseek响应流式内容输出到前端
· AI Agent开发,如何调用三方的API Function,是通过提示词来发起调用的吗
点击右上角即可分享
微信分享提示