# AgentTeam Insight `graph` 接入面与 Go 模块边界盘点

> Thread: `#agentteam-in-agentteam:c18d01cc`
> Task: `#t1467`
> Scope: 只做 AgentTeam Insight 侧接入面、前端 graph 消费契约、Go package 边界、worktree/验证 gate 调研；不改业务代码。
> Baseline: `/Users/lonng/devel/pingcap/agentteam/.worktrees/codex2-agentteam-insight-graph-builder-scan` at `6496f571ed5c` (`origin/main`).

## 1. 结论摘要

`agentteam-insight graph` 应作为 `kits/agentteam-insight` 的公开顶层命令之一，与 `wiki` 并列；最终 CLI 不再暴露 `analyze`。Graph Builder 不应复用历史 `codeanalysis` 的 markdown 输出链路来“拼” graph。

原因：历史 `kits/agentteam-insight/internal/codeanalysis` 是“按目录模块分批调用 OpenCode，写 `<source_path>.md` 分析文档”的系统；Graph Builder 的核心产物则是 `.agentteam-insight/knowledge-graph.json` + `meta.json` + `fingerprints.json` + `config.json`，并要求节点/边/layer/tour schema 通过兼容 validator。

因此实施时应新增一条 Go 组织方式清晰的 `internal/graphbuilder` 模块树：

- CLI 只负责参数解析和调用 orchestrator；
- pipeline/orchestrator 负责编排 full/incremental；
- scanner/importgraph/batcher/extractor/fingerprint/assembler/persistence/schema 各自独立；
- LLM/agent 阶段作为 `agent` 子包，复用现有 `opencoderuntime` 隔离运行方式，但输出必须是 UA-compatible batch graph，而不是 markdown。

## 2. 当前 AgentTeam Insight 存量

### 2.1 CLI 入口

入口在 `kits/agentteam-insight/main.go`：

- `agentteam-insight graph --input <input-repo> --output <output-repo> ...`
- `agentteam-insight wiki --input <input-repo-or-insight-output> --output <wiki-repo> ...`

实现方式：

- `run()` 用首个参数分发子命令；
- `parseGraphOptions()` / `parseWikiOptions()` 解析 flags；
- `commandRunners` 注入 runner，测试可替换；
- `main_test.go` 已覆盖 CLI option 透传、OpenCode runner 注入、输出摘要。

`graph` 最小接入点：

```text
kits/agentteam-insight/main.go
  commandRunners 增加 graph graphbuilder.CommandRunner
  printUsage 增加 agentteam-insight graph ...
  run() 增加 case "graph"
  parseGraphOptions() 返回 graphbuilder.Options
  runGraph() 调 graphbuilder.Run(ctx, options, runner)
```

### 2.2 `codeanalysis` 不是 graph pipeline

`kits/agentteam-insight/internal/codeanalysis` 当前职责：

- `discover.go`：扫描源文件/copy-only 文件，带目录忽略、manifest/natural-language/source 扩展分类；
- `module_plan.go` / `task.go`：按目录形成 `ModulePlan` 和 `ModuleTaskManifest`；
- `analyzer.go`：创建 `.code-analysis/run-*`，并发执行 OpenCode module tasks；
- worker 输出：`outputRoot/<source_path>.md`，schema 是 `code-research.file.v1`；
- prompt 明确要求“每个 direct file 写 markdown artifact”。

可复用点：

- runner 注入模式；
- `opencoderuntime.Prepare()`；
- progress logger 风格；
- output-language flag 规则；
- isolated OpenCode runtime 与 `--jobs > 1` 约束。

不可直接复用点：

- module plan 粒度是 folder module，不是 UA import-graph semantic batches；
- artifact 是 markdown，不是 GraphNode/GraphEdge batch JSON；
- 没有 import map、neighborMap、merge-batch-graphs、layers/tour/fingerprint/change-classifier。

### 2.3 `codewiki` 是二阶段 wiki 生成，不是 dashboard graph

`kits/agentteam-insight/internal/codewiki` 当前职责：

- `Generate()` 读取 source 或 analysis repo；
- 先规划 wiki pages，再逐页调用 OpenCode；
- 输出 markdown wiki 到 `outputRoot`；
- schema 是 `code-wiki.plan.v3`。

它适合继续服务 KB insights wiki，不应承担 UA graph 生成。

### 2.4 MeshX/Web 发布面同步目标

