Novel Publisher — 多平台小说发布器
Overview
A self-contained, local-first publishing engine that pushes novel chapters to four
Chinese platforms: 番茄小说 / 微信公众号 / 微博 / B站. It solves the core constraint
that browser-based pages cannot carry a user's Cookie across origins (CORS), so real
publishing must run through a local Python engine that holds credentials and proxies
each platform's API.
The bundled project lives in assets/novel-publisher/ and contains:
- server.py — local HTTP engine (binds 127.0.0.1:8765 only)
- publisher/ — one adapter per platform (base.py, tomato.py, wechat.py, weibo.py, bilibili.py)
- web/index.html — publishing UI (credential config / chapter management / one-click publish / status)
- config.json.example — credential template
Verified interface details, auth methods, and known pitfalls are in references/platforms.md.
When to Use
- User asks to publish novel chapters to 番茄 / 公众号 / 微博 / B站, automatically or semi-automatically.
- User wants a "novel publisher" / "发布器" rather than just a scheduling dashboard.
- User already has a draft and wants it pushed to one or more platforms.
- User wants to extend the engine with another platform adapter.
Do not use this skill for: platforms with no open publish API (起点/晋江/知乎/七猫/豆瓣阅读) —
for those, only produce formatted copy for manual paste.
Architecture (read before changing anything)
Browser (web/index.html) ──HTTP──▶ Local server.py (127.0.0.1:8765)
│ reads config.json (credentials, LOCAL ONLY)
├─▶ publisher/tomato.py → fanqienovel.com
├─▶ publisher/wechat.py → api.weixin.qq.com (draft)
├─▶ publisher/weibo.py → api.weibo.com (share)
└─▶ publisher/bilibili.py → api.bilibili.com (draft)
- Credentials live only in local
config.json; the web UI never receives them. - The web page communicates with
server.pyvia plain JSON endpoints (/api/status,
/api/config,/api/novels,/api/novel,/api/publish).
Quick Start
- Copy the bundled project to the user's chosen workspace:
assets/novel-publisher/→(用户工作区)/novel-publisher/ - Create credentials file:
cp config.json.example config.json, then fill in each
platform's fields (see Credential Setup below). - Start the engine:
python server.py(managed Python:
C:\Users\Administrator\.workbuddy\binaries\python\versions\3.13.12\python.exe). - Open
http://127.0.0.1:8765in a browser. - Keep
general.dry_run: truefirst to preview what would be sent without making
real requests; flip tofalseonly after verifying credentials.
Platform Capabilities
| Platform | Automation | Endpoint | Notes |
|---|---|---|---|
| 番茄小说 | ✅ real auto | author backend HTTP | 2-step publish; auto use_ai=2 (keep it) |
| 微信公众号 | ⚠️ draft only | draft/add |
freepublish/submit recycled for personal accts → manual final click |
| 微博 | ✅ direct | statuses/share |
needs OAuth access_token (app + auth) |
| B站 | ✅ draft | article/creative/draft/addupdate |
wild API; bili_jct auto-extracted from cookie |
Credential Setup (per platform)
- 番茄: log into the author backend, copy the full request
Cookie, and grab the
X-Secsdk-Csrf-Tokenfrom any publish request header. Cookie expires ~1–2 months. - 公众号: WeChat Official Account
appid+appsecret(from the MP admin console). - 微博: create an open-platform app, authorize, obtain
access_token. - B站: log in, copy the full
Cookie;bili_jct(CSRF) is auto-extracted from it.
Publishing Flow
- In the UI, add a chapter (title / content / summary / tags / optional
book_id). - Select target platform(s) and click publish.
- The engine sends the request through the matching adapter and returns
ok/ error
per platform. On failure it returns a clear message — it never crashes the request. - For 公众号 / B站, finish the last step manually in the platform's web console.
Security
- Credentials are stored only in local
config.json; they are never uploaded or
exposed to the browser/frontend. - The server binds to
127.0.0.1only — not reachable from other machines. use_ai=2on 番茄 is mandatory for compliance; do not strip it.- This engine pushes to the user's own accounts; respect each platform's ToS and any
exclusivity clauses in publishing contracts before cross-posting.
Troubleshooting
- Server won't start / status 502: a stale
server.pyprocess may hold the port,
or the local HTTP proxy intercepts127.0.0.1. Kill old processes and run with
NO_PROXY=127.0.0.1,localhost/HTTP_PROXY=unset. - All platforms show "not configured":
config.jsonmissing or empty — copy from
config.json.exampleand fill it. - 番茄 publish fails with auth error: Cookie expired → re-capture
Cookie+
X-Secsdk-Csrf-Token. - Other known bugs and their fixes are documented in
references/platforms.md.
Extending (add a platform)
- Add a new adapter
publisher/{name}.pysubclassingPublisherBase(frombase.py):
implement_do_publish(chapter)returning aPublishResult, and_dry_publishfor
preview. Setself.name,configuredproperty, and option lists. - Register it in
server.py'sbuild_publishers()with its config key. - Add the credential fields to
config.json.exampleand the platform to the UI dropdown. - Keep credentials local; never send them to the frontend.
Resources
assets/novel-publisher/— the full runnable engine (copy to workspace and run).references/platforms.md— verified endpoints, auth, and the bug-fix log.