当规格成为软件的源头:GitHub Spec Kit 技术深度解析

当规格成为软件的源头:GitHub Spec Kit 技术深度解析

在 AI 编码时代,最值钱的不是代码,而是精确描述"你到底想要什么"的能力。

翻开任何一本软件工程的教材,你都会看到类似的流程图:需求分析 → 系统设计 → 编码实现 → 测试部署。这套方法论已经统治了软件行业几十年。但现实中发生了什么?需求文档写完就锁进抽屉,设计图在第一次 code review 后就再也没人看,测试用例是上线前一天通宵补的。

代码成了唯一的真相,而规格沦为了点缀。

GitHub 的 Spec Kit 想要翻转这件事。


范式转移:从"代码为王"到"规格为王"

传统开发的根本矛盾

软件工程一直有一个无法消除的缝隙:规格和实现之间的鸿沟

我们试过很多方法来缩小这个缝隙——更详细的 PRD、更严格的代码审查、更完善的敏捷流程。但这些都默认了一个前提:缝隙是不可避免的,我们只能尽量窄一点。

Spec-Driven Development(SDD,规格驱动开发)彻底否定了这个前提。它的核心主张是:消除缝隙,而不是缩小缝隙。

怎么做?让规格本身变成可执行的——规格不再是"给人看的参考文档",而是"能直接生成代码的源头"。

这背后的逻辑是:当代码必须从规格中"长出来"时,两者之间就不再有鸿沟,只有转换关系。

为什么是现在?

三个趋势在 2025 年同时成熟,让 SDD 从理论变成了实践:

AI 代码生成能力的临界点。 大语言模型已经能可靠地理解自然语言规格,并将其转化为可工作的代码。这不是取代开发者,而是放大他们的效能——把"规格→代码"这段机械翻译自动化。

软件复杂度的指数级增长。 一个现代应用动辄集成几十个微服务、框架和第三方依赖。靠人力保持所有组件与原始意图的一致性,已经变得几乎不可能。SDD 通过规格驱动来提供系统性的对齐保障。

需求变化的速度空前加快。 Pivot 不再是例外,而是常态。传统开发把需求变更视为"干扰",每次变更都要手动在文档、设计、代码之间传播。而 SDD 中,改规格、重新生成,就是标准流程的一部分。


Spec Kit 技术架构

Spec Kit 是 GitHub 官方开源的 SDD 工具包,它不是一个单一的代码生成器,而是一套完整的方法论基础设施。

核心组件

整个工具包由六个层次组成:

Specify CLI 是整个系统的入口。它是一个 Python CLI 工具(通过 uv 安装),负责项目初始化、集成管理、工作流编排等所有元操作。你不会直接用它写代码,但所有 SDD 流程都通过它来调度。

Templates 系统 是规格的骨架。每个命令(specify、plan、tasks 等)都对应一套结构化模板,确保输出不会遗漏关键信息——从非功能性需求到错误处理,从数据模型到 API 契约。

Integrations 层 连接 AI 编码代理。目前支持 30+ 工具——从 GitHub Copilot、Claude Code、Cursor 到 Codex CLI、Gemini CLI、Qwen Code,甚至包括国产的 Trae、Lingma、Kimi Code。每个集成都会设置好对应的命令文件、上下文规则和目录结构。

Extensions(扩展) 让你添加新能力——领域特定命令、外部工具集成、质量门禁。多个扩展可以独立安装和卸载。

Presets(预设) 定制 SDD 的工作方式——覆盖命令模板、术语对齐、组织标准适配,而不改变底层工具。

Workflows(工作流) 把多步骤的 SDD 流程编排成可重复的序列,支持条件分支、循环、fan-out/fan-in,甚至可以暂停和恢复。

优先级体系

这四层定制机制按优先级从高到低排列:

优先级 类型 位置
1 项目本地覆盖 .specify/templates/overrides/
2 Presets .specify/presets/templates/
3 Extensions .specify/extensions/templates/
4 Spec Kit 核心 .specify/templates/

这意味着你可以从"使用默认模板"开始,逐步通过预设和扩展来定制,最终实现完全的组织级标准化——而不用 fork 整个项目。


SDD 工作流:从想法到代码

六步核心流程

SDD 的核心流程可以用一条流水线来概括:

Constitution(建立宪法)→ Specify(写规格)→ Plan(做计划)→ Tasks(拆任务)→ Implement(写代码)→ Converge(对账)

每一步都有对应的 slash command,让我们用一个真实例子来走一遍。

Step 1: 建立项目宪法

/speckit.constitution 创建原则:代码质量标准、测试覆盖率 >80%、移动端优先的响应式设计、所有 API 必须有 OpenAPI 文档

这一步定义了项目的"基本法"——后续所有生成代码都受它约束。宪法不是写给人看的建议,而是写入 AI 上下文的硬性规则。当后续 plan 和 implement 阶段做出技术决策时,这些原则会被自动引用。

这相当于在提示词工程中设定 system prompt——先画好边界,再让 AI 在边界内发挥。

Step 2: 写规格(最关键的一步)

/speckit.specify 构建一个照片管理应用,可以按日期分组相册,支持拖拽重新排列,相册不嵌套,照片以网格预览

注意这里只描述 What(做什么)和 Why(为什么),完全不涉及技术栈。这一步会自动完成:

  • 扫描现有 specs 目录,确定下一个 feature 编号(001、002…)
  • 从描述中生成语义化的分支名并创建 Git 分支
  • 基于模板生成结构化的 feature 规格文档,放在 specs/[branch-name]/spec.md
  • 自动填充用户故事、验收标准、非功能性需求

AI 在这一步会追问你:相册容量有没有上限?拖拽时要不要显示放置预览?照片要不要支持排序?这些问题在传统开发中往往要到 code review 阶段才被发现。

Step 3: 制定技术计划

/speckit.plan 使用 Vite 构建,尽量用原生 HTML/CSS/JS,图片不上传,元数据存本地 SQLite