当前产品链路里已有“code wiki / repository graph building”概念，但不是 Graph Builder artifact contract 本身。#t1504 拆分后，前端/Web 子批负责把公开预设与 KB progress 文案同步到 AgentTeam Insight：

- `web/src/meshx/components/automations/automationRepositoryFiles.ts` 生成 automation preset：
  - `agentteam-insight graph --input source --output kb/insights ...`
  - `agentteam-insight wiki --input source --input kb/insights --output wiki ...`
- `specs/kb/repository-import-progress.md` 使用 `generating_insight_graph` 表示“Building the insight graph and generating repository wiki content”。
- `meshx/internal/service/kb/kb_import_progress.go` 解析 code-wiki progress payload。
- `internal/forwarder/routes_test.go` 透传 `/repositories/.../code-wiki/generate`。

这些是 KB insights/wiki 产品线；`agentteam-insight graph` 可以后续接入 KB insight graph 阶段，但首版应先做到本地/CI 可生成 compatibility-safe `.agentteam-insight` 文件。

## 3. Graph JSON 兼容消费契约

### 3.1 文件名和目录必须兼容

UA dashboard 直接读取这些文件：

- required: `.agentteam-insight/knowledge-graph.json`
- optional: `.agentteam-insight/meta.json`
- optional: `.agentteam-insight/config.json`
- optional: `.agentteam-insight/domain-graph.json`
- optional: `.agentteam-insight/diff-overlay.json`

注意：用户口语里的 `Graph.json` 要落成 UA 实际文件名 `knowledge-graph.json`，否则现有前端不会自动识别。

Dashboard 的 Vite server 查找规则（`packages/dashboard/vite.config.ts`）：

1. 如果设置 `GRAPH_DIR=<projectRoot>`，读 `GRAPH_DIR/.agentteam-insight/<file>`；
2. 否则读当前工作目录 `.agentteam-insight/<file>`；
3. 再 fallback 到 `../../../.agentteam-insight/<file>`。

因此 `agentteam-insight graph --input <repo>` 默认应写入：

```text
<input-repo>/.agentteam-insight/knowledge-graph.json
<input-repo>/.agentteam-insight/meta.json
<input-repo>/.agentteam-insight/fingerprints.json
<input-repo>/.agentteam-insight/config.json
```

可增加 `--output <project-root-or-graph-root>`，但要明确如果目标是兼容 dashboard，`--output` 表示 project root，而不是直接的 `.agentteam-insight` 目录；或命名为 `--graph-root` 避免歧义。

### 3.2 `knowledge-graph.json` schema

核心类型来自 `understand-anything-plugin/packages/core/src/types.ts` 和 `schema.ts`。

Root：

```json
{
  "version": "1.0.0",
  "kind": "codebase",
  "project": {
    "name": "...",
    "languages": ["go", "typescript"],
    "frameworks": ["..."],
    "description": "...",
    "analyzedAt": "2026-07-02T00:00:00Z",
    "gitCommitHash": "..."
  },
  "nodes": [],
  "edges": [],
  "layers": [],
  "tour": []
}
```

Node 必填字段：

- `id`
- `type`
- `name`
- `summary`
- `tags`
- `complexity`

Node 可选字段：

- `filePath`（必须持久化为相对路径，避免泄露本地路径）
- `lineRange`
- `languageNotes`
- `domainMeta`
- `knowledgeMeta`

允许 node type（以 UA `packages/core/src/schema.ts` 为准）：

```text
file,function,class,module,concept,
config,document,service,table,endpoint,pipeline,schema,resource,
domain,flow,step,
article,entity,topic,claim,source
```

Edge 必填字段：

- `source`
- `target`
- `type`
- `direction` = `forward|backward|bidirectional`
- `weight` in `[0,1]`

允许 edge type：

```text
imports,exports,contains,inherits,implements,
calls,subscribes,publishes,middleware,
reads_from,writes_to,transforms,validates,
depends_on,tested_by,configures,
related,similar_to,
deploys,serves,provisions,triggers,migrates,documents,routes,defines_schema,
contains_flow,flow_step,cross_domain,
cites,contradicts,builds_on,exemplifies,categorized_under,authored_by
```

Layer 必填：`id,name,description,nodeIds[]`。
Tour 必填：`order,title,description,nodeIds[]`；`languageLesson` 可选。

### 3.3 Validator 行为也要复刻或测试覆盖

UA validator 会：

