时间:2026-03-16 10:50
人气:
作者:admin

做自媒体最痛苦的事情不是写内容,而是写完之后要在 5-7 个平台上重复发一遍。
小红书要 emoji 和话题标签,微信公众号要 HTML 内联样式,知乎不能用 Markdown 符号,微博限制 300 字,B站专栏又是另一套编辑器,CSDN 支持 Markdown 但有自己的发布流程,掘金需要选分类和标签……
同一篇内容,改编 7 次,发布 7 次,调格式 7 次。
作为一个程序员,我决定让 AI Agent 帮我干这件事。花了两周时间,我搭了一套基于 AI Agent 的多平台自动分发系统。现在只需要说一句"帮我发布到全平台",Agent 就会自动改编内容、生成配图、逐平台发布。
这篇文章记录整个架构设计、技术选型和踩过的坑,希望对有类似需求的同学有帮助。

整个系统分为三层:
┌─────────────────────────────────────────────────┐
│ 指令层(用户输入) │
│ "写一篇关于 AI Agent 的文章,发到全平台" │
├─────────────────────────────────────────────────┤
│ 编排层(AI Agent) │
│ ┌───────────┐ ┌───────────┐ ┌───────────────┐ │
│ │ 内容生成 │ │ 平台改编 │ │ 配图生成 │ │
│ │ & 写作 │ │ & 格式转换 │ │ (SiliconFlow) │ │
│ └───────────┘ └───────────┘ └───────────────┘ │
├─────────────────────────────────────────────────┤
│ 执行层(多通道发布) │
│ ┌─────┐ ┌──────┐ ┌────┐ ┌────┐ ┌─────┐ │
│ │小红书│ │微信公众│ │微博│ │知乎│ │CSDN │ ... │
│ │ MCP │ │号 API │ │PPT │ │ AS │ │ PPT │ │
│ └─────┘ └──────┘ └────┘ └────┘ └─────┘ │
└─────────────────────────────────────────────────┘
"API 能走 API,API 不行走浏览器自动化,浏览器自动化不行走 AppleScript 注入。"
按照稳定性和维护成本,我把发布通道分成三个层级:
| 层级 | 方案 | 稳定性 | 维护成本 | 适用平台 |
|---|---|---|---|---|
| L1 | REST API | ⭐⭐⭐⭐⭐ | 极低 | 掘金、微信公众号 |
| L2 | Puppeteer Headless | ⭐⭐⭐⭐ | 中等 | 微博、CSDN |
| L3 | Chrome AppleScript | ⭐⭐⭐ | 较高 | 知乎、B站专栏 |
优先选用 L1 方案,L2 作为中间方案,L3 作为兜底。
小红书没有官方开放 API,但社区有一个基于 MCP(Model Context Protocol)协议的开源项目 xiaohongshu-mcp,封装了图文发布能力。
核心代码:
import requests
def publish_to_xiaohongshu(title, content, images):
"""发布图文到小红书"""
payload = {
'title': title[:20], # 标题限制20字
'content': content,
'images': images # 本地文件路径列表
}
resp = requests.post(
'http://localhost:18060/api/v1/publish',
json=payload,
timeout=180
)
return resp.json()
踩坑记录:
/tmp/xhs-mcp.log 确认实际状态。# 图片压缩:1.4MB PNG → 194KB JPEG
from PIL import Image
img = Image.open('big.png').convert('RGB')
img.save('small.jpg', 'JPEG', quality=80, optimize=True)
微信公众号有官方素材管理和草稿 API,可以创建文章草稿,但群发需要人工操作(API 没有群发权限)。
最大的坑是 HTML 内联样式。
<!-- ❌ 错误:裸标签在公众号渲染极其难看 -->
<p>这是一段文字</p>
<h2>这是标题</h2>
<!-- ✅ 正确:每个标签必须带完整 inline style -->
<p style="line-height:1.8;font-size:16px;text-align:justify;margin:10px 0">
这是一段文字
</p>
<h2 style="color:#009688;border-left:3px solid #009688;padding-left:10px;
font-size:140%;text-align:center">
这是标题
</h2>
我最终封装了一套样式模板函数,避免每次手写样式:
class WeChatStyle:
"""微信公众号 HTML 样式模板"""
@staticmethod
def p(text):
return f'<p style="line-height:1.8;font-size:16px;text-align:justify;margin:10px 0">{text}</p>'
@staticmethod
def h2(text):
return f'<h2 style="color:#009688;border-left:3px solid #009688;padding-left:10px;font-size:140%">{text}</h2>'
@staticmethod
def code(text):
return f'<pre style="background:#f6f8fa;padding:16px;border-radius:6px;overflow-x:auto"><code>{text}</code></pre>'
@staticmethod
def blockquote(text):
return f'<blockquote style="border-left:3px solid #009688;background:#f8f8f8;padding:10px 15px;margin:15px 0">{text}</blockquote>'
@staticmethod
def wrap(body):
return f'<section style="font-size:16px;font-family:Optima,Microsoft YaHei;line-height:1.6;color:#333">{body}</section>'
微博没有个人发博 API,只能用 Puppeteer 无头浏览器模拟操作。
关键技术点:
const puppeteer = require('puppeteer-extra');
const StealthPlugin = require('puppeteer-extra-plugin-stealth');
puppeteer.use(StealthPlugin());
// 发送按钮必须用 evaluate 触发,.click() 会被遮挡
await page.evaluate(() => {
const btn = document.querySelector('[node-type="submit"]');
btn.click();
});
// 上传图片后必须等 loading 消失
await page.waitForFunction(() => {
const spinners = document.querySelectorAll('.loading');
return spinners.length === 0;
}, { timeout: 15000 });
踩坑记录: - 必须用 puppeteer-extra-plugin-stealth 绕过反爬 - 发送按钮的 .click() 不工作,要用 page.evaluate() 内部点击 - 图片上传有异步过程,必须等 spinner 消失再提交 - 每条微博之间间隔 ≥2 分钟,否则触发风控
这两个平台反爬非常严格,Headless 浏览器容易被识别。最终采用复用已登录 Chrome 浏览器,通过 macOS AppleScript 注入 JavaScript 的方案。
前提条件: Chrome → 设置 → 开发者 → 勾选"允许 Apple 事件中的 JavaScript"
-- 知乎发文:通过剪贴板粘贴内容
tell application "Google Chrome"
tell active tab of front window
execute javascript "
document.querySelector('.public-DraftEditor-content').focus();
"
end tell
end tell
tell application "System Events"
keystroke "v" using command down -- Cmd+V 粘贴
end tell
知乎的血泪教训: - 绝对不能用 Markdown 符号。##、**、--- 会原样显示 - 不要用 Unicode 装饰符号。▎、━━━、❶❷❸ 在知乎排版很丑 - 正文编辑器是 Draft.js,必须用剪贴板粘贴,不能直接设置 innerHTML
B站的坑: - 编辑器在第二层 iframe(york/read-editor)里 - 标题是 textarea,正文是 contenteditable div,输入方式完全不同 - 发布按钮在 iframe 内部,要跨 iframe 查找
掘金的 API 相对友好,Cookie 认证即可:
import requests
def publish_to_juejin(title, content, category_id, tag_ids):
"""发布文章到掘金"""
cookies = {"sessionid": "your_session_id"}
# 1. 创建草稿
draft = requests.post(
"https://api.juejin.cn/content_api/v1/article_draft/create",
json={
"title": title,
"mark_content": content,
"edit_type": 10 # Markdown
},
cookies=cookies
).json()
draft_id = draft["data"]["id"]
# 2. 更新草稿(加分类和标签)
requests.post(
"https://api.juejin.cn/content_api/v1/article_draft/update",
json={
"id": draft_id,
"category_id": category_id,
"tag_ids": tag_ids
},
cookies=cookies
)
# 3. 发布
result = requests.post(
"https://api.juejin.cn/content_api/v1/article/publish",
json={
"draft_id": draft_id,
"category_id": category_id,
"tag_ids": tag_ids
},
cookies=cookies
).json()
return result
注意: 掘金普通用户只能添加 1 个标签,不是你以为的多个。
CSDN 的 API 需要复杂的阿里云 API 网关签名(X-Ca-Signature),直接调 API 不现实。最终采用 Puppeteer 方案:
// 打开编辑器
await page.goto('https://editor.csdn.net/md/');
// 设置标题
await page.evaluate((title) => {
const input = document.querySelector('.article-bar__title--input');
Object.getOwnPropertyDescriptor(HTMLInputElement.prototype, 'value')
.set.call(input, title);
input.dispatchEvent(new Event('input', { bubbles: true }));
}, title);
// 内容通过 contentEditable 的 execCommand 写入
await page.evaluate((content) => {
const editor = document.querySelector('pre.editor__inner');
editor.focus();
document.execCommand('selectAll');
document.execCommand('delete');
document.execCommand('insertText', false, content);
}, markdownContent);

