第23A章 · Harness Engineering:系统提示词装配工程全解
第23A章 · Harness Engineering:系统提示词装配工程全解
Claude Code最核心的工程秘密不在工具系统,不在Agent架构,而在于它如何精密地组装发送给Claude API的系统提示词(System Prompt)。这套"提示词装配工程"(Harness Engineering)决定了Claude在每次对话中的身份认知、能力边界、行为准则和上下文感知。源码揭示了一套高度模块化、缓存优化、多层注入的提示词流水线。
23A.1 三种身份前缀
一切从身份认知开始。constants/system.ts定义了三种系统提示词前缀,决定Claude如何认知自己:
DEFAULT_PREFIX:
"You are Claude Code, Anthropic's official CLI for Claude."
AGENT_SDK_CLAUDE_CODE_PRESET_PREFIX:
"You are Claude Code, Anthropic's official CLI for Claude,
running within the Claude Agent SDK."
AGENT_SDK_PREFIX:
"You are a Claude agent, built on Anthropic's Claude Agent SDK."getCLISyspromptPrefix()函数根据以下条件选择前缀:
- Vertex API提供商 → 始终使用DEFAULT_PREFIX
- 非交互模式且有appendSystemPrompt → 使用AGENT_SDK_PREFIX
- 其他情况 → 使用DEFAULT_PREFIX
这种设计意味着同一套代码可以让Claude呈现为"Claude Code本体"或"基于Agent SDK的自定义Agent"——身份认知的切换仅取决于一个前缀字符串。
23A.2 系统提示词的七层静态结构
constants/prompts.ts中的getSystemPrompt()函数按顺序组装七个静态段落,构成提示词的"骨架":
1. Intro Section — 身份与核心原则
2. System Section — 系统行为约束
3. Doing Tasks Section — 任务执行指南(代码风格、验证流程)
4. Actions Section — 操作谨慎原则(可逆性偏好)
5. Tools Section — 工具使用规范
6. Tone & Style Section — 语气与风格要求
7. Output Efficiency — 输出效率原则(简洁、避免不必要的评论)这七个段落在所有用户、所有会话中保持一致——它们构成了Claude Code行为的"宪法"。
精简模式例外:当CLAUDE_CODE_SIMPLE=1环境变量启用时,整个系统提示词退化为极简形式,仅包含身份前缀、工作目录和日期。这为开发者提供了一个"裸核"模式,用于调试或构建自定义体验。
23A.3 动态段落:会话级定制
静态骨架之后是动态段落,由systemPromptSection()和DANGEROUS_uncachedSystemPromptSection()两个API管理:
缓存型动态段落(每会话计算一次):
session_guidance — 会话特定的工具指导
memory — 记忆目录内容(loadMemoryPrompt())
ant_model_override — Anthropic内部模型覆盖
env_info_simple — 环境信息(模型、平台、CWD、Git状态)
language — 语言偏好
output_style — 输出风格配置
scratchpad — 草稿目录指令
frc — 函数结果清除指令
summarize_results — 工具结果摘要指导
numeric_anchors — 长度锚点(仅内部)
token_budget — Token预算指导
brief — KAIROS简洁模式易变型动态段落(每轮重算):
mcp_instructions — MCP服务器指令(服务器可在轮次间连接/断开)DANGEROUS_uncachedSystemPromptSection()要求调用者提供"为什么需要破缓存"的原因字符串——这种防御性API设计确保开发者不会随意添加易变段落导致缓存失效。
23A.4 CLAUDE.md:用户注入层
CLAUDE.md文件是用户将自己的指令注入系统提示词的通道。加载器实现了一套四级发现机制:
优先级递增:
/etc/claude-code/CLAUDE.md — 全局托管指令
~/.claude/CLAUDE.md — 用户全局指令
项目根/CLAUDE.md — 项目指令
项目根/.claude/CLAUDE.md — 项目指令(隐藏目录)
项目根/.claude/rules/*.md — 条件规则文件
项目根/CLAUDE.local.md — 本地私有指令@include指令:CLAUDE.md支持@path语法引用外部文件,最大嵌套深度5层,带循环引用检测。
条件规则:.claude/rules/下的Markdown文件支持YAML frontmatter中的paths字段,实现基于路径的条件加载——例如一条规则仅在编辑src/**文件时生效。
安全限制:
- 推荐上限:40,000字符(
MAX_MEMORY_CHARACTER_COUNT) - MEMORY.md入口截断:200行或25,000字节
- 符号链接早期解析,防止路径遍历攻击
- HTML注释(
<!-- -->)自动剥离
加载后的CLAUDE.md内容包装在一个醒目的框架中:
Codebase and user instructions are shown below.
Be sure to adhere to these instructions.
IMPORTANT: These instructions OVERRIDE any default behavior
and you MUST follow them exactly as written.这个"OVERRIDE"声明确保CLAUDE.md中的用户指令可以覆盖系统默认行为。
23A.5 上下文注入:Git状态与系统提醒
context.ts负责收集两类运行时上下文:
系统上下文(getSystemContext()):
- 当前分支名和主分支名
- Git用户名
- 最近5条提交信息
git status --short输出(截断至2000字符)
用户上下文(getUserContext()):
- CLAUDE.md内容
- 当前日期
两者均使用memoize缓存,会话内只计算一次。注入方式不同:
- 系统上下文 → 追加到系统提示词(
appendSystemContext()) - 用户上下文 → 作为首条用户消息前置(
prependUserContext()),包装在<system-reminder>标签中
<system-reminder>标签的设计极为巧妙。系统提示词中明确告知Claude:
Tool results and user messages may include <system-reminder> tags.
<system-reminder> tags contain useful information and reminders.
They are automatically added by the system, and bear no direct
relation to the specific tool results or user messages in which
they appear.这既告诉Claude可以信任这些标签内容,又避免了Claude将其误认为用户直接输入的内容。
23A.6 缓存边界标记:全局缓存的关键
SYSTEM_PROMPT_DYNAMIC_BOUNDARY是整个缓存架构的核心概念:
export const SYSTEM_PROMPT_DYNAMIC_BOUNDARY =
'__SYSTEM_PROMPT_DYNAMIC_BOUNDARY__'这个标记将系统提示词分为两半:
- 标记之前:跨组织共享的静态内容,使用
scope: 'global'缓存 - 标记之后:用户/会话特定的动态内容,不缓存或使用
scope: 'org'
仅在Anthropic第一方(shouldUseGlobalCacheScope())时插入此标记。
23A.7 三种缓存模式
utils/api.ts中的splitSysPromptPrefix()函数将系统提示词拆分为2-4个缓存块,根据场景选择三种模式之一:
模式1:MCP工具缓存模式(有MCP工具时)
归因头部 → cacheScope: null(不缓存)
系统提示前缀 → cacheScope: 'org'
其余内容 → cacheScope: 'org'模式2:全局缓存模式(仅第一方,有边界标记时)
归因头部 → cacheScope: null
系统提示前缀 → cacheScope: null
边界前静态内容 → cacheScope: 'global' ← 全用户共享!
边界后动态内容 → cacheScope: null模式3:组织缓存模式(第三方或无边界标记时)
归因头部 → cacheScope: null
系统提示前缀 → cacheScope: 'org'
其余内容 → cacheScope: 'org'全局缓存模式的经济效益巨大——所有使用Claude Code的用户共享同一份缓存的静态提示词,大幅降低了每次请求的token消耗。
23A.8 缓存控制头部与TTL策略
每个缓存块最终转化为API的cache_control头部:
{
type: 'ephemeral',
ttl: '1h', // 或默认5分钟
scope: 'global' // 或 'org'
}1小时TTL的资格判定(should1hCacheTTL()):
- Anthropic员工 → 直接资格
- Claude.ai订阅者且非超额状态 → 资格
- 资格在会话启动时"锁存"(latched),防止中途变化破坏缓存
消息级缓存断点:每次API请求恰好放置一个cache_control标记在最后一条消息的最后一个块上。对于"发射后不管"的分叉请求,标记放在倒数第二条消息上,避免孤立的KV缓存页。
23A.9 归因头部:隐藏的计费指纹
getAttributionHeader()生成一个HTTP风格的归因头部,嵌入系统提示词最前端:
x-anthropic-billing-header:
cc_version=2.1.88.a3f2c1; ← 版本号 + 指纹哈希
cc_entrypoint=cli; ← 入口点(cli/desktop/web/ide)
cch=___ATTESTATION_TOKEN___; ← 客户端证明令牌占位符
cc_workload=interactive; ← 工作负载类型(交互/cron)指纹哈希由消息内容字符和版本号计算,用于QoS路由和计费追踪。cch占位符在Bun的HTTP栈中被实际的Native Client Attestation令牌替换——这是一种反滥用机制。
23A.10 Token预算管理与自动压缩
上下文窗口感知:utils/context.ts为不同模型配置上下文窗口大小,默认200K token,支持[1m]后缀扩展至1M token。
Token计数双轨制:
- 精确计数:从API响应的
usage字段提取(含cache_creation_input_tokens和cache_read_input_tokens) - 估算计数:4字节/token的粗略估算(JSON为2字节/token),图片固定2000 token
自动压缩三级阈值:
正常 → 预警(距上限20K token)→ 错误(距上限20K token)→ 自动压缩(距上限13K token)压缩失败熔断:连续3次压缩失败后停止重试,防止无限循环。
两种压缩策略:
- Snip压缩(
HISTORY_SNIP特性标志):主动边界截断,保留Snip标记用于UI回滚 - 反应式压缩(
REACTIVE_COMPACT特性标志):API错误后触发,后缀保留,保持最后摘要
微压缩(Microcompact):增量缓存编辑,不做完整摘要。选择性清除旧工具结果(File Read、Bash、Grep等10种工具),插入cache_edits删除块。已固定的编辑在后续请求中复用。
23A.11 多模式提示词适配
同一套装配流水线通过条件分支支持多种运行模式:
| 模式 | 前缀选择 | 特殊段落 | 缓存策略 |
|---|---|---|---|
| 交互模式 | DEFAULT | 完整七层 + 全部动态段落 | 全局/组织缓存 |
| SDK/Agent模式 | AGENT_SDK | 精简 + appendSystemPrompt | 组织缓存 |
| KAIROS自主模式 | DEFAULT | 自主工作段 + 节奏指导 + 首次唤醒问候 | 组织缓存 |
| 精简模式 | DEFAULT | 仅CWD + 日期 | 最小缓存 |
| 协调器模式 | DEFAULT | 协调器上下文注入 | 组织缓存 |
23A.12 防篡改与缓存一致性
系统对缓存一致性的维护极为严格:
缓存破坏检测(promptCacheBreakDetection.ts):每次请求跟踪多个哈希值:
- 系统提示词全文哈希
- 工具Schema逐工具哈希(细粒度检测哪个工具变了)
- 缓存控制哈希(检测scope/TTL翻转)
- Model名称变化
- Beta头部变化
- 全局缓存策略翻转(MCP工具发现/移除)
会话稳定性设计:
- TTL资格在启动时锁存,防止中途GrowthBook翻转导致20K token缓存失效
- 工具Schema全会话缓存,防止特性标志变化导致Schema漂移
- Undercover模式下剥离所有模型名称,防止泄露到公开提交
23A.13 Harness Engineering的设计哲学
从源码分析中可以提炼出五条核心设计原则:
1. 静动分离:将不变的"宪法"与易变的"执行细节"用边界标记分开,最大化缓存命中率。
2. 防御性缓存API:破坏缓存的段落必须提供理由(DANGEROUS_uncachedSystemPromptSection的reason参数),迫使开发者思考缓存影响。
3. 优雅降级:系统提示词的每一层都设计了失败后退路径——CLAUDE.md加载失败则跳过、Git状态获取失败则省略、GrowthBook不可达则使用磁盘缓存。
4. 层级覆盖:用户指令(CLAUDE.md)明确声明可以OVERRIDE系统默认行为,赋予用户最终控制权,同时通过<system-reminder>标签区分元数据与用户输入。
5. 经济性优先:从全局缓存scope到1小时TTL到微压缩,每一个设计决策都在追求token经济性——这直接影响API调用成本和响应延迟。
23A.14 行业视角:Harness Engineering的兴起
"Harness Engineering"(驾驭工程)作为一个正式术语在2026年初进入主流技术词汇。Anthropic在其官方工程博客中将其定义的核心概念命名为"Context Engineering"(上下文工程),将其视为Prompt Engineering的自然演进——从"如何写好一条提示词"升级为"如何策划和维护推理过程中最优的token集合"。
与传统Prompt Engineering的区别:
Prompt Engineering优化单次模型调用;Harness Engineering涵盖整个系统——编排、状态管理、错误恢复、可观测性、多会话协调。Prompt Engineering只是Harness Engineering的一个组成部分。
Harness Engineering的五大支柱(综合NxCode指南与Anthropic实践):
-
工具编排(Tool Orchestration)——明确定义可用工具、调用方式和权限要求。Claude Code的43+工具系统和
CanUseToolFn权限模型是这一支柱的教科书实现。 -
护栏与安全约束(Guardrails)——多层级的确定性规则:权限边界、验证检查(Linter、类型检查)、架构约束、速率限制。Claude Code的七层安全防护体系(第22章)是该支柱的极致体现。LangChain的研究表明,仅通过改进Harness(不改变模型),SWE-bench分数就从52.8%跃升至66.5%。
-
错误恢复与反馈循环(Error Recovery)——自动重试逻辑、自我验证循环、回滚机制、死循环检测。Claude Code的指数退避重试(第23B.4节)和拒绝追踪机制(第10.3节)均属此类。
-
可观测性(Observability)——记录Agent动作、追踪Token用量、记录决策点、发现异常。Claude Code的GrowthBook遥测体系(第23.5节)和归因头部(第23A.9节)是此支柱的实现。
-
人在环路(Human-in-the-Loop)——在高杠杆决策时刻设置审批闸门,而非持续微管理。Claude Code的三级权限模型(Allow/Deny/Ask)精确体现了这一原则。
23A.15 最佳实践:从源码中学到的Prompt Caching策略
Anthropic官方文档揭示了Claude Code背后的Prompt Caching经济学:
缓存定价模型(以Opus 4.6为例):
基础输入: $5 / 百万token
5分钟缓存写入: $6.25 / 百万token(+25%)
1小时缓存写入: $10 / 百万token(+100%)
缓存读取: $0.50 / 百万token(-90%!)这解释了Claude Code为何如此执着于缓存优化——每次缓存命中节省90%的输入token成本。对于一个系统提示词可达数万token的工具,缓存命中率直接决定了运营成本。
Claude Code的缓存实践与官方建议的对照:
| 官方最佳实践 | Claude Code的实现 |
|---|---|
| 静态内容放顶部,动态内容放底部 | SYSTEM_PROMPT_DYNAMIC_BOUNDARY精确分割 |
| 在稳定内容上放置缓存断点 | 归因头部不缓存,静态提示词全局缓存 |
| 每次请求仅一个消息级断点 | 恰好一个cache_control在最后消息的最后块 |
| 多轮对话中渐进复用缓存前缀 | 微压缩保留已固定的cache_edits块 |
| 注意最低token阈值(Opus: 4096) | 系统提示词远超4096token,天然满足 |
| 混合TTL时长TTL在前 | 系统提示词用长TTL,消息用默认5分钟 |
2026年2月的缓存隔离变更:Anthropic将缓存隔离从组织级改为工作区级。这意味着同一组织内不同工作区的缓存不再共享——Claude Code的scope: 'org'策略在此变更后实际指向工作区级缓存。
23A.16 最佳实践:Anthropic官方Prompt Engineering要点
Anthropic官方提示词最佳实践文档提供了一系列直接适用于Harness设计的指导:
结构化原则:
- 使用XML标签(
<instructions>、<context>、<input>)分隔不同类型的内容——Claude Code的<system-reminder>标签正是此原则的实践 - 长文档放在提示词顶部,查询放在底部——测试表明这可提升30%的响应质量
- 用Few-shot示例引导输出格式,包装在
<example>标签中
Agent系统的特殊指导:
- 上下文感知:Claude 4.5/4.6模型能追踪剩余上下文窗口。如果Agent框架支持压缩或外部保存,应在提示词中告知模型:"你的上下文窗口会在接近上限时自动压缩,因此不要因token预算担忧而提前停止任务"——这正是Claude Code的自动压缩机制(第23A.10节)所实现的
- 并行工具调用:显式鼓励并行执行独立工具调用可将成功率提升至接近100%
- 子Agent编排:Claude Opus 4.6有强烈的子Agent倾向,可能在简单grep即可解决的场景也派生子Agent。需要添加指导限制过度使用
- 防止过度工程:模型可能创建不必要的抽象。添加"仅做直接请求的变更"的约束
关键洞察——"攻击性语言已过时":
在Claude 4.5/4.6时代,"YOU MUST"和"NEVER EVER"等强迫性语言反而会降低模型表现。平静、直接的指令效果更好。Claude Code的系统提示词中大量使用了这一策略——用解释性语言("这样做因为...")替代命令性语言。
23A.17 最佳实践:CLAUDE.md编写指南
综合源码分析和社区实践,CLAUDE.md的编写应遵循以下原则:
极简主义:CLAUDE.md应包含尽可能少的指令——理想情况下只包含普适性规则。过长的CLAUDE.md会消耗宝贵的上下文窗口空间,降低模型对其他信息的注意力。
层级化组织:
~/.claude/CLAUDE.md → 跨项目通用偏好(语言、风格)
项目根/CLAUDE.md → 项目架构、构建命令、约定
.claude/rules/*.md → 条件规则(仅特定路径生效)
CLAUDE.local.md → 个人本地偏好(不提交到Git)反模式:
- 不要重复模型已知的信息(如"你是一个AI助手")
- 不要添加过多的格式规则——上下文窗口是有限资源
- 不要在CLAUDE.md中放置敏感信息(API密钥等)
23A.18 最佳实践:反蒸馏与安全防线
源码中一个鲜为人知的机制值得特别关注——Anti-Distillation(反蒸馏)。
当ANTI_DISTILLATION_CC编译时标志和tengu_anti_distill_fake_tool_injection GrowthBook开关同时启用时,Claude Code会在API请求中发送anti_distillation: ['fake_tools']参数,指示服务端"静默注入诱饵工具定义到系统提示词中"。
这意味着:如果有人通过中间人攻击截获API流量并用于训练竞品模型,训练数据中会包含虚假的工具定义,导致训练出的模型调用不存在的工具——一种巧妙的"数据投毒"防御。
此外,Undercover Mode(卧底模式)通过undercover.ts模块(90行代码)实现:在非Anthropic仓库中操作时,剥离所有内部引用——禁止提及内部代号如"Capybara"或"Tengu"、内部Slack频道、仓库名或"Claude Code"本身。在外部构建中,此模块被死代码消除为空操作。
23A.19 上下文工程的未来:从Prompt到Context
Anthropic官方将Harness Engineering的核心重新定义为"Context Engineering"——理由是现代Agent系统中,"提示词"只是上下文的一小部分。完整的上下文包括:
工具定义 → 系统提示词 → 记忆文件 → Git状态 → 对话历史 → 工具结果 → 缓存编辑四种上下文策略(引自LangChain框架化的理论):
- Write(写入)—— 将上下文持久化到外部存储。Claude Code的MEMORY.md和KAIROS日记系统
- Select(选择)—— 检索相关内容。Claude Code的CLAUDE.md条件规则和@include指令
- Compress(压缩)—— 摘要和压缩。Claude Code的Snip/Reactive/Micro三层压缩策略
- Isolate(隔离)—— 为不同Agent分配独立上下文。Claude Code的SubAgent架构和Worktree隔离
Anthropic的核心指导原则:"找到最小的高信号token集合,最大化期望结果的可能性。" Claude Code的整个Harness Engineering体系——从静动分离的系统提示词到精细的缓存控制到智能的上下文压缩——都是这一原则的工程实现。