- sanitize null collections：`tour/layers` null → `[]`；
- normalize node/edge aliases；
- auto-fix 缺失 `type/complexity/tags/summary`；
- auto-fix `direction/weight`；
- drop invalid node/edge/layer/tour；
- edge source/target 不存在会被 drop；
- 没有有效 node 是 fatal。

AgentTeam Insight Go 侧至少要有同构 validator/normalizer，不能只依赖前端容错。验收还应把 Go 生成的 fixture graph 交给 UA `validateGraph()` 跑一遍。

### 3.4 `meta/config/fingerprints` 契约

`meta.json`（UA `AnalysisMeta`）：

写入顺序注意：UA 增量逻辑要求 **先写 `fingerprints.json`，再写 `meta.json`**。否则下一次运行可能看到新 `meta.gitCommitHash` 但没有对应 fingerprint baseline，导致增量退化成 full update。


```json
{
  "lastAnalyzedAt": "ISO time",
  "gitCommitHash": "...",
  "version": "1.0.0",
  "analyzedFiles": 123,
  "theme": { "presetId": "...", "accentId": "..." }
}
```

`config.json`（UA `ProjectConfig`）：

```json
{ "autoUpdate": false, "outputLanguage": "en" }
```

`fingerprints.json`（UA `FingerprintStore`）：

```json
{
  "version": "1.0.0",
  "gitCommitHash": "...",
  "generatedAt": "ISO time",
  "files": {
    "relative/path.go": {
      "filePath": "relative/path.go",
      "contentHash": "sha256 hex",
      "functions": [],
      "classes": [],
      "imports": [],
      "exports": [],
      "totalLines": 42,
      "hasStructuralAnalysis": true
    }
  }
}
```

## 4. 建议的 Go package layout

建议新增 `kits/agentteam-insight/internal/graphbuilder`，不要把 UA 的 `skills/agents/packages` TS 目录机械搬进来。

```text
kits/agentteam-insight/
  main.go                         # 增加 graph 子命令解析，不放业务逻辑
  internal/
    graphbuilder/
      run.go                      # Run(ctx, Options, Runner)；full/incremental 总编排
      options.go                  # Options/Result/CommandRunner/Mode
      progress.go                 # [graph-builder] progress logger
      schema/                     # Go types + validation/normalization，镜像 UA graph schema
        graph.go
        validate.go
        aliases.go
      persistence/                # .agentteam-insight 文件读写 + path sanitization
        store.go
        paths.go
      scanner/                    # 文件枚举、.agentteam-insightignore、语言/类别/行数、git meta
        scanner.go
        ignore.go
        language.go
      extractor/                  # 结构抽取统一 interface + concrete extractors
        extractor.go
        golang/
        typescript/
        generic/
        noncode/
      importgraph/                # import resolution、internal edge、exported symbols
        graph.go
      batching/                   # semantic batches + neighborMap
        batches.go
      fingerprint/                # content hash、structural fingerprint、change classifier
        store.go
        compare.go
        classify.go
      agent/                      # OpenCode/agent dispatch；prompt assets 用 embed.FS
        runner.go
        prompts/
          file_analyzer.md
          architecture_analyzer.md
          tour_builder.md
          assemble_reviewer.md
      assembler/                  # merge batch graphs、normalize ids、dedupe、tested_by fixer
        merge.go
        normalize.go
      layers/                     # architecture output normalizer
        normalize.go
      tour/                       # tour output normalizer
        normalize.go
      testdata/
        fixtures/
```

依赖方向：

```text
main -> internal/graphbuilder
graphbuilder -> scanner, extractor, importgraph, batching, fingerprint, agent, assembler, layers, tour, persistence, schema
scanner -> schema?（尽量只返回 scanner 自己的 FileInfo，避免过早绑定 graph）
extractor -> schema?（返回 StructuralAnalysis；由 assembler/graphbuilder 转 GraphNode/GraphEdge）
assembler -> schema
persistence -> schema + fingerprint
agent -> schema + opencoderuntime
leaf packages 不反向依赖 graphbuilder/run 或 main
```

建议避免：

- `internal/graphbuilder/ua` 单包塞所有逻辑；
- 在 `codeanalysis` 里追加 graph 输出，导致 markdown analysis 和 UA graph pipeline 混在一起；
- 让 `persistence` 依赖 `agent` 或让 `schema` 依赖任何 runtime；
- 把 prompt/agent markdown 当目录结构主轴。prompt 是 `agent` package 的资源，不是模块边界。