同一个主题发不同平台,必须改编,不能直接复制。我给 Agent 定义了各平台的改编规则:
| 平台 | 字数 | 风格特点 | 图片要求 |
|---|---|---|---|
| 小红书 | 350-500 | emoji 多、话题标签、互动引导 | 封面必须 + 3-6 张 |
| 微信公众号 | 800-1500 | 深度分析、小标题分段、专业 | banner + 3-5 张 |
| 微博 | 140-300 | 精炼观点、一句话抓眼球 | 1-2 张 |
| B站/知乎 | 1500-3000 | 长文深度、数据/案例丰富 | 3-5 张 |
| CSDN/掘金 | 1500-3000 | 技术实战、代码示例、架构图 | 架构图 + 代码截图 |
Agent 会根据目标平台的规范,自动调整语气、字数、格式和配图策略,而不是简单截断或复制。
所有配图通过 SiliconFlow 的 FLUX.1 模型生成。成本极低,生成速度快:
import requests
def generate_image(prompt, size="1024x576"):
resp = requests.post(
"https://api.siliconflow.cn/v1/images/generations",
headers={"Authorization": f"Bearer {API_KEY}"},
json={
"model": "black-forest-labs/FLUX.1-schnell",
"prompt": prompt,
"image_size": size,
"num_inference_steps": 4
}
)
return resp.json()["images"][0]["url"]
每张图大约 2-3 秒生成完毕,一篇文章 3 张配图总计不到 10 秒。
发布顺序有讲究——先 API 类,后浏览器自动化类:
1. 小红书(MCP API) → 最稳定,先发
2. 微信公众号(官方 API) → API 调用,快速
3. 掘金(REST API) → Cookie 认证,简单
4. 微博(Puppeteer) → 无头浏览器,可能需要处理验证码
5. CSDN(Puppeteer) → 同上
6. B站专栏(AppleScript) → 需要 Chrome 在前台
7. 知乎专栏(AppleScript) → 同上
API 类平台不受 UI 状态影响,放前面;浏览器自动化可能遇到验证码或加载问题,放后面不影响前面的发布进度。
系统还集成了技术热点监控模块,从 10+ 个技术社区抓取热榜:
# 基于 DailyHotApi 的热榜聚合
TECH_SOURCES = {
"ithome": "IT之家",
"36kr": "36氪",
"juejin": "掘金",
"csdn": "CSDN",
"sspai": "少数派",
"v2ex": "V2EX",
"github": "GitHub Trending",
"hn": "Hacker News"
}
def get_tech_hot_topics():
"""获取技术热榜 Top 10"""
topics = []
for source, name in TECH_SOURCES.items():
resp = requests.get(f"http://localhost:6688/{source}")
data = resp.json().get("data", [])[:3]
for item in data:
topics.append({
"title": item["title"],
"source": name,
"url": item.get("url", "")
})
return sorted(topics, key=lambda x: x.get("hot", 0), reverse=True)[:10]
每天自动抓取技术热点,筛选与 AI/自动化/工程实践相关的话题,作为内容创作的选题池。
搭建完成后的效果对比:
| 指标 | 手动发布 | 自动化发布 |
|---|---|---|
| 单次发布耗时 | 1-2 小时 | 10-15 分钟 |
| 内容一致性 | 容易漏改 | 按规则严格改编 |
| 配图质量 | 找图+调整 | AI 生成,风格统一 |
| 人工干预 | 全程手动 | 仅公众号需手动群发 |
| 可扩展性 | 加一个平台 +1h | 加一个平台 +2h 一次性 |
这套系统的核心不是某个具体技术,而是分层的自动化策略:
每增加一个新平台,先评估它属于哪一层,再选择对应的技术方案。不要试图用一种方案覆盖所有平台——每个平台的反爬策略、编辑器实现、API 开放度都不同。
下一步计划: - 接入 Medium、Dev.to 等海外技术社区(它们有友好的 API) - 增加发布后的数据监控(阅读量、点赞、评论) - 优化 AI 改编质量,让不同平台的内容风格差异更大
如果这篇文章对你有帮助,欢迎点赞收藏。 后续我会持续分享 AI Agent 在实际工作中的应用实践,包括热点监控、自动评论互动、数据分析等。
本文首发于掘金和 CSDN,所有代码均为实际运行版本,非示例代码。
上一篇:国内OpenClaw玩家圈共识:智创聚合API才是真香选择
下一篇:没有了