这一步把产品规格翻译成技术方案。AI 会:

  • 读取并分析 spec.md 中的需求和验收标准
  • 对照项目宪法,确保技术选型符合约束
  • 生成数据模型(data-model.md
  • 生成 API 契约(contracts/ 目录)
  • 生成研究文档(research.md),包含库的对比、性能基准等

每一个技术决策都有记录的 rationale,追溯到具体的需求条目。这意味着当未来有人问"为什么选 SQLite 而不是 PostgreSQL",答案就在文档里,而不是丢失在 Slack 历史消息中。

Step 4: 拆解任务

/speckit.tasks

从 plan.md 出发,自动生成可执行的任务列表。关键特性:

  • 并行标记:独立任务会被标记 [P],标识可以安全并行的任务组
  • 依赖排序:有依赖关系的任务按正确顺序排列
  • 验收条件:每个任务都有明确的"完成标准"

输出是 specs/[branch-name]/tasks.md,一份结构化的执行清单。

Step 5: 执行实现

/speckit.implement

AI 按任务列表逐个实现。这个阶段的概念映射非常优雅:

  • 领域概念 → 数据模型
  • 用户故事 → API 端点
  • 验收场景 → 测试用例

测试不再是事后补的,而是从规格中"自然生长"出来的。因为验收条件在 spec 阶段就定义好了,implement 只是把它翻译成可执行的测试代码。

Step 6: 收敛对账

/speckit.converge

这是一个经常被忽视但极其重要的步骤:对比现有代码和 spec/plan/tasks,找出遗漏的工作项并追加为新任务。它回答的问题是:"我们生成的代码,真的实现了规格中定义的所有东西吗?"


进阶能力

Clarify:在计划之前消除模糊

/speckit.clarify

运行在 specify 之后、plan 之前。AI 会系统性地分析规格中的模糊点、矛盾点和遗漏点,然后向你提问。这就像有一个经验丰富的架构师帮你做 design review,但在你写一行代码之前。

Analyze:交叉一致性验证

/speckit.analyze

运行在 tasks 之后、implement 之前。它检查 spec、plan、tasks 三个文档之间的一致性:

  • spec 中的每个需求,在 plan 中都有对应的技术方案吗?
  • plan 中的每个设计决策,在 tasks 中都有对应的任务吗?
  • 有没有孤立的任务(不追溯到任何需求)?

这相当于"英文写的单元测试"——在写代码之前先验证文档的质量。

Checklist:质量门禁

/speckit.checklist

生成定制化的质量检查清单,验证需求的完整性、清晰度和一致性。可以被纳入 CI 流程,成为自动化的质量门禁。


Workflow 引擎:可编排的 SDD 流水线

Spec Kit 不只是提供孤立的命令,它还有一个完整的 Workflow 引擎,把多步骤流程编排成可重复、可暂停、可恢复的流水线。

内置的 Full SDD Cycle

Spec Kit 自带一个完整 SDD 循环工作流,把 specify → plan → tasks → implement 串联起来,中间插入人工审核门禁:

schema_version: "1.0"
workflow:
  id: "speckit"
  name: "Full SDD Cycle"
  description: "Runs specify → plan → tasks → implement with review gates"

steps:
  - id: specify
    command: speckit.specify
    input:
      args: "{{ inputs.spec }}"

  - id: review-spec
    type: gate
    message: "Review the generated spec before planning."
    options: [approve, reject]
    on_reject: abort

  - id: plan
    command: speckit.plan

  - id: review-plan
    type: gate
    message: "Review the plan before generating tasks."
    options: [approve, reject]
    on_reject: abort

  - id: tasks
    command: speckit.tasks

  - id: implement
    command: speckit.implement

一行命令启动:

specify workflow run speckit -i spec="构建一个看板系统,支持拖拽任务管理"

支持的步骤类型

Workflow 引擎支持 10 种步骤类型:

类型 用途
command 调用 Spec Kit 命令
prompt 向 AI 发送任意提示
shell 执行 shell 命令
init 引导新项目
gate 人工审核门禁
if 条件分支
switch 多路分发
while 条件循环
do-while 至少执行一次的循环
fan-out / fan-in 并行分发与结果聚合

状态持久化

每个 workflow run 都会持久化状态到 .specify/workflows/runs/<run_id>/

  • state.json — 当前运行状态和步骤进度
  • inputs.json — 已解析的输入值
  • log.jsonl — 逐步骤执行日志

这意味着当你在一个 gate 步骤暂停后,可以用 specify workflow resume <run_id> 从断点恢复。这在需要人工审核的场景中特别有用——你可以花一天时间审核 spec,然后一键继续。


实战效率对比

传统方式和 Spec Kit 方式的效率差异是显著的。以构建一个实时聊天功能为例:

传统方式:

步骤 耗时
写 PRD 文档 2-3 小时
创建设计文档 2-3 小时
手动搭建项目结构 30 分钟
写技术规格 3-4 小时
创建测试计划 2 小时
合计 约 12 小时

使用 Spec Kit:

步骤 耗时
/speckit.specify 写规格 5 分钟
/speckit.plan 做计划 5 分钟
/speckit.tasks 拆任务 5 分钟
合计 约 15 分钟

15 分钟内你得到了:完整的 feature 规格(含用户故事和验收标准)、详细的技术实现计划(含技术选型理由)、API 契约和数据模型、测试场景、所有文档都在 feature 分支中正确版本化。

当然,这不意味着 15 分钟就能上线一个聊天系统。后续的 implement、测试、调试仍然需要时间。但前置的文档和规划工作从 12 小时压缩到 15 分钟,这个量级的提升是实实在在的。


谁适合用 Spec Kit?

高度适配的场景

AI-Native 团队。 如果你已经在用 Copilot、Claude Code 或 Cursor 写代码,Spec Kit 是天然的升级——从"AI 帮你写函数"进化到"AI 帮你写整个 feature"。

提示词工程师。 SDD 的核心理念——"精确描述你要什么"——和提示词工程完全同构。规格本质上就是给 AI 的结构化提示词。

教学场景。 SDD 强制学生先想清楚"要什么"再动手,这培养了系统思维。学生不能跳过需求分析直接写代码,因为 Spec Kit 的流程不允许。

快速原型和 MVP。 "如果我改这个需求,重新实现要多久?"——在 SDD 中,答案是"改 spec,重新生成"。这使得探索多个技术方案的成本极低。

需要谨慎的场景

遗留系统改造。 Spec Kit 的价值在新项目中最大化。对于已有大量代码的遗留系统,你需要先为现有功能"补写"规格,才能享受 SDD 的好处——这个补写过程本身就很昂贵。

高度定制化的底层系统。 如果你写的是操作系统内核、编译器或数据库引擎,规格→代码的转换可能不如业务应用那么直接。


SDD 的深层启示

规格即提示词

站在提示词工程的视角看 SDD,会有一个有趣的发现:规格文档本质上就是给 AI 的结构化提示词。

  • Constitution = System Prompt(设定边界和规则)
  • Spec = User Prompt(描述具体任务)
  • Plan = Chain-of-Thought(让 AI 展示推理过程)
  • Tasks = Step-by-Step Decomposition(任务分解)
  • Converge = Self-Check(自我验证)

这意味着 SDD 最佳实践和提示词工程最佳实践高度重合。一个优秀的提示词工程师,天然就是优秀的规格编写者。

代码的终局

SDD 提出了一个深刻的问题:当代码可以从规格中自动生成时,代码还是资产吗?

在 SDD 的世界观中,代码更像是"编译产物"——可以随时从源头重新生成。真正的资产是规格、是团队对需求的理解、是架构决策的记录。

这意味着未来的开发者可能不再"写代码",而是"写规格"。代码变成了一种中间表示,就像我们不再手写汇编一样。

从 0 到 1,从 1 到 N

SDD 的流程本质上是:

0 (idea) → 1 (spec) → implementation → 1' (new spec) → new implementation → 2 → 3 → N

第一次实现是 0→1,后续的每次修改都是改规格、重新生成。同一个规格可以生成不同的实现(用不同的技术栈、优化不同的维度),就像同一个设计图纸可以盖出不同材料的房子。

这让"重新开始"不再昂贵——你不需要从代码中剥离旧逻辑,只需要修改规格的对应部分,然后重新生成。


快速上手

# 1. 安装 uv(如果没有的话)
curl -LsSf https://astral.sh/uv/install.sh | sh

# 2. 安装 Specify CLI(替换为最新版本号)
uv tool install specify-cli --from git+https://github.com/github/spec-kit.git@v0.8.5

# 3. 初始化项目
specify init my-project --integration copilot
cd my-project

# 4. 启动你的 AI 编码代理,然后依次运行:
# /speckit.constitution   ← 定义项目原则
# /speckit.specify        ← 写规格
# /speckit.clarify        ← 消除模糊点
# /speckit.plan           ← 做技术计划
# /speckit.analyze        ← 一致性检查
# /speckit.tasks          ← 拆任务
# /speckit.implement      ← 写代码
# /speckit.converge       ← 对账

或者用 Workflow 一步到位:

specify workflow run speckit -i spec="你的需求描述"

结语

Spec Kit 不是一个代码生成工具。它是一种开发哲学的载体——规格才是软件的真正源头,代码只是它的投影。

这个哲学并不新(形式化方法领域已经探索了几十年),但 AI 代码生成能力的成熟让它第一次变得可操作。当 GitHub 这样的平台级玩家开始投入,意味着这不只是实验性的尝试,而是软件工程范式转移的信号。

对于每一个在 AI 时代写代码的人来说,值得思考的问题是:你花在描述"要什么"上的时间,是否配得上它的重要性?

Spec Kit 给出的答案是:把最好的精力放在规格上,剩下的交给机器。


GitHub 仓库:github/spec-kit
官方文档:github.github.io/spec-kit

Views: 49

解码 Claude Code(七)— 深度报告:三个真实项目的完整复盘

前六期我们拆解了 Claude Code 的每一个核心模块。这一期,我们走进真实项目——不谈理论,只看结果。

三个案例来自 Anthropic 工程团队和社区开发者的第一手报告。它们规模不同、领域不同,但都回答了同一个问题:当 Claude Code 真正"上阵"的时候,会发生什么?

案例一:16 个 Claude 并行写 C 编译器

项目概况

2026 年 2 月,Anthropic 安全团队研究员 Nicholas Carlini 做了一个疯狂的实验:用 16 个 Claude 实例并行开发一个 C 编译器,目标是可以编译 Linux 内核。

最终结果:

  • 代码量:100,000 行 Rust
  • 会话数:近 2,000 个 Claude Code 会话
  • Token 消耗:20 亿输入 + 1.4 亿输出
  • 成本:约 20,000 美元
  • 能力:能编译 Linux 6.9(x86/ARM/RISC-V)、QEMU、FFmpeg、SQLite、PostgreSQL、Redis
  • 测试通过率:GCC torture test 套件 99%

这不是 demo,不是原型——这是一个能编译 Doom 的编译器。

架构设计:最简并行方案

Carlini 没有设计复杂的编排系统。整个架构只有三个组件:

1. 无限循环(Ralph Loop)

#!/bin/bash
while true; do
  COMMIT=$(git rev-parse --short=6 HEAD)
  LOGFILE="agent_logs/agent_${COMMIT}.log"
  claude --dangerously-skip-permissions \
    -p "$(cat AGENT_PROMPT.md)" \
    --model claude-opus-X-Y &> "$LOGFILE"
done

Claude 完成一个任务,立即开始下一个。它没有选择——循环永远不会停(除非 Claude 不小心执行了 pkill -9 bash 把自己杀了,这确实发生过一次)。

2. Git 文件锁实现任务分配

每个 agent 在 current_tasks/ 目录下创建文件来"锁定"任务。如果两个 agent 抢同一个任务,Git 的同步机制会强制第二个选别的。没有中心调度器,没有消息队列——就是文件系统 + Git。

3. 容器化隔离

每个 agent 运行在独立的 Docker 容器里,各自 clone 代码到本地,完成后 push 到上游仓库。合并冲突频繁发生,但 Claude 有能力自行解决。

关键发现

测试质量决定上限。 Carlini 反复强调:Claude 会不遗余力地解决你给它的任何问题,所以测试套件必须近乎完美,否则 Claude 会解错题。

他发现 Claude 会不断用新功能破坏已有功能,于是搭建了 CI 流水线,强制每次提交不能 break 现有测试。测试不是给自己写的——是给 Claude 写的。

站在 Claude 的角度设计工具。 测试输出不能刷屏(会污染上下文窗口),错误信息必须一行就能 grep 到(ERROR: 具体原因),日志要预计算汇总统计(免得 Claude 自己算一遍浪费时间)。

Claude 还有个致命弱点:无法感知时间。不加限制的话,它会花几个小时跑测试,而不是推进开发。解决方案是 --fast 模式:只跑 1%-10% 的随机抽样,既覆盖全部文件,又能快速定位回归。

并行不是银弹。 当所有 agent 面对同一个大问题时(比如编译 Linux 内核),16 个 agent 会卡在同一个 bug 上,互相覆盖修复。Carlini 的解法很巧妙:用 GCC 作为"对照编译器",随机分配文件给 GCC 和 Claude 的编译器,通过二分法定位哪些文件有问题,从而让不同 agent 修复不同 bug。

碰到的天花板

这个项目也暴露了 Opus 4.6 的极限:

  • 无法实现 16 位 x86 代码生成器(输出的代码超过 Linux 的 32K 限制)
  • 生成的代码效率远低于 GCC(即使开了全部优化,还不如 GCC 关优化)
  • Rust 代码质量合理,但远达不到专家水平
  • 新功能和修复经常破坏已有功能

Carlini 的总结很诚实:这个编译器"已经达到了 Opus 能力的极限"。

教训提炼

维度 教训
测试 测试不是验证工具,是导航工具。没有好测试,agent 会迷路
并行 任务独立时并行是免费的,任务耦合时并行反而有害
成本 2 万美元听起来贵,但比一个团队几个月的人力便宜一个数量级
架构 最简方案(文件锁 + Git)往往优于复杂编排系统
局限 即使是最强的模型,在专家级任务上仍有明显天花板

案例二:GAN 启发的三代理全栈开发

项目概况

2026 年 3 月,Anthropic Labs 团队的 Prithvi Rajasekaran 公开了一项研究:如何让 Claude 自主完成复杂的前端设计和全栈应用开发。

他的灵感来源出人意料——生成对抗网络(GAN)。

在 GAN 里,生成器负责产出,判别器负责挑剔。Rajasekaran 把这个结构搬到了 AI 编程中:一个 agent 写代码,另一个 agent 审代码,两者对抗迭代,直到质量达标。

从前端设计开始

问题很明确:Claude 默认倾向于产出"安全但无聊"的布局——技术上能用,但视觉上毫无记忆点。

Rajasekaran 设计了四个评分维度:

维度 权重 核心问题
设计品质 看起来是一个整体,还是零件拼凑?
原创性 有刻意的设计决策,还是模板默认值?
工艺 排版层级、间距一致性、色彩和谐度
功能性 用户能不能不猜就完成任务?

前两个权重更高,因为工艺和功能性 Claude 本来就做得不错,真正缺的是审美上的冒险。

然后他构建了对抗循环:

生成器:根据提示创建 HTML/CSS/JS
    ↓
评估器:用 Playwright 打开页面,截图、导航、逐维度打分、写详细批评
    ↓
生成器:根据批评修改,或彻底转向新的美学方向
    ↓
重复 5-15 轮

关键细节:评估器不是看静态截图打分,而是真的打开浏览器导航页面、截图、仔细研究后再评分。每轮迭代都有真实的墙钟时间,完整运行最长可达四小时。

最精彩的一刻

Rajasekaran 让 Claude 为一个荷兰艺术博物馆设计网站。前九轮迭代产出了一系列干净但中规中矩的暗色主题页面。

然后第十轮,Claude 推翻了之前所有的方向,重新想象了这个网站——它变成了一个空间体验:用 CSS perspective 渲染的 3D 房间,棋盘格地板,画作以自由位置挂在墙上,通过门道在画廊房间之间导航。

这是单次生成不可能出现的创意飞跃。

扩展到全栈开发

验证了生成器-评估器模式后,Rajasekaran 将其扩展为三代理系统:

规划器(Planner):接收 1-4 句话的用户描述,扩展为完整产品规格。关键约束——只描述"做什么"和"为什么",不规定"怎么做"。因为如果规划器在技术细节上猜错了,错误会级联传播到下游。

生成器(Generator):按功能一个接一个地实现(sprint 模式)。每个 sprint 结束后自我评估,然后交给评估器。技术栈固定:React + Vite + FastAPI + SQLite(后换为 PostgreSQL)。

评估器(Evaluator):不只是看代码——它打开应用,实际操作每个功能,记录 bug,写报告反馈给生成器。这一次,评估器真的在"使用"软件,而不是在"读"代码。

解决的三个核心问题

问题一:上下文腐烂。 长时间运行后,agent 开始遗忘早期指令,做出矛盾决策。早期用 Sonnet 4.5 时特别严重("上下文焦虑"——模型会提前结束工作)。Opus 4.5 基本消除了这个问题,配合自动 compaction 就够了。

问题二:自我评价偏差。 Agent 对自己产出的评价几乎总是正面的——即使明显平庸。把评价者和生产者分开后,评价可以校准为"挑剔"风格,而生成器有了具体的改进目标。

问题三:长任务失控。 将完整应用拆解为逐功能 sprint,每个 sprint 有明确的起止和验证条件。这比"一口气写完整个应用"靠谱得多。

教训提炼

维度 教训
评估 分离生成和评估是质量的关键杠杆
迭代 5-15 轮对抗迭代远优于单次生成
规划 规划器应约束"做什么"而非"怎么做"
创意 允许 agent 推翻方向,可能产生意外突破
成本 每次完整运行可达 4 小时,但产出质量显著高于一次性生成

案例三:Managed Agents — 从宠物到牲畜

项目概况

前两个案例都是研究实验。第三个案例是真正的生产系统——Anthropic 的 Managed Agents 托管服务。

这个故事的核心不是 Claude 多聪明,而是如何设计一个能持续运行的 AI agent 基础设施。

"宠物"问题

最初的架构很直觉:把所有东西塞进一个容器——Claude、运行 harness、执行沙箱、会话记录。

问题很快暴露:

  • 容器挂了 = 会话丢了(而且没地方调试)
  • harness 假设所有资源都在旁边(客户要求连接自己的 VPC 时就傻了)
  • 安全隐患:Claude 生成的不可信代码和密钥在同一个容器里(一次提示注入就能拿到 token)

这就是经典的"宠物"问题——你精心照料它,它挂了你很难受。

解耦方案:"大脑"和"手"

Anthropic 的解法来自操作系统设计哲学:像 Unix 把硬件抽象为文件一样,把 agent 组件抽象为接口。

大脑(Brain)= Claude + harness,负责思考和决策
手(Hands)= 沙箱和工具,负责执行
会话(Session)= 事件日志,独立存储

三者通过极简接口连接:

大脑 → 手:execute(name, input) → string
大脑 → 会话:emitEvent(id, event)
会话 → 大脑:getSession(id) / getEvents()

这意味着:

  • 容器挂了?大脑捕获错误,Claude 决定是否重试,新容器按标准配方重建
  • harness 挂了?新 harness 启动,从会话日志恢复,继续上次的事件
  • 客户要连接自己的 VPC?大脑不需要知道手在哪里,只需要调 execute

性能飞跃

解耦带来了意外收获:

  • 首 token 延迟(TTFT)中位数降低 60%,p95 降低超过 90%
  • 原因:之前每个会话都要等容器启动完成才能开始推理;现在推理可以先开始,容器按需创建

安全架构

密钥永远不出现在沙箱里:

  • Git 操作:sandbox 初始化时用 token clone 仓库,配置本地 git remote,之后 push/pull 不需要 token
  • MCP 工具:OAuth token 存在安全保险库,通过专用代理调用,harness 和沙箱都碰不到凭据
  • 原则:Claude 能"用"权限,但永远"看不到"凭据

教训提炼

维度 教训
架构 解耦大脑和手,让每个组件可以独立失败和替换
接口 设计少量稳定的抽象接口,比优化任何单一实现更重要
安全 凭据永远不应存在于不可信代码可达的地方
性能 延迟来自不必要的等待,而非计算本身
演进 为"尚未想到的程序"设计系统,接口比实现更持久

三个案例的共同脉络

把三个项目放在一起看,你会发现它们在说同一件事:

规律一:反馈闭环是第一生产力

C 编译器项目靠 CI 测试套件闭环,前端设计靠评估器打分闭环,Managed Agents 靠会话日志 + 错误恢复闭环。

没有闭环的 agent 就像没有方向盘的车——动力再强也没用。闭环越精确、越自动化,agent 的表现就越好。

规律二:管理上下文 = 管理 AI 的"智商"

C 编译器项目用 Git 文件锁隔离任务上下文,前端项目用三代理分工隔离角色上下文,Managed Agents 用会话日志解耦存储上下文。

三个项目的核心挑战都是同一个:随着任务变长,上下文窗口会被垃圾填满,模型的注意力被分散,性能下降。解决方案不是更大的上下文窗口——而是更聪明的上下文隔离。

规律三:最简架构往往赢

C 编译器没有复杂编排,只有文件锁 + Git。前端项目没有微服务,只有三个 agent + 一个循环。Managed Agents 的核心就是三个接口。

这不是巧合。在 AI agent 领域,模型的智力在飞速增长,但 harness 编码的假设会迅速过时。越简单的架构,越容易适配新一代模型。

规律四:评估比生成更难

三个项目都花了大量精力在"怎么评判结果好不好"上——而不是"怎么让 Claude 写出结果"。

C 编译器的测试套件、前端项目的四维评分体系、Managed Agents 的会话恢复机制——这些才是真正的工程挑战。生成代码 Claude 已经很擅长了,但告诉它"你做得好不好"仍然需要人类精心设计。

用户的真实感受

社区开发者 @svpino 在用 Claude Code 构建了一个完整的 SaaS 应用后写道:

"我用 Claude Code 写了一个从前端到数据库的完整应用。期间我只做了一件事:坐在旁边看它工作,偶尔在它走偏的时候拉一下。这种感觉就像你在驾驶一辆自动驾驶汽车——你知道它大部分时间在正确行驶,但你随时准备接管方向盘。"

另一位开发者 @swyx 的总结更精炼:

"Claude Code 改变的不是你写代码的速度,而是你思考代码的方式。你不再想'怎么实现这个功能',而是想'怎么描述这个功能才能让 AI 做对'。这是一个元认知层面的转变。"

展望:从工具到伙伴

三个案例揭示了一个趋势:Claude Code 正在从"工具"进化为"伙伴"。

C 编译器项目展示了它的极限能力——在结构良好的环境里,它已经可以完成专家级的工程任务。前端项目展示了它的创意潜力——在对抗迭代的驱动下,它能做出超越预期的设计决策。Managed Agents 展示了它的工程成熟度——在生产环境里,它已经可以作为可靠的基础设施运行。

但所有案例也指向同一个瓶颈:AI 仍然需要一个精心设计的环境才能发挥最大潜力。测试、评估、反馈、上下文管理——这些"脚手架"决定了 AI 的天花板。

下一期,也是本系列的最后一期,我们将跳出具体案例,看看 AI 编程的未来。Karpathy 预言的 Software 3.0 时代,Boris Cherny 心中的终极开发体验,以及 Anthropic 对 AI 编程的长期愿景。


系列导航

参考来源

Views: 19

解码 Claude Code(六)— 实战技巧:从 Boris 和团队偷师的 30 条黄金法则

不是官方文档,不是营销话术。这是一个每天用 AI 写 100% 代码的人,用半年时间摸索出来的真实经验。

写在前面

前五期我们聊了 Claude Code 的起源、架构、记忆系统、技能和多代理协作。这一期换个节奏——不讲理论,只讲实操。

这篇文章的素材来自 Boris Cherny(Claude Code 创造者)在 2026 年 1-4 月发布的四组技巧分享,以及 Anthropic 团队成员 Thariq 关于会话管理的深度指南。我把它们重新组织成 6 个主题,30 条具体可执行的建议。

每一条都有出处,每一条都经过 Anthropic 内部团队的日常验证。

Coding Tips

一、并行是一切的起点

Boris 反复强调:并行是最大的生产力提升,没有之一。

1. 同时跑 5 个 Claude

Boris 的日常:5 个终端窗口,每个运行一个独立的 Claude Code 实例。一个重构代码,一个写测试,一个搜索依赖,一个审查 PR,一个处理 bug 报告。

具体操作:用 git worktree 创建 5 个独立的工作树,每个窗口一个。这样 5 个 Claude 互不干扰,各自操作各自的代码副本。

# 创建 worktree
git worktree add ../feature-a feature-a
git worktree add ../feature-b feature-b

# 在每个 worktree 里启动 Claude
cd ../feature-a && claude
cd ../feature-b && claude

或者用更简单的方式:claude -w 一键在 worktree 中启动。

2. 本地 + 云端双线作战

5 个本地 Claude 还不够?再开 5-10 个云端实例。claude.ai/code 支持在浏览器里运行 Claude Code,用 /teleport 可以在本地终端和云端之间无缝切换。

Boris 的组合拳:5 个本地 + 10 个云端 = 同时 15 个 Claude 在干活。

3. 把”每天做两次的事”变成斜杠命令

如果某个操作你一天要做两次以上,把它变成一条斜杠命令。

---
name: commit-push-pr
description: "提交代码、推送、创建 PR"
---

执行以下步骤:
1. 运行测试
2. git add 所有变更
3. 根据变更内容生成 commit message
4. git push
5. 创建 Pull Request

Boris 的 /commit-push-pr 命令可能是他用得最多的一条——每天执行几十次。

4. 用 /loop 把重复工作自动化

/loop 是 Boris 最喜欢的"隐藏功能"之一。它可以让 Claude 按固定间隔自动执行任务,最长持续一周。

他的日常配置:

/loop 5m /babysit          → 每5分钟自动处理PR review
/loop 30m /slack-feedback  → 每30分钟把Slack反馈变成PR
/loop 1h /pr-pruner        → 每小时清理过期PR

把技能和 loop 组合起来,就变成了一个 7x24 小时工作的 AI 助手。

二、验证闭环:最重要的一条

Boris 说过一句话,被整个社区反复引用:

给 Claude 验证自己工作的方式,效果提升 2-3 倍。这是获得高质量输出的最重要单一因素。

5. Claude 测试每一次变更

Boris 每次让 Claude 写完代码后,都会让它自己测试。不是"帮我看看有没有问题"——而是"运行测试,确保通过"。

这是他从 Meta 带来的习惯:代码质量不是审查出来的,是验证出来的。

6. 前端必须给 Claude 浏览器

让 Claude 写前端代码但不给它浏览器,就像让设计师蒙着眼睛画画。

Chrome 扩展是 Boris 做前端时的标配。Claude 写完代码后自动打开浏览器截图,对比设计稿,发现差异后自动修复。这个循环一直持续到页面看起来"对了"为止。

7. 用”挑战式提示”逼迫 Claude 自审

不要只说"帮我写这个功能"。试试这样说:

"审查这段代码,不要创建 PR,直到我通过你的测试。"

或者:

"向我证明这个方案有效。对比 main 分支和当前分支的行为差异。"

Boris 把这叫做"让 Claude 当你的审查者"——反向利用 AI 的能力来提升输出质量。

8. 失败后不要纠正,要重写

当一个修复方案"勉强能用"时,Boris 会说:

"基于你现在知道的一切,扔掉这个方案,实现那个优雅的解法。"

这个技巧的底层逻辑是:Claude 在尝试过程中学到了很多关于代码库的上下文,但它当前的实现可能只是在最初的错误假设上打补丁。让它带着新知识重新来过,往往能得到更好的结果。

9. 让 Claude 修复大多数 bug

不需要手把手教。直接说"修复失败的 CI 测试",或者把 Slack 里的 bug 线程贴给 Claude,只说一个字:"修。"

Claude 可以读日志、分析堆栈、定位代码、提出修复方案、运行测试验证。整个过程你只需要审查最终结果。

三、会话管理:对抗”上下文腐烂”

这一节的素材来自 Thariq(Anthropic 团队成员),他给出了目前最系统的会话管理指南。

10. 理解 Context Rot

即使有 1M token 的上下文窗口,模型性能也不是线性的。大约在 300-400k token 时,模型开始被无关信息干扰——注意力被分散到越来越多的 token 上,旧的不相关内容开始影响当前的判断。

这就是 Context Rot(上下文腐烂)。

11. 每个回合结束都是一个决策点

Claude 完成一个回合后,你有 5 个选择:

选项 上下文保留 适用场景
Continue 保留全部 同一任务,上下文仍然相关
Rewind 保留前半,丢弃后半 Claude 走错方向了
/compact 有损摘要 中期任务,需要清理冗余
/clear 只保留你写的 brief 全新任务
Subagent 主上下文 + 最终结果 会产生大量中间输出的任务

12. Rewind > 纠正

这是 Thariq 最推荐的习惯。

当 Claude 尝试方案 A 失败了,你的直觉可能是说"不对,试方案 B"。但这会把失败的方案 A 和你的纠正都留在上下文里。

更好的做法是 Rewind(双击 Esc):回退到失败尝试之前,用你学到的信息重新提示。

纠正后:上下文 = 5个文件读取 + 2次失败尝试 + 2次纠正 + 最终修复
回退后:上下文 = 5个文件读取 + 1个有经验的提示 + 最终修复

上下文更干净,模型的注意力更集中。

13. Compact 是中期任务的救星

当会话变长但你不想从头来过,/compact 是最好的选择。它会要求 Claude 摘要当前对话,然后用摘要替换历史。

关键技巧:用提示词引导 compact 的方向

/compact 保留认证重构的细节,丢弃测试调试的过程

不引导的 compact 可能会丢失重要信息——因为模型在做 compact 时处于"最不聪明"的状态(上下文已经很满了)。

14. 主动 compact,不要等到自动触发

等到自动 compact 触发时,模型已经处于 Context Rot 状态,摘要质量会下降。

正确做法:在你觉得上下文开始膨胀但模型还没变笨的时候,主动执行 /compact,带上方向提示。

四、CLAUDE.md:投资回报率最高的 5 分钟

15. 每次纠错后更新 CLAUDE.md

Boris 的原话:

每次你纠正 Claude 后,以这句话结尾:"更新你的 CLAUDE.md,确保你不再犯这个错误。"

Claude 非常擅长为自己写规则。它会精确地提取错误的模式,写成可执行的指令。

16. 团队共享,通过 PR 协作更新

CLAUDE.md 不应该是某个人的私有文件。Boris 的团队把它检入 git,通过 PR 协作更新。

一个更有趣的做法:在同事的 PR 上 @claude,让 Claude 在 review 过程中自动更新 CLAUDE.md。Boris 把这叫做"复利工程"——每次代码审查都在为未来的 AI 辅助投资。

17. 持续迭代直到错误率可测量地下降

CLAUDE.md 不是写一次就完事的。Boris 建议:

  1. 用一周时间记录 Claude 犯的所有错误
  2. 为每类错误添加一条规则
  3. 再用一周观察错误率是否下降
  4. 重复直到效果显著

这个过程可能需要几轮迭代,但每一轮都在让 Claude 变得更好。

18. 用 notes 目录积累项目知识

一个 Anthropic 工程师的做法:让 Claude 为每个任务/项目维护一个 notes 目录,每次 PR 后更新。然后在 CLAUDE.md 里指向这个目录。

这样 CLAUDE.md 本身保持简洁(只放规则和约定),而详细的项目知识存在 notes 里,按需加载。

五、工具和环境优化

19. 用 Opus + Thinking 处理一切

这听起来违反直觉——Opus 比 Sonnet 慢,为什么还要用?

Boris 的解释:虽然单次响应更慢,但因为 Opus 犯错更少、工具使用更准确,你需要纠错的次数大幅减少。总耗时反而更短。

这就像开车走高速 vs 走小路:高速看起来绕远了,但因为不用等红灯,总时间更短。

20. 用 PostToolUse Hook 自动格式化代码

Claude 生成的代码通常格式良好,但最后 10% 可能和项目的 lint 规则不一致。一个简单的 Hook 就能解决:

"PostToolUse": [{
  "matcher": "Write|Edit",
  "hooks": [{
    "type": "command",
    "command": "bun run format || true"
  }]
}]

每次 Claude 写入或编辑文件后自动格式化,CI 再也不会因为格式问题失败。

21. 预授权权限,不要跳过权限检查

--dangerously-skip-permissions 看起来很方便,但 Boris 坚决反对。正确做法是用 /permissions 预先授权已知的安全操作:

{
  "permissions": {
    "allow": [
      "Bash(npm test*)",
      "Bash(npm run lint*)",
      "Bash(git status*)",
      "Bash(git diff*)"
    ]
  }
}

把这些规则检入 settings.json,整个团队共享。

22. 给 Claude 接入你所有的工具

通过 MCP,Claude 可以访问 Slack、BigQuery、Sentry、GitHub 等所有团队工具。Boris 已经 6 个月没写过一行 SQL 了——所有数据查询都通过 Claude + BigQuery 完成。

配置方法:在 .mcp.json 中定义 MCP 服务器,检入 git 共享。

23. 语音输入:说得比打得快 3 倍

Boris 大部分代码是"说"出来的,不是"打"出来的。

语音输入的好处不只是速度——它让你的 prompt 自然变得更详细。打字时你会下意识压缩信息,说话时你会自然补充更多上下文。而 prompt 越详细,Claude 的输出越好。

终端里运行 /voice,然后按住空格键说话。macOS 上也可以双击 fn 键触发系统听写。

24. --bare 让 SDK 启动快 10 倍

用 Claude Code 做 CI/CD 或自动化时,默认会搜索所有 CLAUDE.md、settings 和 MCP 配置。加上 --bare 跳过这些搜索,启动速度提升 10 倍:

claude -p "总结这个代码库" \
  --output-format=stream-json \
  --bare

Boris 透露,未来的版本会把 --bare 变成默认行为——因为它在非交互场景下几乎总是更好的选择。

六、高级工作流

25. /batch:大规模变更的核武器

需要把一个重构应用到几十甚至几百个文件?/batch 会先和你确认方案,然后自动分发到数十/数百个 worktree agent 并行执行。

每个 agent 在独立的代码副本上工作,完成后自动合并。这是 Claude Code 处理大规模代码迁移的终极工具。

26. 用 Hooks 挂载到 Agent 生命周期

Hooks 让你在 Claude 的关键节点执行自定义逻辑:

  • SessionStart:每次启动时动态加载上下文
  • PreToolUse:记录模型执行的所有 bash 命令
  • Stop:Claude 停止时"戳"它一下让它继续

第三个特别有用——长时间运行的任务中,Claude 有时会过早停止。用 Stop Hook 自动推送它继续,直到任务真正完成。

27. 子代理不只是”分工”,更是”上下文隔离”

子代理最大的价值不是并行执行——而是上下文隔离。

当你知道接下来的一块工作会产生大量中间输出(20 次文件读取、12 次 grep、3 条死路),而这些输出你之后不再需要——把它交给子代理。只有最终结论会返回主上下文。

判断标准很简单:我之后还需要这些工具输出吗?不需要就丢给子代理。

28. 会话分支:探索不同方向的安全网

/branch 从当前会话分叉出一个新方向。原来的会话完好无损,你可以随时切回来。

适用场景:一个方案不确定能不能走通?先 branch 一下,在分支里试。失败了切回来,零损失。

29. 跨仓库工作:--add-dir

当你需要同时操作多个代码仓库时,用 --add-dir 把其他目录加入 Claude 的工作范围:

claude --add-dir ../shared-libs --add-dir ../api-gateway

这不仅让 Claude "看到"这些仓库,还自动授予了操作权限。

30. 用 Explanatory 模式学新东西

Claude Code 不只是写代码的工具,也是学习工具。在 /config 里切换到 "Explanatory" 或 "Learning" 输出风格,Claude 会在每次变更时解释"为什么这么做"。

还可以让它:
- 生成 HTML 幻灯片解释不熟悉的代码
- 画 ASCII 图描述新协议和代码架构
- 构建间隔重复学习技能——你解释理解,Claude 提问补漏洞


总结:30 条法则的底层逻辑

把 30 条技巧摊开看,你会发现它们都围绕三个核心原则:

原则一:给 AI 反馈闭环。 验证工作(5-9)是最重要的一组技巧。没有反馈的 AI 就像没有方向盘的车——动力再强也没用。

原则二:管理上下文就是管理 AI 的"智商"。 会话管理(10-14)、CLAUDE.md(15-18)、子代理(27)都在做同一件事——确保模型的注意力集中在正确的事情上。

原则三:自动化一切重复操作。 斜杠命令(3)、/loop(4)、Hooks(26)、权限预授权(21)——把人类从重复劳动中解放出来,让 AI 处理 AI 最擅长的事。

这三条原则不只适用于 Claude Code。它们是 2026 年"AI 辅助开发"这个领域的通用方法论。不管你用什么工具,只要你记住这三条,就能显著提升 AI 编程的效率和质量。


系列导航

下期预告:真正的项目是怎么用 Claude Code 完成的?从天气应用到大规模重构,从个人 side project 到 Anthropic 内部的生产系统。第七期,我们走进真实案例。

Views: 6

Views: 26

Docker容器化遗留应用(五):综合案例

Docker容器化遗留应用(五):综合案例

Docker容器化

系列导读

这是《Docker容器化遗留应用》系列的最后一篇,前面介绍了容器化理论和实战案例,本篇将通过一个真实的遗留CRM系统容器化案例,展示完整流程。


遗留CRM系统容器化案例

系统架构

原始架构(单体应用):

  • Apache web服务器
  • PHP 7.2后端
  • MySQL 5.7数据库
  • 所有组件耦合在一起

目标

  • 提升扩展性(应对流量高峰)
  • 提高维护性(独立更新组件)
  • 加快部署效率(从小时到分钟)

步骤一:组件隔离

# docker-compose.yml
version: '3.8'

services:
  # 反向代理
  nginx:
    image: nginx:alpine
    ports:
      - "80:80"
    volumes:
      - ./nginx.conf:/etc/nginx/nginx.conf:ro
    networks:
      - crm-network

  # PHP后端
  php:
    build: ./php
    volumes:
      - ./html:/var/www/html
    networks:
      - crm-network

  # 数据库
  database:
    image: mysql:5.7
    environment:
      MYSQL_ROOT_PASSWORD: ${DB_PASSWORD}
    volumes:
      - mysql-data:/var/lib/mysql
    networks:
      - crm-network

  # 会话管理
  redis:
    image: redis:alpine
    networks:
      - crm-network

networks:
  crm-network:

volumes:
  mysql-data:

步骤二:数据迁移

# 导出现有数据
mysqldump -u root -p crm > crm_backup.sql

# 启动新容器
docker compose up -d

# 导入数据
docker exec -i crm-database-1 mysql -u root -p${DB_PASSWORD} crm < crm_backup.sql

步骤三:测试与部署

# 功能测试
docker run --rm selenium/standalone-chrome python tests/ui_tests.py

# 性能测试
jmeter -n -t crm_load_test.jmx

# 安全测试
docker run --rm owasp/zap2docker-stable zap-baseline.py -t http://crm-app

效果对比:容器化前后

指标 容器化前 容器化后 提升幅度
部署时间 2小时 2分钟 98% ↓
回滚时间 1小时 10秒 99.9% ↓
资源利用率 15% 70% 366% ↑
扩展速度 30分钟/台 5秒/容器 99.7% ↓
环境差异bug 每月3-5个 0 100% ↓

总结:容器化不是万能药,但是良药

获得的好处

  • 环境一致性:告别"在我机器上能跑"
  • 快速扩展:应对流量高峰不再是噩梦
  • 提升部署效率:从小时级到分钟级
  • 降低运维成本:自动化管理

需要注意

  • ⚠️ 有状态应用(数据库)需要特殊处理
  • ⚠️ 安全配置不能忽视
  • ⚠️ 监控和日志必须跟上
  • ⚠️ 团队需要学习新技术栈

下一步行动

从最简单的Web服务器开始,先在测试环境练手,积累经验后再处理复杂系统。

记住:容器化是一场马拉松,不是百米冲刺。


系列总结

《Docker容器化遗留应用》系列完整内容

  1. (一)为什么要容器化 - 理解容器化优势
  2. (二)容器化三步走 - 掌握基本操作
  3. (三)网络与数据管理 - 理解核心概念
  4. (四)实战案例 - 学习真实场景
  5. (五)综合案例 ← 当前

参考资源


恭喜你完成了整个系列!你的遗留应用已经准备好迎接新生了!

Views: 24

Docker容器化遗留应用(四):实战案例

Docker容器化遗留应用(四):实战案例

Docker容器化

系列导读

这是《Docker容器化遗留应用》系列的第四篇,前几篇介绍了容器化基础,本篇将通过实战案例演示如何容器化真实应用。


案例1:Apache服务器容器化

场景描述

一个运行了5年的Apache服务器,配置复杂,依赖特定版本的PHP模块。需要在不修改代码的情况下容器化。

步骤一:准备工作

mkdir dockerized-apache && cd dockerized-apache

步骤二:编写Dockerfile

FROM ubuntu:20.04

# 避免交互式提示
ENV DEBIAN_FRONTEND=noninteractive

# 安装Apache和PHP
RUN apt-get update && \
    apt-get install -y apache2 php libapache2-mod-php && \
    apt-get clean && \
    rm -rf /var/lib/apt/lists/*

# 复制配置文件
COPY ./my-httpd.conf /etc/apache2/apache2.conf
COPY ./html/ /var/www/html/

# 暴露端口
EXPOSE 80

# 启动Apache(前台运行)
CMD ["apachectl", "-D", "FOREGROUND"]

步骤三:构建与运行

# 构建镜像
docker build -t dockerized-apache .

# 运行容器
docker run -d -p 8080:80 --name my-apache dockerized-apache

# 测试访问
curl http://localhost:8080

案例2:数据库容器化

开发环境 vs 生产环境

环境 推荐方案 理由
开发 容器化数据库 快速启停,易于重置
测试 容器化数据库 隔离测试数据
生产 托管数据库服务 自动备份、高可用

数据迁移:平滑过渡

# 从现有数据库导出数据
mysqldump -u root -p mydb > backup.sql

# 启动新的MySQL容器
docker run -d --name my-mysql \
  -e MYSQL_ROOT_PASSWORD=mypassword \
  -v mysql-data:/var/lib/mysql \
  mysql:8.0

# 导入数据
docker exec -i my-mysql mysql -u root -pmypassword < backup.sql

配置灵活性

# 开发环境:使用容器化数据库
docker run -d --name dev-db \
  -e MYSQL_ROOT_PASSWORD=dev mysql:8.0

# 生产环境:连接托管数据库
docker run -d --name prod-app \
  -e DB_HOST=my-rds-instance.amazonaws.com \
  -e DB_PASSWORD=${DB_PASSWORD} \
  my-app

配置与环境变量管理

环境变量注入

# 通过-e参数注入
docker run -d --name my-app \
  -e DB_HOST=database.local \
  -e DB_PASSWORD=${DB_PASSWORD} \
  my-application

使用.env文件

# .env文件
DB_HOST=database.local
DB_PASSWORD=supersecret
API_KEY=abc123
# docker-compose.yml
services:
  app:
    image: my-application
    environment:
      - DB_HOST=${DB_HOST}
      - DB_PASSWORD=${DB_PASSWORD}

配置文件挂载

# 挂载主机配置文件
docker run -d --name my-app \
  -v /path/to/config:/app/config:ro \
  my-application

安全提示:敏感信息不要硬编码在Dockerfile中,使用环境变量或密钥管理服务。


安全加固措施

1. 镜像安全

# 使用Docker Scout扫描漏洞
docker scout cves my-legacy-app

# 使用Clair扫描
docker run --rm -v /var/run/docker.sock:/var/run/docker.sock \
  arminc/clair-local-scan my-legacy-app

2. 最小权限原则

# 创建非root用户
RUN useradd -m myuser

# 切换到非root用户
USER myuser

# 设置工作目录
WORKDIR /home/myuser

3. 能力限制

# 删除所有能力,仅添加必要的
docker run -d --name my-app \
  --cap-drop=all \
  --cap-add=net_bind_service \
  my-application

4. 只读挂载

# 保护配置文件不被篡改
docker run -d --name my-app \
  -v /path/to/config:/app/config:ro \
  my-application

5. 监控与日志

# 查看容器日志
docker logs -f my-app

# 实时监控资源使用
docker stats my-app

下篇预告

下一篇:《Docker容器化遗留应用(五):综合案例》

将详细介绍:

  • 遗留CRM系统容器化全流程
  • 系统架构拆分
  • 测试与部署
  • 效果对比

系列导航

  • (一)为什么要容器化 - 容器化优势与基本概念
  • (二)容器化三步走 - 从零到一的实践指南
  • (三)网络与数据管理 - 容器间通信与持久化
  • (四)实战案例 ← 当前
  • (五)综合案例 - 遗留CRM系统容器化全流程

通过实战案例,你已经掌握了容器化的核心技术!

Views: 7