## 5. `graph` 子命令建议形态

首版 CLI：

```bash
agentteam-insight graph --input <repo> [--output <repo-or-output-root>] [--mode full|incremental|auto] [--jobs N] [--output-language LANG] [--review] [--isolate-opencode-runtime] [--model provider/model]
```

建议语义：

- `--input`：待分析仓库，必填；
- `--output`：默认等于 `--input`；写 `<output>/.agentteam-insight/*`；
- `--mode full`：忽略旧 graph/fingerprint，全量生成；
- `--mode incremental`：要求已有 graph/fingerprints/meta，按 git commit diff + fingerprint 更新；
- `--mode auto`：存在可用 fingerprints 则 incremental，否则 full；
- `--output-language`：写入 `config.json`，用于 LLM 文本内容；
- `--review`：可选 LLM graph-reviewer；默认走 deterministic validation；
- `--jobs > 1` 继续沿用现有约束：必须 `--isolate-opencode-runtime`。

输出 stdout 摘要类似：

```text
generated knowledge graph: 123 files, 456 nodes, 789 edges, 6 layers, 8 tour steps; graph: <repo>/.agentteam-insight/knowledge-graph.json
```

## 6. Full / Incremental pipeline 对 AgentTeam Insight 的落地边界

Planner 可把实现拆成以下阶段。

### 6.1 Full path 必须完整同构

1. Pre-flight：resolve input/output、git commit、config、worktree redirect 策略。
2. Ignore：生成/读取 `.agentteam-insightignore`。
3. Scan：文件列表、language、fileCategory、sizeLines、frameworks、project meta、importMap。
4. Batch：按 import graph 生成 batches + neighborMap。
5. Analyze：并发 agent 分批产出 batch GraphNode/GraphEdge。
6. Assemble：merge/normalize/dedupe/drop dangling/tested_by fixer。
7. Layers：架构层 agent + normalizer。
8. Tour：导览 agent + normalizer。
9. Validate：Go validator + UA validator compatibility gate。
10. Persist：`knowledge-graph.json`、`meta.json`、`fingerprints.json`、`config.json`。

### 6.2 Incremental path 的最小正确边界

1. 读取 `meta.gitCommitHash` / `fingerprints.gitCommitHash`。
2. `git diff <last>..HEAD --name-only` 得 changed/deleted/new。
3. 对现有文件重算 structural fingerprint。
4. classify：`SKIP|PARTIAL_UPDATE|ARCHITECTURE_UPDATE|FULL_UPDATE`。
5. PARTIAL：只重新分析 changed/new batches；删除旧 graph 中 changed/deleted file nodes 及相关 edges；写 `batch-existing.json` 与新 batches 一起 merge。
6. ARCHITECTURE：在 partial 基础上重跑 layers/tour。
7. FULL：回到 full path。
8. 保存新的 fingerprints/meta。

注意：UA 的 incremental 语义不是“只 append 新节点”，而是“先 prune 旧 changed file nodes/edges，再 merge existing + fresh batch”。这点需要在 Go assembler 测试里固定。

## 7. 前端识别与验收方式

### 7.1 最低兼容验收

给一个 fixture repo 运行：

```bash
cd kits/agentteam-insight
go run . graph --input <fixture-repo> --mode full --output <fixture-repo>
```

必须产生：

```text
<fixture-repo>/.agentteam-insight/knowledge-graph.json
<fixture-repo>/.agentteam-insight/meta.json
<fixture-repo>/.agentteam-insight/fingerprints.json
<fixture-repo>/.agentteam-insight/config.json
```

然后用 UA core validator 验证：

```bash
cd /Users/lonng/devel/ai/Understand-Anything/understand-anything-plugin/packages/core
pnpm build
node -e 'import("./dist/schema.js").then(({validateGraph})=>{const fs=require("fs"); const g=JSON.parse(fs.readFileSync(process.argv[1],"utf8")); const r=validateGraph(g); if(!r.success) throw new Error(r.fatal||"invalid"); console.log("ok", r.issues.length)})' <fixture-repo>/.agentteam-insight/knowledge-graph.json
```

Dashboard 手动/冒烟验收：

```bash
cd /Users/lonng/devel/ai/Understand-Anything/understand-anything-plugin/packages/dashboard
GRAPH_DIR=<fixture-repo> pnpm dev
```

