ARTICLE · INTELLIGENCE

战地情报 · 详情页

来自尧图项目组的一线实战观察与深度解析

深入 graphify extraction-spec 语义抽取子代理提示词:节点 ID 契约、置信度离散刻度与 JSON Schema

深入 graphify extraction-spec 语义抽取子代理提示词:节点 ID 契约、置信度离散刻度与 JSON Schema 深入 graphify extraction-spec 语义抽取子代理提示词节点 ID 契约、置信度离散刻度与 JSON Schema【免费下载链接】graphifyTurn any codebase, with its docs, SQL schemas, configs, and PDFs, into a queryable knowledge graph. A /graphify skill for Claude Code, Cursor, Codex, and Gemini CLI: local deterministic AST parsing, every edge explained, no vector store.项目地址: https://gitcode.com/GitHub_Trending/graph/graphifygraphify 的/graphify流水线把代码用确定性 AST 抽取、文档用 LLM 语义抽取分成两条轨道而 extraction-spec.md 正是语义轨道的核心契约它是分发给每一个语义抽取子代理subagent的逐字提示词模板定义了子代理读哪些文件、抽什么关系、如何给节点命名、按什么刻度标注置信度、最终以什么 JSON Schema 落盘。本文以该文档为骨架完整拆解其规则体系并结合仓库中真正执行契约的校验器、ID 生成函数与防漂移测试说明这些看似提示词约定的规则如何成为保证图完整性不产生孤儿重复节点、不丢失增量更新对齐的工程约束。一、extraction-spec.md 在 /graphify 流水线中的位置该文档开头即声明了加载时机只有当语料中至少存在一个 doc、paper 或 image 分块时才在 Step 3 Part B 加载它纯代码语料跳过 Part B永远不会读取此文件。每个语义子代理收到的提示词都是该模板的逐字替换版本需要替换的占位符有五个占位符含义FILE_LIST该子代理负责的本次分块文件清单逐字、绝对路径CHUNK_NUM当前分块序号TOTAL_CHUNKS分块总数DEEP_MODE是否以--mode deep运行CHUNK_PATH子代理必须把结果 JSON 写到的精确绝对路径在宿主技能文件 skill-opencode.md 中可以看到它的完整消费链路Step B0 先做抽取缓存检查Step B1 把未命中缓存的文件切成每块 20–25 个文件的分块每张图片单独成块因为视觉理解需要独立上下文同目录文件尽量聚在同一块以便抽取跨文件关系Step B2 在单条消息里派发全部子代理OpenCode 平台使用mention派发同一消息中的所有 mention 并行执行Step B3 收集、写缓存并合并。技能文件明确写道关于确切的子代理提示词JSON schema、节点 ID 规则、置信度刻度、超边与视觉规则见references/extraction-spec.md。仅在此处加载且仅当至少一个分块包含 doc、paper 或 image 时加载。也就是说extraction-spec.md 不是给人阅读的说明文档而是机器间协议的规范文本——它同时约束 LLM 子代理的输出行为和下游合并器build_merge的匹配行为。二、三层置信度体系EXTRACTED / INFERRED / AMBIGUOUS规范为每条边定义了三个置信度等级这是 graphify诚实审计honest audit trail设计在抽取层的直接体现EXTRACTED关系在源码中是显式的import、call、引用、see §3.2 这类文本指针INFERRED合理推断共享数据结构、隐含依赖AMBIGUOUS不确定——必须标记出来供人工审查不允许直接省略。这三档在仓库的 schema 校验器 validate.py 中被硬编码为常量VALID_CONFIDENCES {EXTRACTED, INFERRED, AMBIGUOUS}validate_extraction()会对每条边做合法性检查非法值会进入错误列表并最终由assert_valid()抛出异常。因此子代理输出的不是自由文本而是必须通过机器校验的结构。2.1 confidence_score 的离散刻度规范对confidence_score的要求非常严格每条边必须携带禁止省略禁止把 0.5 当默认值且各等级取值如下置信等级允许的取值语义EXTRACTED恒为1.0源码中显式存在的关系INFERRED五值之一0.95/0.85/0.75/0.65/0.55永不取 0.5见下表AMBIGUOUS0.1–0.3不确定标记待审INFERRED 五档的判定基准原样继承自规范文本0.95直接结构性证据共享数据结构、跨文件命名引用0.85强推断功能对齐清晰但没有直接的符号级链接0.75合理推断共享问题域 相似形状需要解释0.65弱推断主题相关但没有形状证据0.55投机但可信仅有表层共现。规范还给出了一条来自生产经验的元规则模型对离散刻度的遵循度高于连续区间——生产环境观察到双峰分布50% 的边坍缩到 0.540% 到 0.85说明区间式引导会被模型坍缩成二分法因此这里强制五档离散值。若上述档位都不贴合应把边标记为 AMBIGUOUS而不是选 0.4 或更低的值。仓库中test_inferred_confidence_rubric.py等测试正是围绕这一刻度契约建立的回归保护tests/test_inferred_confidence_rubric.py。三、节点与 file_type六值封闭枚举规范约束file_type必须且只能是以下六个值之一其他任何值无效并会被拒绝code、document、paper、image、rationale、concept这与 validate.py 中VALID_FILE_TYPES {code, document, paper, image, rationale, concept}完全一致——规范文本与校验代码是同一契约的两面。针对文档/论文文件规范给出两条关键纪律rationaleWHY决策原因、权衡、设计意图不作为独立节点存储而是作为rationale属性挂在相关概念节点上。不得为 rationale 单独创建节点或 fragment 节点只有本身构成命名实体或概念的东西才有资格成为节点。概念性节点思想、原则、机制、设计模式使用file_type:rationale或concept。四、按文件类型分轨的抽取规则规范对不同文件类型给出差异化的关注点核心思想是语义抽取只补 AST 到不了的边4.1 代码文件聚焦 AST 找不到的语义边调用关系、共享数据、架构模式不要重复抽取 import——AST 已经拿走了这些边重复抽取会造成节点/边污染。calls边有两条硬性方向约束source 必须是调用方发起调用的函数/类target 必须是被调方方向永不反转calls边必须停留在同一种语言内部Python 函数不能callsJS/TS/Go/Rust/Java 符号反之亦然。跨语言调用边是幽灵产物phantom artifacts永远不要输出。4.2 图片文件用视觉理解图是什么而非 OCR规范要求对图片使用视觉能力理解图片本身是什么UI 截图布局模式、设计决策、关键元素、用途图表指标、趋势/洞察、数据来源推文/帖子主张作为节点加上作者、被提及的概念示意图diagram组件与连接科研图research figure证明了什么、方法、结果手写/白板想法与箭头读不确定的内容标记 AMBIGUOUS。4.3 DEEP_MODE 与语义相似边当构建时给出了--mode deep模板中占位为DEEP_MODE子代理应激进地产出 INFERRED 边——间接依赖、共享假设、潜在耦合拿不准的标记 AMBIGUOUS 而不是省略。此外规范定义了一类特殊边semantically_similar_to当同一分块内两个概念没有任何结构链接无 import、无 call、无引用却解决同一问题或表达同一思想时添加该边并标为 INFERREDconfidence_score落在 0.6–0.95 区间反映相似度。规范给出的三类示例两个都校验用户输入但互不调用的函数代码中的一个类与论文中一个概念描述同一算法两个处理同一失败模式但方式不同的错误类型。约束是只在相似性真正非显然且跨切面时添加平凡相似不加分。4.4 超边Hyperedges当 3 个或更多节点共同参与一个仅靠成对边无法表达的共享概念、流程或模式时向顶层hyperedges数组添加超边。规范给出的示例实现同一协议/接口的所有类认证流程中的全部函数即使它们并非互相都调用;论文某节中共同构成一个连贯思想的全部概念。使用纪律节制使用——只有当群组关系提供了成对边之外的信息时才加每个分块最多 3 条超边。4.5 YAML frontmatter 透传如果文件带有 YAML frontmatter--- ... ---要把source_url、captured_at、author、contributor四个字段复制到该文件产出的每个节点上——这是/graphify add抓取的 URL 语料保留来源元数据的基础。五、节点 ID 格式与 AST 抽取器对齐的硬契约这是整份规范中工程后果最重的部分。ID 规则原文要点小写仅允许[a-z0-9_]无点号、无斜杠格式为{stem}_{entity}其中 stem 是去掉扩展名的完整仓库相对路径保留所有路径层级、用_连接每段小写非字母数字字符替换为_entity 是同样方式归一化的符号名使用每一级目录而不只是直接父目录——这让不同目录下同名文件互不冲突顶层文件如setup.py无父目录直接用文件名字干setup_my_func禁止在 ID 后追加分块号、序号或任何后缀不允许_c1、_c2、_chunk2之类ID 必须仅由标签确定性推出——同一实体无论落在哪个分块处理都必须生成同一 ID。规范给出的全部示例这些示例本身就是测试断言的锚点见后文第六节src/auth/session.py ValidateToken - src_auth_session_validatetoken lib/utils/helpers.py parse_url - lib_utils_helpers_parse_url tests/test_foo.py _helper - tests_test_foo_helper docs/v1/api/README.md getUser - docs_v1_api_readme_getuser setup.py (顶层文件) my_func - setup_my_func为什么必须用全路径规范警告只用文件名如session_validatetoken或只用直接父目录如auth_session_validatetoken会制造孤儿幽灵重复节点。这与 AST 侧的实现一一对应extractors/base.py 中的_file_stem()明确注释使用所有段——而不只是直接父目录#1504——意味着不同目录下的同名文件获得不同 ID而不是坍缩成一个 last-writer-wins 节点并给出docs/v1/api/README.md - docs_v1_api_readme的同一组例子_make_id()再把分隔符折叠成下划线。也就是说LLM 子代理语义轨和确定性 AST 抽取器结构轨共同遵守同一 ID 算法两条轨道产出的节点才能在 Part C 合并时按 ID 精确去重AST 节点优先语义节点按 ID 去重追加。规范还提示如果项目是按旧的直接父目录格式构建的应运行graphify extract --force干净重建。六、规范文本与代码的双向防漂移一个值得注意的仓库设计规范文本是人工维护的提示词而它给出的 ID 示例是 LLM 的地面真值——一旦示例与代码漂移同一符号会被两条轨道生成不同 ID图就会分裂。仓库用一个专门的测试把这份规范本身锁进了测试套件tests/test_extraction_spec_ids.py。该测试的行为扫描graphify/skills/与tools/skillgen/fragments/下每一份shipped 的extraction-spec.mdOpenCode 版只是其中一份skillgen 从共享片段渲染出各宿主平台的副本用正则解析文中所有形如path entity → id的示例对每个示例调用生产环境真实函数_make_id(_file_stem(path), entity)断言输出与示例完全一致test_cautionary_wrong_forms_are_actually_wrong进一步把反面示例也锁死断言文件名-only 与直接父目录-only 两种 ID 形态确实不等于正确形态。它的失败条件是双向的规范示例被改成错误值或 ID 函数被改动导致文档示例不再成立测试都会挂掉。换句话说本文引用的全部示例不是文档装饰而是 CI 中可执行的契约。七、source_file 逐字规则与 CHUNK_PATH 落盘规则规范对source_file字段出现在每个 node、edge、hyperedge 上给出了一条逐字符复制规则source_file必须设置为来源文件在FILE_LIST中原样出现的路径——逐字、绝对路径不得缩短为 basename、不得重新相对化、不得剥离任何目录前缀、不得更换分隔符引擎在下游统一做分隔符归一化、相对构建根build root的相对化。原文给出的动机保持完整构建与增量--update 在同一基准上这样build_merge的 replace-on-re-extract 才能命中已有节点并替换而不是累积一个重复节点。配合宿主技能中 Step 4 的注释root使source_file相对化到与--updaterunbook 相同的基准保证全量构建与增量更新不会在重抽取时漂移可以确认这条提示词规则的落点就是增量更新的节点匹配键。落盘规则同样具体子代理必须用 Write 工具把 JSON 写到CHUNK_PATH指定的精确绝对路径——因为 Write 工具对相对路径按未定义的 cwd 解析文件会被静默丢失。宿主技能 Step B3 的验收信号也与之呼应检查.graphify_chunk_NN.json是否存在于磁盘上存在且含有效nodes/edges才计入缺失则提示子代理可能以只读方式派发请改用 general-purpose agent 重跑不静默跳过超过一半分块失败则停止并要求用户重跑。八、输出 JSON Schema逐字段解读规范第 63–64 行给出了必须严格匹配的输出 Schema原文示例缩进整理{ nodes: [{ id: auth_session_validatetoken, label: Human Readable Name, file_type: code|document|paper|image|rationale|concept, source_file: FILE_LIST 中的路径逐字, source_location: null, source_url: null, captured_at: null, author: null, contributor: null }], edges: [{ source: node_id, target: node_id, relation: calls|implements|references|cites|conceptually_related_to|shares_data_with|semantically_similar_to|rationale_for, confidence: EXTRACTED|INFERRED|AMBIGUOUS, confidence_score: 1.0, source_file: FILE_LIST 中的路径逐字, source_location: null, weight: 1.0 }], hyperedges: [{ id: snake_case_id, label: Human Readable Label, nodes: [node_id1, node_id2, node_id3], relation: participate_in|implement|form, confidence: EXTRACTED|INFERRED, confidence_score: 0.75, source_file: FILE_LIST 中的路径逐字 }], input_tokens: 0, output_tokens: 0 }要点归纳顶层四个键nodes、edges、hyperedges三个数组加上input_tokens/output_tokens两个计量字段子代理输出占位零值宿主在 Step B3 从 Agent 工具的usage字段读回真实 token 数并写回再合并各块求和节点必填id、label、file_type、source_file与 validate.py 中REQUIRED_NODE_FIELDS一致可选的来源追溯字段source_location/source_url/captured_at/author/contributor用于 frontmatter 透传与行级引用边必填source、target、relation、confidence、source_file对应REQUIRED_EDGE_FIELDSrelation是一个 8 值封闭枚举边两端必须命中已声明的 node id校验器会检查悬空端点超边只允许EXTRACTED/INFERRED两档置信度不允许 AMBIGUOUSrelation 为 3 值枚举输出纪律只输出合法 JSON无解释、无 markdown 围栏、无开场白。九、规范如何与缓存机制联动SPEC_PATH宿主技能 skill-opencode.md 的 Step B0 中有一处容易被忽略的细节语义缓存的读写都要传入同一个SPEC_PATH参数——即这份references/extraction-spec.md的绝对路径cached_nodes, cached_edges, cached_hyperedges, uncached check_semantic_cache( all_files, rootINPUT_PATH, prompt_fileSPEC_PATH)其语义是缓存条目归属于产生它的那份提示词。当 graphify 升级修改了 extraction-spec 提示词旧提示词产出的缓存条目会因 prompt_file 指纹不匹配而被判为失效、重新抽取提示词未变时则直接回放缓存。同理 Step B3 的save_semantic_cache(..., prompt_fileSPEC_PATH)写入时必须用同一 SPEC_PATH——读用一个提示词、写用另一个提示词的条目会落进下一次运行查不到的命名空间。这让 graphify/cache.py 中的check_semantic_cache/save_semantic_cache与规范文本之间形成了一个可追溯的闭环规范即缓存版本号。十、小结一份提示词为何要写成工程契约回看整份 extraction-spec.md它的每条规则都对应一个下游工程问题规则防住的故障模式三层置信度 离散刻度模型把不确定边伪装成事实边连续区间被坍缩成二分calls方向与单语言约束反向边、跨语言幽灵边污染调用图rationale 作为节点属性图被解释性碎片淹没、社区检测失真全路径节点 ID 禁后缀两条轨道 ID 不一致 → 孤儿重复节点同实体跨分块 ID 漂移source_file 逐字复制全量构建与--update增量基准漂移 → replace 失配、重复累积精确绝对 CHUNK_PATH相对路径 Write 落盘到错误 cwd结果静默丢失六值 file_type / 8 值 relation 封闭枚举非法输出在 validate.py 处被机器拒绝而非静默混入prompt_file 缓存指纹提示词升级后旧缓存被误回放对使用者而言这份文件的实用价值在于如果你在自研LLM 抽取 确定性解析混合的知识图谱流水线extraction-spec.md 提供了一个可复制的完整样例——用封闭枚举约束词汇表、用离散刻度约束数值、用与解析器共享的 ID 算法约束身份、用规范文本进测试的方式约束文档漂移。在 graphify 仓库内部它与 skill-opencode.md 的 Step B 流程、extractors/base.py 的 ID 函数、validate.py 的 schema 校验、tests/test_extraction_spec_ids.py 的防漂移测试共同构成了一条从提示词到磁盘产物的可验证链路。【免费下载链接】graphifyTurn any codebase, with its docs, SQL schemas, configs, and PDFs, into a queryable knowledge graph. A /graphify skill for Claude Code, Cursor, Codex, and Gemini CLI: local deterministic AST parsing, every edge explained, no vector store.项目地址: https://gitcode.com/GitHub_Trending/graph/graphify创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考
RELATED READING

延伸阅读

更多一线实战笔记与深度复盘,助您持续精进