OpenCLI 学习 04:Harness 目录与文件分工

1. 为什么我在这一部分容易混乱

因为一个 harness 目录里通常会同时出现:

  • 设计文档
  • README
  • Skill
  • CLI 入口
  • core 业务模块
  • utils 后端桥接
  • tests

如果不先按职责区分,很容易把这些文件都看成“某种说明文档”或者“某种脚本入口”。

2. 一个标准 harness 的结构

我目前可以把一个标准 harness 粗略理解成:

<software>/
└── agent-harness/
    ├── <SOFTWARE>.md
    ├── setup.py
    └── cli_anything/
        └── <software>/
            ├── __main__.py
            ├── README.md
            ├── <software>_cli.py
            ├── core/
            ├── utils/
            ├── tests/
            └── skills/

3. 每一层是干什么的

<SOFTWARE>.md

例如:

  • GIMP.md
  • LIBREOFFICE.md

它不是主要给 Agent 调用时读的。

它更像:

  • 设计分析文档
  • 软件专项 SOP
  • 说明为什么 harness 要这样设计

通常会写:

  • 软件本体怎么工作
  • GUI 操作怎么映射到 CLI
  • 为什么选这种后端策略
  • 项目模型如何设计

所以它更偏开发者/维护者视角。

setup.py

它负责:

  • 包怎么安装
  • 安装后命令叫什么
  • 依赖有哪些

也就是把这个 harness 变成一个真正可安装的 CLI 工具。

README.md

这是给人类用户看的使用说明。

通常会写:

  • 怎么安装
  • 怎么运行
  • 有哪些命令
  • 示例命令是什么

所以它偏“人类可读”。

<software>_cli.py

这是最关键的运行入口文件。

它负责:

  • 定义命令树
  • 定义参数
  • 解析 CLI 输入
  • 调用 core
  • 输出结果
  • 处理错误

所以它不是“说明怎么用”的文档,而是:

真的被执行的 CLI 入口代码。

core/

这是业务逻辑层。

里面一般按领域拆模块,例如:

  • document.py
  • writer.py
  • export.py
  • session.py

它负责真正的数据处理、状态变化、业务规则和导出策略。

utils/

这是工具层和后端桥接层。

最关键的通常是 backend 文件,例如:

  • gimp_backend.py
  • lo_backend.py

它负责:

  • 找真实软件
  • 组装命令
  • 调用 subprocess
  • 检查输出文件

所以它是 harness 和真实软件之间的桥。

tests/

测试目录一般包括:

  • test_core.py
  • test_full_e2e.py
  • TEST.md

作用分别是:

  • 单元测试
  • 端到端测试
  • 测试计划与测试结果记录

这部分是为了证明 harness 不是“看起来能用”,而是真的可验证。

skills/SKILL.md

这个才是真正偏给 Agent 读的说明文档。

它主要告诉 Agent:

  • 这个 harness 是干什么的
  • 适合什么场景
  • 什么时候应该调用
  • 有哪些命令组
  • 调用时有哪些注意事项

所以它更偏 Agent 视角。

4. 我目前对三个关键文档的区分

<SOFTWARE>.md

  • 回答:为什么这样设计
  • 偏开发/维护视角

README.md

  • 回答:人类怎么使用
  • 偏用户视角

SKILL.md

  • 回答:Agent 什么时候该调用、如何调用
  • 偏 Agent 视角

5. 我目前对 <software>_cli.py 的理解

它不是文档,而是执行入口。

也就是说,当用户或 Agent 真的输入:

cli-anything-libreoffice export render report.pdf

最后就是 libreoffice_cli.py 里对应的命令函数被执行。

所以它负责的是:

  • 接受命令
  • 调用业务逻辑
  • 返回结果

6. 当前我的一句话总结

一个 harness 目录本质上是在把“设计说明、运行入口、业务逻辑、后端桥接、测试验证、Agent 说明”打包到一起。

而我现在最重要的区分是:

  • <SOFTWARE>.md 不是给 Agent 主要调用时读的
  • SKILL.md 才是更偏给 Agent 使用的说明
  • <software>_cli.py 是真正执行命令的入口代码

Read more

MCP 服务端的隐藏设计:结论性数据如何改变

Agent 的工作方式 我们以为 MCP 服务只是查数据的管道,拆开一看,发现服务端已经把分析结论都算好了。这个发现改变了我对 Agent 架构的理解。 起因:一次对 MCP 服务的逆向探索 最近在研究 MCP(Model Context Protocol)的实际应用,我选了一个真实的商业 MCP 服务 —— 某电商卖家流量分析平台作为研究对象。该服务提供了 27 个工具,覆盖关键词分析、流量运营、广告洞察等领域。 最初的预期很简单:MCP 服务就是一个数据接口,Agent(LLM)调用它拿到原始数据,然后自己分析、得出结论、给用户建议。 实际拆开一看,完全不是这么回事。 第一个发现:返回数据里藏着完整的分析结论 我写了一个 Python 脚本,绕过所有 AI 客户端,直接用

By ladydd

FastAPI 异步任务服务的并发设计演进:从单进程轮询到多 Worker 协程直处理

本文记录了一个 FastAPI 异步任务服务在并发架构上的思考和演进过程。这个服务的本质很简单:接收客户端请求,转发给下游 AI API,把结果存起来供客户端轮询。它不做复杂的业务计算,不做数据聚合,就是一个纯转发层——接活、派活、存结果。正因为场景足够简单,我们才有机会做一次化繁为简的架构妥协,把原本"看起来该用任务队列"的设计砍到只剩三行核心配置。 一、先说清楚场景:我们到底在干什么 这个服务做的事情可以用一句话概括: 客户端提交参数 → 服务转发给下游 AI API → 等结果 → 存 Redis → 客户端来取。 关键特征: * 纯 IO 转发:服务本身不做任何 CPU 密集计算,所有耗时都花在等下游 API 返回。一次调用几秒到几十秒不等,全是网络等待。 * 异步模式:客户端提交任务后立即拿到 task_id,

By ladydd

从连上一个 MCP 服务到理解 AI 系统的工程本质

一次从"会用"到"理解原理"再到"能优化"的完整探索记录。 本文记录了我通过实际动手连接一个远程 MCP 服务(SIF —— 亚马逊卖家流量分析平台),一步步深入理解 MCP 协议机制、LLM 上下文管理、注意力资源分配、以及工具编排优化方案的全过程。 一、起点:连上一个真实的 MCP 服务 什么是 MCP? MCP(Model Context Protocol)是 Anthropic 主导设计的一个开放协议,目的是标准化 AI 应用与外部工具/数据源之间的通信方式。你可以把它理解为"AI 世界的 USB 接口"

By ladydd
陕公网安备61011302002223号 | 陕ICP备2025083092号