项目文件夹

文件
wehub-resource-sync f3d80b4628
Auto Release / auto-release (push) Failing after 1s
CI / lint (push) Failing after 0s
CI / screenshot-quality (push) Failing after 3s
CI / pr-policy (push) Has been skipped
CI / test (3.11) (push) Failing after 0s
CI / test (3.12) (push) Failing after 0s
CI / test (3.13) (push) Failing after 3s
CI / coverage (push) Failing after 1s
Legibility / legibility (push) Failing after 3s
chore: import upstream snapshot with attribution
2026-07-13 12:31:48 +08:00

461 行
14 KiB
HTML

此文件含有模棱两可的 Unicode 字符
此文件含有可能会与其他字符混淆的 Unicode 字符。 如果您是想特意这样的,可以安全地忽略该警告。 使用 Escape 按钮显示他们。
<!doctype html>
<html lang="zh-Hans">
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1">
<title>本地 AI Agent Trace Viewer 指南 - claude-tap</title>
<meta
name="description"
content="使用 claude-tap 在本地查看 Claude Code、Codex、OpenAI Responses API、Gemini 和其他 AI 编程 Agent traces。"
>
<link rel="canonical" href="https://liaohch3.com/claude-tap/guides/agent-trace-viewer.zh.html">
<link rel="alternate" hreflang="en" href="https://liaohch3.com/claude-tap/guides/agent-trace-viewer.html">
<link rel="alternate" hreflang="zh-Hans" href="https://liaohch3.com/claude-tap/guides/agent-trace-viewer.zh.html">
<link rel="alternate" hreflang="x-default" href="https://liaohch3.com/claude-tap/guides/agent-trace-viewer.html">
<style>
:root {
--color-bg: #f4f7fb;
--color-panel: #ffffff;
--color-ink: #111827;
--color-muted: #5f6f84;
--color-line: #dce5ef;
--color-blue: #2563eb;
--color-blue-soft: #dbeafe;
--color-shadow: rgba(26, 43, 68, 0.12);
--font-sans: ui-sans-serif, system-ui, -apple-system, BlinkMacSystemFont, "Segoe UI", sans-serif;
--font-mono: ui-monospace, SFMono-Regular, Menlo, Monaco, Consolas, "Liberation Mono", monospace;
--space-2: 0.5rem;
--space-3: 0.75rem;
--space-4: 1rem;
--space-5: 1.25rem;
--space-6: 1.5rem;
--space-8: 2rem;
--space-10: 2.5rem;
--space-12: 3rem;
--space-16: 4rem;
--radius: 8px;
}
* {
box-sizing: border-box;
}
html,
body {
margin: 0;
overflow-x: clip;
}
body {
background: var(--color-bg);
color: var(--color-ink);
font-family: var(--font-sans);
line-height: 1.75;
}
a {
color: inherit;
}
img {
display: block;
max-width: 100%;
}
.shell {
width: min(1040px, calc(100% - 32px));
margin: 0 auto;
}
.topbar {
background: rgba(244, 247, 251, 0.92);
border-bottom: 1px solid var(--color-line);
position: sticky;
top: 0;
z-index: 10;
backdrop-filter: blur(14px);
}
.topbar-inner {
align-items: center;
display: flex;
gap: var(--space-4);
justify-content: space-between;
min-height: 68px;
}
.brand {
align-items: center;
display: flex;
gap: var(--space-3);
text-decoration: none;
}
.brand-mark {
align-items: center;
background: var(--color-ink);
border-radius: 6px;
color: #fff;
display: inline-flex;
font-family: var(--font-mono);
font-size: 0.92rem;
font-weight: 700;
height: 34px;
justify-content: center;
width: 34px;
}
.nav {
align-items: center;
display: flex;
gap: var(--space-4);
font-size: 0.94rem;
white-space: nowrap;
}
.nav a {
color: var(--color-muted);
text-decoration: none;
}
.nav .primary {
background: var(--color-ink);
border-radius: 999px;
color: #fff;
padding: 0.58rem 0.92rem;
}
.hero {
padding: var(--space-16) 0 var(--space-10);
}
.eyebrow {
color: var(--color-blue);
font-size: 0.84rem;
font-weight: 700;
margin: 0 0 var(--space-4);
text-transform: uppercase;
}
h1 {
font-size: clamp(2.65rem, 7vw, 5.5rem);
letter-spacing: 0;
line-height: 0.98;
margin: 0;
max-width: 12ch;
overflow-wrap: anywhere;
}
.lead {
color: var(--color-muted);
font-size: clamp(1.04rem, 2vw, 1.24rem);
margin: var(--space-6) 0 0;
max-width: 68ch;
}
.hero-actions {
display: flex;
flex-wrap: wrap;
gap: var(--space-3);
margin-top: var(--space-8);
}
.button {
align-items: center;
border: 1px solid var(--color-line);
border-radius: 999px;
display: inline-flex;
font-weight: 700;
justify-content: center;
min-height: 44px;
padding: 0.72rem 1rem;
text-decoration: none;
white-space: nowrap;
}
.button.dark {
background: var(--color-ink);
border-color: var(--color-ink);
color: #fff;
}
.button.light {
background: var(--color-panel);
color: var(--color-ink);
}
.article-grid {
display: grid;
gap: var(--space-8);
grid-template-columns: minmax(0, 220px) minmax(0, 1fr);
padding-bottom: var(--space-16);
}
.toc {
align-self: start;
background: var(--color-panel);
border: 1px solid var(--color-line);
border-radius: var(--radius);
padding: var(--space-5);
position: sticky;
top: 92px;
}
.toc strong {
display: block;
font-size: 0.9rem;
margin-bottom: var(--space-3);
}
.toc a {
color: var(--color-muted);
display: block;
font-size: 0.92rem;
padding: 0.32rem 0;
text-decoration: none;
}
article {
background: var(--color-panel);
border: 1px solid var(--color-line);
border-radius: var(--radius);
box-shadow: 0 24px 60px var(--color-shadow);
padding: var(--space-10);
}
article > *:first-child {
margin-top: 0;
}
h2 {
font-size: clamp(1.7rem, 3vw, 2.5rem);
line-height: 1.08;
margin: var(--space-12) 0 var(--space-4);
overflow-wrap: anywhere;
}
p,
li {
color: var(--color-muted);
}
ul {
padding-left: 1.25rem;
}
pre {
background: #0e1726;
border: 1px solid #1f2f46;
border-radius: var(--radius);
color: #d8e7ff;
font-family: var(--font-mono);
overflow: auto;
padding: var(--space-5);
}
code {
font-family: var(--font-mono);
}
.note {
background: var(--color-blue-soft);
border: 1px solid #bfdbfe;
border-radius: var(--radius);
color: #1e3a8a;
padding: var(--space-5);
}
figure {
margin: var(--space-8) 0;
}
figure img {
border: 1px solid var(--color-line);
border-radius: var(--radius);
}
figcaption {
color: var(--color-muted);
font-size: 0.92rem;
margin-top: var(--space-3);
}
.footer {
color: var(--color-muted);
padding: var(--space-8) 0;
}
@media (max-width: 860px) {
.article-grid {
grid-template-columns: 1fr;
}
.toc {
position: static;
}
.nav a:not(.primary):not(.lang) {
display: none;
}
}
@media (max-width: 520px) {
.shell {
width: min(100% - 24px, 1040px);
}
h1 {
font-size: clamp(2.4rem, 18vw, 4rem);
}
article {
padding: var(--space-6);
}
.button {
width: 100%;
}
}
</style>
</head>
<body>
<header class="topbar">
<div class="shell topbar-inner">
<a class="brand" href="../index.zh.html"><span class="brand-mark">ct</span><strong>claude-tap</strong></a>
<nav class="nav" aria-label="主导航">
<a href="../index.zh.html">首页</a>
<a href="../support-matrix.zh.html">客户端</a>
<a class="lang" href="agent-trace-viewer.html">English</a>
<a class="primary" href="https://github.com/liaohch3/claude-tap">GitHub</a>
</nav>
</div>
</header>
<main>
<section class="hero">
<div class="shell">
<p class="eyebrow">指南</p>
<h1>本地 AI Agent Trace Viewer</h1>
<p class="lead">
使用 claude-tap 在本地查看 Claude Code、Codex、OpenAI Responses API、Gemini 和其他 AI 编程 Agent traces。
</p>
<div class="hero-actions">
<a class="button dark" href="https://github.com/liaohch3/claude-tap">打开 GitHub</a>
<a class="button light" href="../index.zh.html">返回概览</a>
</div>
</div>
</section>
<div class="shell article-grid">
<aside class="toc" aria-label="指南章节">
<strong>章节</strong>
<a href="#what-is-a-trace">什么是 trace?</a>
<a href="#local">为什么本地查看?</a>
<a href="#supported">支持的客户端</a>
<a href="#how">如何查看</a>
<a href="#inspect">先看什么</a>
<a href="#export">HTML 导出</a>
</aside>
<article>
<p>
<code>claude-tap</code> 是面向 AI 编程 Agent 的本地 trace viewer 和 HTML 导出工具。它可以查看 prompt、工具调用、token 用量、延迟、流式响应、请求 diff 和原始 API 请求结构,不需要把私有运行记录上传到云端 dashboard。
</p>
<figure>
<img src="../viewer-zh.png" alt="claude-tap 本地 AI agent trace viewer,展示请求、工具调用、token 用量和延迟">
<figcaption>面向真实 agent session 的本地 viewer,而不是从终端日志反推出来的记录。</figcaption>
</figure>
<h2 id="what-is-a-trace">什么是 AI agent trace?</h2>
<p>AI agent trace 是一次 agent 运行背后的请求和响应链路记录。对于编程 Agent,一个有用的 trace 通常包括:</p>
<ul>
<li>System prompt 和对话历史</li>
<li>工具 schema、工具调用、工具输入和工具结果</li>
<li>重建后的流式响应内容</li>
<li>Token 用量、cache 用量和延迟</li>
<li>相邻轮次之间的请求 diff</li>
</ul>
<p>终端显示 agent 说了什么;trace 显示 agent 实际发出了什么。</p>
<h2 id="local">为什么要本地查看 trace?</h2>
<p>
很多 observability 产品适合生产系统,但本地调试的目标不同。当编程 Agent 接触私有代码、私有 prompt、仓库元数据或内部工具时,最稳妥的默认方式是在自己的机器上检查 trace。
</p>
<p class="note">
claude-tap 默认把 trace session 留在本地。常见认证 header 会在记录前脱敏,导出的 HTML 文件也是由你自己控制的静态 artifact。
</p>
<h2 id="supported">支持的 traces 和客户端</h2>
<p>claude-tap 可以追踪和查看这些客户端的会话:</p>
<ul>
<li>Claude Code</li>
<li>Codex CLI</li>
<li>Codex App</li>
<li>Gemini CLI</li>
<li>Cursor CLI</li>
<li>OpenCode</li>
<li>Kimi CLI</li>
<li>Pi</li>
<li>Hermes Agent</li>
<li>Qoder CLI</li>
<li>Antigravity CLI</li>
<li>CodeBuddy CLI</li>
</ul>
<p>它也支持 Anthropic Messages、OpenAI Responses、OpenAI Chat Completions、Gemini 和 Claude 兼容网关等 trace 形态。</p>
<h2 id="how">如何查看 trace</h2>
<p>安装 claude-tap</p>
<pre><code>uv tool install claude-tap</code></pre>
<p>通过 claude-tap 启动客户端:</p>
<pre><code># Claude Code
claude-tap
# Codex CLI
claude-tap --tap-client codex
# Codex App 本地会话监听
claude-tap --tap-client codexapp
# Gemini CLI
claude-tap --tap-client gemini -- -p "hello"</code></pre>
<p>打开本地 dashboard,或导出独立 HTML 文件:</p>
<pre><code>claude-tap export trace.jsonl --format html</code></pre>
<h2 id="inspect">先看哪些内容?</h2>
<ul>
<li>Agent 是否收到了你预期的 prompt 和上下文?</li>
<li>多轮之间工具 schema 是否发生了变化?</li>
<li>Agent 是否用正确参数调用了正确工具?</li>
<li>Token 增长来自历史、工具结果,还是重复上下文?</li>
<li>延迟来自模型调用、工具调用,还是很长的流式响应?</li>
</ul>
<h2>Claude trace viewer</h2>
<p>
对于 Claude Code 和 Anthropic 兼容流量,claude-tap 可以展示 Anthropic Messages 请求、工具调用、流式响应、token 用量和 Claude 兼容网关元数据。
</p>
<h2>Codex trace viewer</h2>
<p>
对于 Codex CLI,claude-tap 支持 OpenAI API key 模式和 ChatGPT 订阅 OAuth 模式。对于 Codex App,它会监听 CODEX_HOME 或 ~/.codex 下的本地 session JSONL 文件。它可以查看 OpenAI Responses API 流量、WebSocket 记录、本地 transcript 记录、工具调用、reasoning/output 区块、token 用量和请求 diff。
</p>
<h2 id="export">导出 trace 到 HTML</h2>
<p>HTML 导出适合生成可移植的 review artifact</p>
<ul>
<li>和其他 maintainer 分享一次调试运行</li>
<li>给 pull request 附上证据</li>
<li>归档一次模型行为回归</li>
<li>在 prompt 或工具变更期间对比相邻请求</li>
</ul>
<p>
当你需要快速检查私有 agent runs 时,适合使用本地 trace viewer。当你需要生产监控、团队 dashboard、告警或长期遥测时,适合使用托管 observability。
</p>
</article>
</div>
</main>
<footer class="footer"><div class="shell">claude-tap 是 MIT 协议开源项目。</div></footer>
</body>
</html>