用途
GrepAI Trace Graph 用于构建完整的调用图,递归展示函数之间的依赖关系。它适合以下场景:
- 映射完整的函数依赖
- 理解复杂的代码流程
- 为大型重构做影响分析
- 可视化应用架构
主要能力
grepai trace graph 会构建一棵递归的依赖树。例如:
main
├── initialize
│ ├── loadConfig
│ │ └── parseYAML
│ └── connectDB
│ ├── createPool
│ └── ping
├── startServer
│ ├── registerRoutes
│ │ ├── authMiddleware
│ │ └── loggingMiddleware
│ └── listen
└── gracefulShutdown
└── closeDB
深度控制
使用 --depth 限制递归深度:
# 默认深度(2 层)
grepai trace graph "main"
# 更深分析(3 层)
grepai trace graph "main" --depth 3
# 浅层(1 层,等同于 callees)
grepai trace graph "main" --depth 1
# 非常深(5 层)
grepai trace graph "main" --depth 5
输出格式
支持 JSON 输出:
grepai trace graph "main" --depth 2 --json
紧凑 JSON:
grepai trace graph "main" --depth 2 --json --compact
TOON 输出(v0.26.0+),相比 JSON 可减少约 50% 的 token:
grepai trace graph "main" --depth 2 --toon
注意:--json 与 --toon 互斥。
提取模式
# 快速模式(基于正则)
grepai trace graph "main" --mode fast
# 精确模式(tree-sitter AST)
grepai trace graph "main" --mode precise
循环依赖处理
GrepAI 会检测并标记循环依赖:
main
├── processA
│ └── processB
│ └── processA [CYCLE]
在 JSON 中表现为 "cycle": true。
使用方式
基本用法:
grepai trace graph "FunctionName"
示例:
grepai trace graph "main"
输出示例:
🔍 Call Graph for "main"
main
├── initialize
│ ├── loadConfig
│ └── connectDB
├── startServer
│ ├── registerRoutes
│ └── listen
└── gracefulShutdown
└── closeDB
Nodes: 9
Max depth: 3
典型使用场景
理解应用流程:
grepai trace graph "main" --depth 4
影响分析:
# 哪些地方依赖这个工具函数?
grepai trace graph "validateInput" --depth 3
# 修改数据库层的完整影响
grepai trace graph "executeQuery" --depth 2
代码审查:
# 这个函数是否过于复杂?
grepai trace graph "processOrder" --depth 5
# 节点越多 = 复杂度越高
文档生成:
# 生成架构图数据
grepai trace graph "main" --depth 3 --json > architecture.json
重构规划:
# 如果修改这里会破坏什么?
grepai trace graph "legacyAuth" --depth 3
可视化
导出为 DOT 格式(Graphviz):
grepai trace graph "main" --depth 3 --json | python3 << 'EOF'
import json
import sys
data = json.load(sys.stdin)
print("digraph G {")
print(" rankdir=TB;")
def traverse(node, parent=None):
name = node.get('name') or node.get('n')
if parent:
print(f' "{parent}" -> "{name}";')
children = node.get('children') or node.get('c') or []
for child in children:
traverse(child, name)
traverse(data.get('root') or data.get('r'))
print("}")
EOF
然后渲染:
dot -Tpng graph.dot -o graph.png
Mermaid 图:
grepai trace graph "main" --depth 2 --json | python3 << 'EOF'
import json
import sys
data = json.load(sys.stdin)
print("```mermaid")
print("graph TD")
def traverse(node, parent=None):
name = node.get('name') or node.get('n')
if parent:
print(f" {parent} --> {name}")
children = node.get('children') or node.get('c') or []
for child in children:
traverse(child, name)
traverse(data.get('root') or data.get('r'))
print("```")
EOF
比较图规模
跟踪复杂度变化:
# 获取节点数量
grepai trace graph "main" --depth 3 --json | jq '.stats.nodes'
# 对比重构前后
echo "Before: $(grepai trace graph 'main' --depth 3 --json | jq '.stats.nodes') nodes"
# ... 重构 ...
echo "After: $(grepai trace graph 'main' --depth 3 --json | jq '.stats.nodes') nodes"
适用场景
- 理解应用启动流程
- 重构前的影响分析
- 代码审查中评估函数复杂度
- 生成架构文档数据
- 重构规划
限制与注意事项
常见问题
图过大或超时:
- 降低深度:
--depth 2 - 追踪特定函数而非 main
- 使用
--mode fast
检测到大量循环:
- 这表明代码中存在循环依赖,建议重构。
缺失分支:
- 尝试
--mode precise - 检查文件是否已建立索引
- 确认语言是否已启用
最佳实践
- 从浅层开始:先用
--depth 2,按需增加 - 聚焦分析:追踪特定函数,不必总是 main
- 导出用于文档:使用 JSON 生成图表
- 长期跟踪:将节点数量作为复杂度指标
- 调查循环:循环依赖是代码坏味道
输出格式说明
Trace graph 结果示例:
🔍 Call Graph for "main"
Depth: 3
Mode: fast
main
├── initialize
│ ├── loadConfig
│ │ └── parseYAML
│ └── connectDB
│ ├── createPool
│ └── ping
├── startServer
│ ├── registerRoutes
│ │ ├── authMiddleware
│ │ └── loggingMiddleware
│ └── listen
└── gracefulShutdown
└── closeDB
Statistics:
- Total nodes: 12
- Maximum depth reached: 3
- Cycles detected: 0
Tip: Use --json for machine-readable output
Use --depth N to control recursion depth