TriliumNext × WechatSync 多平台发布 开发文档
这个项目是什么
trilium-wechatsync 是一套桥接服务 + TriliumNext 补丁:让你在 TriliumNext 笔记里写好一篇文章后,点一下就能发布到知乎、微信公众号、CSDN、掘金、B站、头条、百家号、小红书等 20+ 中国内容平台,并在 /publish 发布控制台实时看到各平台登录状态、发布结果和草稿编辑链接。
注意它和 jinghui/wechatsync(Chrome 扩展 fork)是两个仓库:那个是浏览器扩展本体,本仓库是让 TriliumNext 调用扩展能力的桥接与打补丁方案,不含扩展代码。
架构
浏览器 /publish 页面
① HTTP POST /api/publisher/publish
→ TriliumNext 服务(Docker 或裸机)
② HTTP(9601)
→ 桥接服务器 wechatsync-server.mjs(WS 9600 / HTTP 9601)
③ WebSocket(9600)
→ Chrome + WechatSync 扩展(各平台已登录)
④ 扩展调用平台官方接口
→ 知乎 / 公众号 / CSDN / …
为什么必须有桥接这一层:WechatSync 的 CLI 只能以 SECONDARY 模式短暂运行,而 Chrome 后台页约 40 秒会被休眠导致 WebSocket 断连。桥接服务器常驻 PRIMARY 模式,扩展只连一次即可长期在线(25 秒心跳保活),并把各平台登录状态缓存下来,供 Trilium 侧随时查询。
技术栈与架构分层
- 桥接服务器:Node.js ESM 脚本(
bridge/wechatsync-server.mjs),同时提供 WebSocket(默认 9600)与 HTTP API(默认 9601),由 systemd 常驻。 - TriliumNext 侧补丁:两份 TypeScript(服务端发布逻辑、API 路由)+ 一份前端页面(
publish.html发布控制台),通过patch/patch.sh覆盖进 TriliumNext 源码并重新构建。 - CLI:
@wechatsync/cli(npm 全局包),由 Trilium 服务端调用,通过SYNC_WS_HOST指向桥接。 - MCP:
mcp/MCP_INTEGRATION.md记录 MCP Server 集成方式。
仓库结构
trilium-wechatsync/
├── install.sh # 桥接一键安装(systemd + Token)
├── bridge/
│ ├── wechatsync-server.mjs # 常驻桥接服务器(PRIMARY 模式)
│ ├── wechatsync-bridge.service # systemd 服务单元
│ └── wechatsync-bridge-wrapper.sh
├── patch/
│ ├── wechatsync.ts # → apps/server/src/services/publisher/wechatsync.ts
│ ├── publisher_frontend.ts # → apps/server/src/routes/api/publisher_frontend.ts
│ ├── publish.html # → apps/client/public/publish.html
│ └── patch.sh # 应用补丁 + Docker 路径修正
└── mcp/
└── MCP_INTEGRATION.md # MCP Server 集成说明
安装与本地开发
桥接装在宿主机(不是容器里):
sudo bash install.sh
安装脚本做五件事:把 wechatsync-server.mjs 复制到 /usr/local/share/wechatsync-bridge/;生成并安装 wechatsync-bridge.service 到 /etc/systemd/system/(端口可用环境变量 SYNC_WS_PORT 覆盖,默认 9600);首次运行生成 Token 写入 /etc/wechatsync-token.conf(权限 600);systemctl restart wechatsync-bridge 启动服务并检查存活;最后检查 Docker 容器内是否装了 CLI。HTTP 端口 = WS 端口 + 1(默认 9601)。
给 TriliumNext 打补丁:
bash patch/patch.sh /path/to/triliumnext
安装 CLI(Trilium 跑在 Docker 里就要装进同一个容器):
npm install -g @wechatsync/cli
docker exec triliumnext npm install -g @wechatsync/cli
配置项说明
| 配置项 | 含义 | 默认值 |
|---|---|---|
SYNC_WS_PORT |
桥接 WebSocket 端口(install.sh 可覆盖) |
9600 |
| 桥接 HTTP 端口 | CLI / Trilium 调用的 REST 端口,等于 WS 端口 +1 | 9601 |
/etc/wechatsync-token.conf |
桥接鉴权 Token(base64 存储,填进扩展设置) | 首次安装自动生成 |
host.docker.internal |
Trilium 在容器内访问宿主机桥接的默认主机名 | 代码默认 |
BRIDGE_HOST |
Trilium 裸机运行时的桥接地址环境变量 | localhost |
SYNC_WS_HOST |
注入给 CLI 的桥接主机名 | host.docker.internal |
| 扩展设置「服务器地址」 | Chrome 扩展连接的 WebSocket 地址 | ws://<NAS_IP>:9600 |
Docker 网络关键点
Trilium 在容器、桥接在宿主机时,容器里的 localhost 指向容器自己,访问不到宿主机服务,必须用 Docker 内置 DNS host.docker.internal(宿主机网关 172.17.0.1)。本仓库所有代码默认按此约定:
wechatsync.ts的checkBridge()请求http://host.docker.internal:9601/status;publisher_frontend.ts的platform-status请求http://host.docker.internal:9601/platforms;- CLI 调用注入
SYNC_WS_HOST=host.docker.internal。
宿主机裸跑 Trilium 时设置 BRIDGE_HOST=localhost 即可。
二次开发要点
- 改容器内文件必须重启容器:Node 启动时只把代码加载进内存一次,改
main.cjs之类的文件不重启不生效。 - 断连降级:桥接或扩展断开时,
platform-status返回缓存状态并标注「📦 缓存」,页面不会一片空白;发布请求最多重试 5 次等待扩展连上。 - URL 提取与重试逻辑都在
patch/wechatsync.ts里,改发布行为从这个文件入手,别直接改 Trilium 源码(下次patch.sh会覆盖)。 - 已知问题:什么值得买(SMZDM)因扩展侧缺 CSRF token 发布报错;头条号 / 小红书 / 什么值得买不在扩展原生
listPlatforms()中,可发布但登录状态显示「❓ 未知」。
相关链接
- Gitea 仓库:http://127.0.0.1:3200/jinghui/trilium-wechatsync
- 上游扩展:https://github.com/wechatsync/WechatSync
- 协议:MIT