
AnyGen CLI Harness 测试体系深度解析从 63 项测试到三类真实工作流验证【免费下载链接】CLI-AnythingCLI-Anything: Making ALL Software Agent-Native -- CLI-Hub: https://clianything.cc/项目地址: https://gitcode.com/GitHub_Trending/cl/CLI-Anything本指南围绕 AnyGen 云内容生成平台的 CLI 封装层cli-anything-anygen测试文档展开完整梳理其 63 项自动化测试的分层设计、mock 策略、E2E 验证路径与真实业务场景回放方法并结合源码剖析配置解析、任务生命周期、会话管理、导出校验等被测功能的底层实现帮助开发者理解如何为Agent 原生的 HTTP API CLI 构建可离线运行、可面向真实服务验证的测试矩阵。一、测试资产总览9 个测试类、63 项测试的双层结构AnyGen 是一个运行在服务端的异步内容生成平台通过 REST API 生产 PPT、DOCX、网页、故事书、SmartDraw 图表与数据分析报告。与本地 GUI 目标不同CLI 本身不承担渲染职责其测试策略因此呈现出鲜明的双层特征。TEST.md 给出的测试资产清单一目了然文件测试类数量测试数量覆盖重点test_core.py645配置、任务创建、轮询、会话、导出校验的单元测试test_full_e2e.py318E2E API 测试 CLI 子进程测试合计963两层测试的边界定义非常清晰可以从测试文件首行 docstring 直接确认test_core.py —— Unit tests for AnyGen CLI — mocked HTTP, no API key needed. 所有单元测试都使用 mock 的 HTTP 响应不发起真实 API 调用因此不需要 API key可以在任何 CI 环境离线运行。test_full_e2e.py —— E2E tests for AnyGen CLI — require ANYGEN_API_KEY for real API calls. 需要设置ANYGEN_API_KEY环境变量用于对真实云端服务做端到端验证。这套分层方法本质上遵循了经典的测试金字塔底层用 mock 覆盖所有参数构造、错误分支与边界条件快速、稳定、无成本上层用真实 API 验证端到端链路少量、慢速、但对可用性最关键。二、单元测试深入剖析6 个测试类的职责与实现佐证2.1 TestConfig —— 配置解析与 API Key 优先级6 项配置测试覆盖了 CLI 配置层的核心行为。对应实现位于 anygen_backend.py配置文件加载与保存load_config()从~/.config/anygen/config.json读取文件不存在时返回空字典。测试中通过patch(...CONFIG_FILE...)注入临时路径验证读写往返。save_config()在保存时会创建目录并以chmod(0o600)设置权限保护 API key。API key 三级优先级CLI 参数 环境变量 配置文件。get_api_key()的实现顺序是先返回非空cli_key否则读ANYGEN_API_KEY环境变量最后回退到load_config().get(api_key)。对应测试test_api_key_priority_cli_arg与test_api_key_priority_env分别验证前两级。损坏配置文件容错load_config()捕获JSONDecodeError与IOError损坏时返回{}不让 CLI 崩溃。认证 token 构造_make_auth_token()会智能判断——key 已带Bearer前缀则原样返回否则自动补前缀test_make_auth_token_bare/test_make_auth_token_already_bearer。缺失 key 的异常_require_api_key(None)抛出带完整引导信息的RuntimeError提示三种提供 key 的途径--api-key、环境变量、config set。2.2 TestCreateTask —— 请求体构造与错误路径8 项测试对应create_task()的实现见 anygen_backend.py。这些测试不仅验证返回值还通过mock_post.call_args[1][json]直接断言发送出去的请求体test_create_slide_task验证slide操作会携带slide_count等参数。test_create_invalid_operation操作类型校验。VALID_OPERATIONS [chat, slide, doc, storybook, data_analysis, website, smart_draw]传入非法值抛出ValueError。test_create_with_file_tokensfile_tokens被原样放入请求体供任务引用已上传文件。test_create_with_stylestyle会被拼接到 prompt 末尾形成Style requirement: ...后缀——这是 style 参数的实现细节请求体中没有独立 style 字段而是注入 prompt。错误路径双分支HTTP 状态码非 200 抛RuntimeError(...HTTP 500...)HTTP 200 但successfalse时取error字段抛出模拟配额超限等业务错误。test_create_saves_local_recordtask.py的create_task()会在调用 API 后把任务记录写入~/.cli-anything-anygen/tasks/{task_id}.json见 core/task.py实现本地任务历史。2.3 TestQueryTask —— 状态查询5 项测试针对非阻塞的query_task()验证返回完整 task dict含status、progress、outputcompleted 状态能解析出file_url/file_nameHTTP 错误抛异常。本地记录的更新发生在 core/task.py 的包装层每次查询都会把最新状态回写本地记录。2.4 TestPollTask —— 轮询核心循环8 项测试集中验证 CLI 的阻塞式轮询引擎poll_task()anygen_backend.py这是整个 CLI 最重要的运行时机制循环直至完成通过mock_query.side_effect依次注入running(30%) → running(70%) → completed(100%)三种状态断言返回 completed 且sleep被调用 2 次——正好对应两次状态切换之间的等待。超时max_time默认 1200 秒20 分钟interval默认 3 秒。测试用mock_time.side_effect [0, 0, 9999]伪造时钟跳变触发TimeoutError。失败短路任一查询返回failed立即抛RuntimeError携带服务端 error 信息。进度回调on_progress(status, progress_pct)只在进度变化时被调用防止无意义的重复回调。瞬时失败容忍与自定义参数max_time/interval均可由调用方覆盖。轮询完成后task.py 会补写completed_at时间戳并持久化最终状态。2.5 TestSession —— 会话与撤销/重做10 项测试覆盖 core/session.py 的Session类它为 REPL 提供命令历史与 undo/redo 能力record()追加历史并清空 redo 栈新操作使之前的撤销失效这由test_undo_clears_redo_on_record验证。undo()弹出最后一条历史移入 redo 栈redo()反向操作空栈时两者都返回None。history(limit20)支持截取最近 N 条status()返回history_count/can_undo/can_redo/redo_count。会话持久化save()/_load()序列化 history 与 redo 栈到 JSON会话文件默认位于~/.cli-anything-anygen/session.json见 anygen_cli.py。写盘使用_locked_save_json()通过fcntl.flock独占锁实现原子写入防止并发损坏。test_load_corrupt_file验证坏 JSON 静默降级为空会话而非崩溃。2.6 TestExportVerify —— 下载产物完整性校验8 项测试对应 core/export.py 的verify_file()。由于渲染发生在服务端CLI 拿到文件后必须做最后一道质检扩展名校验方式判定要点.pptx/.docx/.xlsxZIP 魔数PK\x03\x04 解包包内须含[Content_Types].xml才算合法 OOXML否则记为普通 ZIP.pdf文件头%PDF-5 字节 magic bytes.png文件头\x89PNG\r\n\x1a\n8 字节签名.svg读取前 500 字符文本须含svg标签.xml/.drawio文本首字符以?xml或开头.jsonjson.load可解析测试还覆盖空文件size0判 invalid、缺失文件File not found、坏 ZIPBadZipFile捕获返回corrupt_zip。返回值统一为{valid, format, file_size, details}E2E 测试正是靠它做最终断言。三、E2E 测试面向真实云端服务的三条链路test_full_e2e.py 的运行前提是设置合法 keyANYGEN_API_KEYsk-xxx python3 -m pytest cli_anything/anygen/tests/test_full_e2e.py -v -s未设置时requires_api_key装饰器pytest.mark.skipif自动跳过全部 18 项保证 CI 中无 key 也不至于失败。3.1 TestSlideWorkflow 与 TestDocWorkflow两套测试结构对称各 6 项验证 slidePPTX与 docDOCX两条完整链路。核心是run_full_workflow()驱动的create → poll → download端到端流程result run_full_workflow( API_KEY, slide, Create a brief 3-slide presentation about CLI tools, output_dirstr(tmp_path), slide_count3, )断言链条包括任务状态为completed、本地文件存在、文件大小 1KBsize 1000的合理性检查防止下载到空壳文件、verify_file()返回 valid 且格式正确。这两条测试验证了平台两个最常用的内容生产方向——汇报演示与文档写作。3.2 TestCLISubprocess —— 以真实子进程验证 CLI 契约6 项测试不直接 import 模块而是通过subprocess.run()调用真实 CLI 命令test_full_e2e.py。CLI 可执行文件的解析逻辑_resolve_cli()值得注意优先使用 PATH 中已安装的cli-anything-anygen命令若设置了CLI_ANYTHING_FORCE_INSTALLED1但命令缺失直接报错提示pip install -e .否则回退到python3 -m cli_anything.anygen.anygen_cli方便开发期运行。CLI_ANYTHING_FORCE_INSTALLED1 ANYGEN_API_KEYsk-xxx python3 -m pytest cli_anything/anygen/tests/test_full_e2e.py -v -s验证的 CLI 契约点包括--help退出码为 0 且输出包含 AnyGen--json config path输出可解析 JSON 且含path字段--json task list输出 JSON 数组本地任务历史--json session status输出含history_counttask create --operation slide --prompt ...需 key返回task_id完整task run子进程链路需 key产出本地文件并通过格式校验。这类以 JSON 为标准协议的断言直接呼应了 CLI 的 Agent 友好设计——ANYGEN.md 明确说明结构化的--json输出让 Agent 可以解析 task_id、status 与文件路径这是 Agent 无法自行组合多步 HTTP 工作流auth → upload → prepare → create → poll → download时选择 CLI 封装的根本原因。四、真实业务场景回放三类工作流验证模式TEST.md 第三部分给出了三组超越单测的场景级验证模板模拟真实用户如何借助 CLI 完成工作。它们共同的价值是把多个 API 调用串成业务剧本验证的不再是单个函数而是整个使用体验。Scenario 1季度业务复盘 PPTQuarterly Business Review Deck模拟角色基于数据制作演示文稿的高管操作编排upload file → prepare (multi-turn) → create slide → poll → download验证点产物为合法 PPTX、大小 0、是真实的 OOXML ZIP。此场景演示了最完整的能力栈先file upload上传数据文件换取file_token再用task prepare做多轮需求澄清服务端会返回reply、status与suggested_task_params见 anygen_backend.py最后把澄清结果与文件引用一起交给task create。Scenario 2技术设计文档Technical Design Document模拟角色生成设计文档的工程师操作编排create doc → poll → download → verify DOCX验证点DOCX 是合法 ZIP/OOXML内含Content_Types.xml。这条链路对应最简路径也是 CLI 单条命令task run --operation doc的完整等价物。Scenario 3架构图Architecture Diagram模拟角色绘制系统架构图操作编排create smart_draw → poll → download产物为 drawio/excalidraw验证点输出是合法 XMLdrawio或 JSONexcalidraw。smart_draw属于DOWNLOADABLE_OPERATIONS {slide, doc, smart_draw}见 anygen_backend.py其产物通过.drawio/.xmlXML 校验与.jsonJSON 校验路径被verify_file()覆盖。这三类场景恰好映射到 AnyGen 支持的可下载产物全集合二进制办公文档OOXML、矢量图片PDF/PNG/SVG、结构化绘图文件drawio XML / excalidraw JSON。export.py 的分支结构就是为这三大类产物设计的。五、测试体系的设计启示与工程化要点5.1 无 key 也能跑mock 隔离是 CI 底线45 项单元测试通过unittest.mock.patch把requests.post/requests.get/time.sleep/time.time全部替换从而离线、确定性地验证请求体构造是否包含正确参数轮询状态机running→completed / failed / timeout是否正确迁移错误如何被归类为ValueError参数错或RuntimeError服务错。这使得单元测试可以进任何 CI而把真金白银的 API 调用限定在需要ANYGEN_API_KEY的 E2E 层。5.2 用verify_file兜底远程产物质量因为渲染完全在服务端网络传输可能造成截断或损坏E2E 断言中反复出现文件 1KB verify_file()valid的组合。这是对远程生成内容型 CLI 特别有价值的防线不信任 HTTP 200 本身而是校验产物魔数与容器结构。5.3 双入口测试import 与 subprocess 缺一不可E2E 层同时保留Python import 直调与子进程黑盒调用两种测试形式。前者利于调试与断言精度后者才是对终端用户/Agent 真实使用方式的忠实模拟——尤其验证了_resolve_cli()对安装版命令与开发模块两种入口的兼容。5.4 本地记录让异步任务可追溯~/.cli-anything-anygen/tasks/*.json记录每个任务的 prompt、operation、状态流转、输出元数据与本地文件路径格式见 ANYGEN.md 中的.anygen-task.json示例。task list/session history命令与相应测试共同保证了即使云端任务早已结束本地依然可以复盘什么时候、用什么 prompt、产出了什么文件。5.5 如何运行完整测试在 agent-harness 目录下安装依赖后先跑离线单测python3 -m pytest cli_anything/anygen/tests/test_core.py -v再执行带真实 key 的 E2E 套件需先通过config set api_key sk-xxx或环境变量提供凭证key 可在 anygen 平台 Integration 设置页获取ANYGEN_API_KEYsk-xxx python3 -m pytest cli_anything/anygen/tests/test_full_e2e.py -v -s六、从测试反推被测对象架构速览测试文档的价值不止于验证了什么还在于它精准描绘了被测系统的形态。结合 ANYGEN.md 的架构图与cli命令组定义anygen_cli.py可以还原出完整的 CLI 表面cli-anything-anygen ├── task │ ├── create # 创建生成任务返回 task_id/task_url写本地记录 │ ├── status # 非阻塞查询 │ ├── poll # 阻塞轮询至完成可自动下载 │ ├── download # 下载产物 │ ├── thumbnail # 下载缩略图 │ ├── run # 全流程 create→poll→download │ ├── list # 本地任务历史 │ └── prepare # 多轮需求澄清 ├── file upload # 上传参考文件 → file_token ├── config # set/get/delete/pathAPI key 管理 ├── session # status/history/undo/redo └── repl # 交互式命令行全局--json标志切换 JSON 输出--api-key提供最高优先级的凭证注入。所有命令的错误处理统一由handle_error装饰器完成捕获FileNotFoundError/ValueError/RuntimeError/TimeoutErrorJSON 模式下输出结构化 error 对象非 REPL 下以退出码 1 结束。总结这份 63 项测试的文档完整定义了 cli-anything-anygen 的质量边界45 项 mock 单测锁定参数构造、状态机、会话与文件校验的确定性行为18 项 E2E 测试打通 PPTX/DOCX 两条云端生产链路并以真实子进程守住 CLI 契约三组场景模板则沉淀了数据驱动的 PPT、文档撰写、图表绘制三类可复用的业务验证剧本。对于任何正在为云服务构建 Agent 原生 CLI 的开发者这套离线单测守边界 真实 E2E 守链路 场景剧本守体验的测试分层都是可以直接借鉴的工程范本。【免费下载链接】CLI-AnythingCLI-Anything: Making ALL Software Agent-Native -- CLI-Hub: https://clianything.cc/项目地址: https://gitcode.com/GitHub_Trending/cl/CLI-Anything创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考