WeWrite架构:Prompt负责判断、Python负责确定性的3层解耦设计
【免费下载链接】wewrite公众号内容全流程 Skill,从热点抓取到微信草稿箱,一句话跑完整条内容管道项目地址: https://gitcode.com/gh_mirrors/wew/wewrite
WeWrite 架构把一个公众号内容全流程 Skill 拆成三层:Prompt 层负责选题、事实与表达的判断,Python 层负责打分、排版、发布等确定性操作,State 层把用户数据隔离在~/.wewrite/。这种「判断与执行分离」的设计,让新手也能看懂 AI 内容管道为什么既灵活又可靠。
一张图看懂 WeWrite 三层解耦架构
设计原则只有一句话:prompt 负责判断,Python 负责确定性。整个项目目录与三层一一对应:
| 层 | 位置 | 职责 |
|---|---|---|
| Prompt 层 | skills/ 下 10 个自包含 skill | 选题、事实、观点、实用性与表达判断 |
| Runtime 层 | src/wewrite/(pip 包wewriteCLI) | 打分、转 HTML、调微信 API、生图、成本路由 |
| State 层 | ~/.wewrite/(可用WEWRITE_HOME覆盖) | 凭证、风格、历史、学习产物、输出文件,全部在仓库外 |
你说「写一篇公众号文章」 │ ▼ Prompt 层:抓热点 → 选题评分 → 任务书 → 初稿 → 编辑审稿(判断) │ ▼ Python 层:wewrite score / preview / publish(确定性操作) │ ▼ State 层:~/.wewrite/runs/<run_id>/ 保存每一步产物(可恢复)三者的关系可以这样理解:Prompt 像总编辑,Python 像印刷厂,State 像档案室。
Prompt 层:10 个自包含 Skill 如何承载判断逻辑
Prompt 层的实体是 skills/ 下的 10 个 skill 目录:主入口 skills/wewrite/SKILL.md 加上选题、写作、审稿、配图、排版发布、学习、数据、改写、风格 9 个专项模块。
每个 skill 是一个自包含目录:SKILL.md写清触发条件与流程,references/放详细规则。以审稿为例,skills/wewrite-review/SKILL.md 定义了「准确、观点、有用、合声、好读」五项判断标准,以及pass / revise / needs_input三种结论和两轮复审上限——这些判断标准是纯文字契约,由模型在运行时理解执行。
一个关键细节:Prompt 只输出决策,不直接动外部世界。例如审稿 Skill 决定「可发布」后,真正执行推送的是 Python 层的wewrite publish命令,且必须先通过wewrite run permission publish allow拿到用户明确授权。判断归判断,执行归执行,边界清晰。
Python 层:CLI 调度器与三类确定性操作
Runtime 层的入口是 src/wewrite/cli.py 里的命令调度器。它只做一件事:「子命令名 → 模块」映射并透传参数,把 16 个子命令分发到 commands/ 与 toolkit/,本身不重复定义任何参数。
确定性操作集中在三类:
排版转换:同输入必同输出
toolkit/converter.py 的convert方法把 Markdown 经过固定管线转成微信兼容 HTML:容器块预处理 → 中英文自动加空格 → 代码块增强 → 列表转 section → 外链转脚注 → 内联 CSS 注入。每一步都是机械规则,没有任何「看情况」。
主题加载同样确定:toolkit/theme.py 的load_theme按「用户主题目录 → 内置 themes/」固定顺序搜索 18 个 YAML 主题,文件缺失或字段不全就明确报错,而不是随机降级。
任务状态机:原子写与字段保护
commands/run_manager.py 的run子命令管理每篇文章的独立任务:创建、恢复、封存、授权。底层的 runs.py 用临时文件 +os.replace原子写状态,避免半截文件;PROTECTED_ARTICACTS一类保护字段确保正文封存后不可被下游悄悄改写。
机械检查:只提示,不越权
wewrite score做 11 项机械检查,定位套话、碎句、重复节奏等风险。注意它的定位:分数只提示问题,是否改稿仍由 Prompt 层的编辑判断决定——这正是三层分工的缩影。
State 层:把用户数据移出仓库的 paths.py
paths.py 是整个 State 层的唯一枢纽:所有用户状态(凭证、风格、历史、学习产物、输出)统一放在$WEWRITE_HOME(默认~/.wewrite),CLI 和 skill 都通过它解析路径。ensure_home幂等地创建output、runs、exemplars、lessons、themes等标准子目录。
每篇文章再用独立任务目录隔离:契约见 skills/wewrite/references/pipeline-state.md。runs/<run_id>/state.yaml记录步骤状态、发布授权与产物路径(brief.yaml、claims.yaml、draft.md、article.md等),下游模块只读当前任务内的路径,多篇并行互不覆盖。
三层如何协作:一次「继续上次」的完整链路
状态机把三层串起来,跑通一次「继续上次的文章」:
- Agent 读 skills/wewrite/SKILL.md 的路由表,判断这是恢复任务而非新建(Prompt 层)
- 运行
wewrite run list,唯一确定后wewrite run resume <run_id>(Python 层) - 恢复
runs/<run_id>/state.yaml里的进度,只重做失败或未完成步骤(State 层) - 步骤完成后
wewrite run step <name> completed,最终wewrite run finish封存正文并写入历史
上午选完题,下午说「继续上次」就能接上,靠的就是这条链路。
解耦带来的三个实际好处
- Skill 复制即用:skill 目录自包含,复制到任何 Agent 的 skills 目录就能工作,不依赖仓库其他部分
- CLI 独立升级:CLI 是独立 pip 包,与 skill 分开安装、分开升级,互不牵连
- 换机器零成本:用户状态全部在
~/.wewrite/,换机器只需带走这一个目录——风格、学习成果、历史文章一个不少
小结:关键文件路径速查
WeWrite 架构的核心,就是把「不确定性的判断」和「确定性的执行」放进不同层,再用 State 层把用户数据彻底隔离。想深入某个环节,从这些入口看起:
- 状态目录解析:src/wewrite/paths.py
- 命令调度器:src/wewrite/cli.py
- 任务状态机:src/wewrite/commands/run_manager.py
- 排版转换引擎:src/wewrite/toolkit/converter.py
- 主题系统:src/wewrite/toolkit/theme.py
- 主入口 Skill:skills/wewrite/SKILL.md
- 任务状态契约:skills/wewrite/references/pipeline-state.md
【免费下载链接】wewrite公众号内容全流程 Skill,从热点抓取到微信草稿箱,一句话跑完整条内容管道项目地址: https://gitcode.com/gh_mirrors/wew/wewrite
创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考