页面应能加载 graph，无 fatal validation error；file preview 只能读 graph 中的相对 `filePath`。

### 7.2 AgentTeam repo 内常规 gate

当前 baseline 已通过：

```bash
cd kits/agentteam-insight && go test ./...
```

实现期建议每批至少跑：

```bash
cd kits/agentteam-insight && go test ./...
git diff --check
```

涉及 MeshX/Web automation 接入时再补：

```bash
cd web && npx tsx --test src/meshx/components/automations/automationRepositoryFiles.test.ts
GOCACHE=/tmp/agentteam-go-cache go test ./internal/forwarder ./meshx/internal/service/kb -run 'CodeWiki|ImportProgress|Forward' -count=1
```

若修改 root/KB 产品链路，再走对应 `meshx`/`web` focused tests。

## 8. Worktree / cherry-pick 交付建议

已有组 worktree：

```text
/Users/lonng/devel/pingcap/agentteam/.worktrees/agentteam-insight-graph-builder-plan
branch: plan/agentteam-insight-graph-builder-ua
```

Codex2 当前研究 worktree：

```text
/Users/lonng/devel/pingcap/agentteam/.worktrees/codex2-agentteam-insight-graph-builder-scan
branch: research/codex2-agentteam-insight-graph-builder-scan
```

建议：

1. Codex2/GLM2 的调研结果各自提交为 `docs/research/...` 文档 commit；
2. Planner cherry-pick 这两个 research commit 到组 worktree，合成 `docs/superpowers/plans/...` 或 `docs/research/...implementation-plan.md`；
3. Reviewer2 对 plan/schema gate 通过后，再开实现批次分支；
4. 实现分支建议按 package 边界拆：
   - `feat/agentteam-insight-graph-builder-schema-persistence`
   - `feat/agentteam-insight-graph-builder-scan-fingerprint`
   - `feat/agentteam-insight-graph-builder-extractors-importgraph`
   - `feat/agentteam-insight-graph-builder-batch-assembler`
   - `feat/agentteam-insight-graph-builder-agent-layers-tour`
   - `feat/agentteam-insight-graph-builder-cli-dashboard-compat`
5. Planner 只 cherry-pick 过 gate 的 commits 到组 worktree，避免两个 worker 在同一 worktree 互相覆盖。

## 9. 与 #t1466 语义抽取的对齐

GLM2 的 #t1466 抽取把边界分为“必须确定性复刻”和“可后续 LLM/agent 增强”。AgentTeam Insight 计划应直接采用这个判定准则：

- Dashboard 能否加载、增量能否正确决策、文件布局/schema/validator/path sanitize/fingerprint 写入顺序是否正确，全部属于必须确定性复刻。
- Summary/tags/languageNotes/layers/tour/domain graph/graph-reviewer 等自然语言质量可先启发式降级，再逐步接入 LLM/agent 增强。
- `fingerprints.json` / `intermediate/*` 虽然不被 dashboard 直接读，但属于 pipeline correctness state，不能为了“前端只读 5 个文件”而省略。

## 10. 主要风险和建议决策

1. **“完整一样”的边界要写进 spec**：
   - schema、file layout、full/incremental stage、merge/normalization/fingerprint 必须同构；
   - LLM 文字摘要不可能 byte-for-byte 一样，但输出字段和引用边界必须一致；
   - batching 算法如果不完全复刻 graphology/Louvain，必须证明最终 graph 语义不受影响，或把 Louvain parity 列为 P0。
2. **AST extractor 覆盖成本高**：
   - Go 可先用标准库 `go/parser` 做 Go extractor；
   - 多语言 exact parity 需要 tree-sitter Go binding 或受控调用 UA core；
   - 如果目标是“前端可识别”而非“所有语言 extractor 完全同等”，可以先以 Go/TS fixture 驱动分阶段扩展。
3. **不要把 graph 作为 KB wiki 的副产物**：
   - KB insights/wiki 和 UA dashboard graph 是两个产物；
   - 可以共享 source snapshot 和 AgentTeam Insight runtime，但 persistence/schema 不应混在 `codewiki`。
4. **前端文件预览依赖相对路径**：
   - 持久化前必须 sanitize `node.filePath`；
   - absolute path 只能在内存/临时任务里存在，不能写入 graph。
5. **测试要有 UA validator 兼容门**：
   - 只跑 Go tests 不能证明 UA dashboard 能吃；
   - 需要至少一个 Node validator golden gate。
