本节只讨论一件事:Shell Engineering 的开发阶段和运行阶段。
1.1 传统开发中的两个阶段
开始一个 Shell Engineering 项目之前,先搞清楚一件事:你现在是在开发,还是在运行。
在传统开发里,这两个阶段分得非常清楚。
开发阶段
假设你要用 Python 做一个项目。开发阶段,你在 PyCharm 或 VS Code 里写代码,用 pip 管理依赖,用 pytest 写测试。这个阶段的核心任务就是:写代码、调试、确保功能正确。
运行阶段
开发完了,代码要跑到用户手里。但"运行"的含义,取决于你做的是什么:
| 项目类型 | 运行方式 | 交付物 | 用户怎么用 |
|---|---|---|---|
| Web 应用 | 部署到服务器 | 一个网址 | 打开浏览器访问,不需要下载任何东西 |
| 库 / 组件 | 发布到 PyPI | 一个包名 | 其他开发者 pip install,在你的代码之上继续开发 |
| 桌面应用 / App | 打包分发 | .exe / .dmg / .apk | 下载安装,双击图标就能用 |
不管哪种形式,有一条规则是一样的:运行时不调源代码。 用户拿到的是编译后的产物、打包好的文件、或者一个远程服务。没有人会把 .py 源码直接发给最终用户。
你可能会想:开源项目不就是把源码给用户吗?没错,但那是"分发",不是"运行"。运行阶段关心的是代码怎么跑起来,而不是代码长什么样。
所以,我们可以看到,传统时代的软件开发和运行流程是比较明确的,开发阶段是有明确交付物的。开发阶段和运行阶段泾渭分明。
1.2 Agent 时代的开发和运行阶段
但到了 Agent 时代,很多人反而搞不清楚了。Shell Engineering 到底有没有开发阶段和运行阶段?好像从头到尾都是在和 Hermes 对话,那到底什么算开发,什么算运行?
回想一下我们在第八章做的映画系统。我们从头到尾都在和 Hermes 对话,让它理解需求、写代码、测试功能。整个过程就是一场接一场的对话,我们并没有刻意去区分"现在是在开发"还是"现在是在运行"。写完一个功能就测一下,测完发现不对就改,改完再测。开发和运行混在一起,边做边用。
这样做有没有问题?对于映画系统来说,没什么问题。因为我们从一开始就把它定位为个人使用的工具,并不打算发布出去给别人用。
这就好比你给自己写了一个 Web 项目。你可以在本机直接跑起来,自己用,不需要部署到远程服务器,不需要考虑负载均衡,不需要打包成 Docker 镜像。你能这么做,是因为你既是开发者也是唯一的用户。
映画系统也是同样的道理。我们没有区分开发阶段和运行阶段,不是因为这两个阶段不存在,而是因为我们没有交付的需求。
但这不等于 Shell Engineering 没有开发阶段和运行阶段。一旦你要把这个系统交付给另一个人使用,难度就会提升很多个量级。
这个问题值得你想一想。
现在换一个场景。假如我们准备把胶囊系统发布出去,让其他人也能用。那么你需要认真想一想:
- 胶囊系统的开发阶段包含哪些工作?开发阶段需要用到哪些工具?
- 运行阶段又是什么?运行阶段需要用到哪些工具?
- 开发阶段结束时,你交付的到底是什么?是代码?是 Skill 文件?还是一份 SPEC 文档?
- 你要把这个系统交给一个用户使用。你给他什么?给他一整套开发文件,让他自己搭环境?还是给他一个打包好的东西,装上就能用?
在继续往下读之前,不妨先停下来想一想上面这些问题。不用给出标准答案,先有自己的思考。等后面讲完 SPEC、OpenSpec、SDD 这些概念,你会自然地知道答案。
1.3 ■ 学点英语
| 中文 | English | 音标 | 说明 |
|---|---|---|---|
| Python 语言 | Python | /ˈpaɪθɑːn/ | 常用于脚本、自动化和后端开发的编程语言 |
| Python 测试框架 | pytest | /ˈpaɪ test/ | 用来编写和运行 Python 自动化测试的框架 |
| Python 软件包索引 | PyPI | /ˌpaɪ piː ˈaɪ/ | Python 社区发布和获取第三方软件包的平台 |
| 集成开发环境 | PyCharm | /ˈpaɪ tʃɑːrm/ | 面向 Python 开发的集成开发工具 |
| 代码编辑器 | VS Code | /ˌviː es ˈkoʊd/ | 支持扩展、调试和多种语言的代码编辑器 |
| 容器平台 | Docker | /ˈdɑːkər/ | 用容器封装应用及其运行环境的工具 |