不能。pinpoint仅监控到类+方法签名粒度的框架/中间件入口调用,不自动采集任意java方法耗时;需手动加@trace注解并满足多项前提条件才能实现细粒度追踪。

Pinpoint agent 能否直接定位到 Java 方法级别耗时?
不能。Pinpoint 本身不采集单个方法的执行耗时,它只监控到类+方法签名(如 com.example.service.UserService.login)粒度的调用统计,且依赖于「被拦截的入口方法」——比如 Spring Controller、RPC 接口、DataSource 执行点。它不会自动埋点每个 private 方法或工具类方法。
这意味着:你看到的「慢方法」其实是被 Pinpoint 主动插桩的框架/中间件入口,不是任意 Java 方法。想定位到真正耗时的内部方法(比如某个 for 循环或 JSON 解析),得靠其他手段配合。
如何让 Pinpoint 显示更细粒度的方法调用?
必须手动加 @Trace 注解(需引入 pinpoint-trace-api 依赖),并确保该方法被 Pinpoint agent 的字节码增强逻辑捕获。这不是开箱即用的功能,有明确前提:
-
@Trace只对 public 实例方法生效,static、private、final 方法会被跳过 - 目标类不能是 JDK 类或被
bootstrap classloader加载(否则 agent 不会增强) - 必须启用
profiler.annotation.enable=true(在pinpoint.config中配置) - 注解所在模块的 classpath 必须能被 Pinpoint agent 的 classloader 看到(常见坑:打成 fat jar 后
pinpoint-trace-api冲突或缺失)
示例:
@Trace
public String processOrder(Order order) {
// 这里会被 Pinpoint 记为一个独立 span
return buildResponse(order);
}
为什么在 Pinpoint UI 看不到自己加的 @Trace 方法?
最常见原因是字节码未被增强,而非注解写错了。排查顺序如下:
- 检查应用启动日志是否含
TraceClassLoadEventListener onTransform,确认 agent 正在尝试增强你的类 - 用
jcmd <pid> VM.native_memory summary</pid>或jstat -class <pid></pid>观察类加载数量是否异常偏低(可能因 classloader 隔离导致 agent 失效) - 临时在目标方法第一行加
System.out.println("trace test");,看是否执行——若没输出,说明方法根本没被调用或被优化掉了(如被 Spring AOP 代理绕过) - 确认没有和
spring-aop、byte-buddy等其他 agent 冲突(Pinpoint 不兼容多数同类字节码工具)
真正要定位方法级热点,该用什么替代方案?
Pinpoint 是链路追踪工具,不是 profiler。遇到「不知道哪行代码慢」的场景,优先用:
-
async-profiler:attach 到进程,采样 CPU/alloc,输出火焰图,能精准到行号。命令示例:./profiler.sh -e cpu -d 30 -f profile.html <pid></pid> -
jstack+arthas:arthas的watch和trace命令可动态观测方法耗时,无需重启,适合临时诊断 - 结合使用:先用 Pinpoint 发现慢接口 → 用 async-profiler 抓该接口压测时的 CPU 火焰图 → 定位到具体方法甚至循环体内部
别指望 Pinpoint 替代 profiler。它的优势在于跨服务调用上下文串联,而不是单机方法级性能剖析。
Java免费学习笔记:立即使用
解锁 Java 大师之旅:从入门到精通的终极指南











