소스 정보
- 저장소
- aAAaqwq/AGI-Super-Team
- 최근 소스 활동
- 2026년 4월 24일 11:04
- 감지된 SKILL.md 언어
- 중국어
- 스타
- 86
- 포크
- 22
설치 방법
기본적으로 소스를 먼저 확인하는 Prompt가 선택됩니다. 직접 명령으로 전환하거나 로컬 사본을 다운로드할 수도 있습니다.
소스 파일 검토
설치 여부를 결정하기 전에 SKILL.md와 SkillsMP에 표시된 보조 파일을 읽어 보세요.
메뉴
기본적으로 소스를 먼저 확인하는 Prompt가 선택됩니다. 직접 명령으로 전환하거나 로컬 사본을 다운로드할 수도 있습니다.
설치 여부를 결정하기 전에 SKILL.md와 SkillsMP에 표시된 보조 파일을 읽어 보세요.
SOC 직업 분류 기준
Codex 또는 Claude로 설치 이 Prompt를 복사해 Codex, Claude 또는 다른 어시스턴트에 붙여 넣으면 Skill 페이지를 검토하고 설치를 진행할 수 있습니다.
직접 명령은 검토 Prompt를 거치지 않습니다. 실행하기 전에 소스를 확인하세요.
npx skills add https://github.com/aAAaqwq/AGI-Super-Team --skill douyin-publisher명령은 한 줄로 유지됩니다. 복사하기 전에 가로로 스크롤해 전체 내용을 확인하세요.
로컬 사본을 원하시나요? SkillsMP에서 현재 제공할 수 있는 파일을 다운로드하세요.
SKILL.md 표시 중
币安广场合约投机雷达 v5:以最近24小时专业交易帖为主要证据,回源核验帖子, 联合币安公共合约行情、4周期K线、布林带、ATR、量能和RR,生成可审计的本地影子报告。 触发词:币安广场、扫描币安、binance square、合约机会、交易信号雷达、4小时雷达
BTC 5分钟K线实时方向预测。v5.9对抗式审查重构: 13因子收敛到3个有证据信号(half_body延续+volume放量+meanrev回归, 11个47-49%硬币因子清零) + 三层独立信息过滤(多周期4h/1h/15m趋势 + 跨资产ETH/SOL广度 + 真订单流OFI) + 移除bull×0.92惩罚/Platt置信度门控。半K线策略第2分钟执行。黑天鹅防护: ATR spike+FNG<25。Binance端点双向故障切换。
BB 双向套利策略:加密合约 10x 杠杆布林带均值回归。布林带收窄=横盘→在下轨买、上轨卖;三重过滤器(1h趋势/RSI/BB甜区)确认碗平放,轨对轨止盈(RR 2:1~4:1)。含实时WebSocket模拟盘(paper)、历史回测(simulate/backtest_daily)、币安永续实盘CLI(trade_exec)。触发:'bb套利'、'布林带'、'bollinger'、'横盘策略'、'NEAR'、'回测'、'模拟盘'、'paper trading'。
| name | douyin-publisher |
| description | 抖音图文/视频发布(OpenClaw Browser 自动化):登录检测→内容校验→上传页导航→填标题/正文→上传封面+素材→暂存离开。 |
| metadata | {"version":"2.0.0","author":"Daniel Li","domains":["content","publishing","automation","douyin"],"type":"automation"} |
核心技术栈:OpenClaw
browser工具(不依赖独立 Playwright 脚本) 安全原则:默认只存草稿,只在 Daniel 明确确认后才允许点击发布
mode=draft — 每次发布流程终点是「暂存离开」,不是「发布」发布前参考 references/platform-rules.md 确认内容合规:
Step 1: 登录检测 ──→ Step 2: 内容检测 ──→ Step 3: 进入发布页
│
Step 6: 暂存离开 ←── Step 5: 上传素材 ←── Step 4: 填写内容
│
▼
确认回传给 Daniel
目标:确认浏览器已登录抖音创作者平台,未登录则发送二维码给 Daniel
browser(action="open", url="https://creator.douyin.com/creator-micro/home", profile="user")
profile="user"使用 Daniel 的本地浏览器(已有登录态概率最高) 如果 user profile 不可用,使用默认 profile(OpenClaw 托管浏览器)
browser(action="snapshot")
判断是否已登录:
creator-micro,页面出现创作者后台内容login/passport,或页面出现「扫码登录」「验证码登录」如果未登录:
# 截取二维码区域
browser(action="screenshot", path="/tmp/douyin_qr_login.png")
然后发消息给 Daniel:
message(action="send", message="⚠️ 抖音未登录,请扫描二维码登录。登录完成后回复"ok"",
media="/tmp/douyin_qr_login.png")
等待 Daniel 回复后,重新检测:
browser(action="navigate", url="https://creator.douyin.com/creator-micro/home")
# 等待 5 秒让页面加载
browser(action="snapshot")
# 确认已进入创作者后台
截图确认并记录:
browser(action="screenshot", path="/tmp/douyin_step1_logged_in.png")
目标:在动手前确认所有文件就绪、格式正确、内容合规
# 确认文件存在、格式、大小
ls -lh /path/to/images/*.jpg /path/to/cover.png
file /path/to/images/*.jpg
图文要求:
| 项目 | 要求 |
|---|---|
| 图片数量 | 2-35 张 |
| 格式 | JPG, PNG, WebP(不支持 GIF) |
| 单张大小 | ≤50MB |
| 推荐比例 | 3:4(1080×1440)或 4:3 |
视频要求:
| 项目 | 要求 |
|---|---|
| 格式 | MP4 (H.264) |
| 分辨率 | ≥720×1280,推荐 1080×1920 |
| 大小 | ≤16GB |
| 时长 | 15秒-60分钟 |
# 确认标题和描述文件
cat /path/to/content.md
校验规则:
#话题名(无空格)向 Daniel 确认:
📋 内容检测报告
━━━━━━━━━━━━━━
📌 标题:{title}({len}字)
📝 描述:{desc[:50]}...({len}字)
🏷️ 话题:{tags}
🖼️ 素材:{count} 张图片 / {video} 视频
📐 格式:{formats}
📦 大小:{total_size}
✅ 全部就绪,开始发布流程
目标:导航到正确的发布页面,处理好可能的弹窗
图文发布:
browser(action="navigate", url="https://creator.douyin.com/creator-micro/content/upload?default-tab=3")
视频发布:
browser(action="navigate", url="https://creator.douyin.com/creator-micro/content/upload")
# 等待文件上传控件出现(证明页面已完全加载)
browser(action="snapshot")
检查 snapshot 中是否有 input[type="file"]。如果没有:
抖音经常弹出"上次未发布内容"提示。检测并关闭:
browser(action="act", kind="evaluate", fn="""() => {
const els = document.querySelectorAll('*');
for (const el of els) {
const t = el.textContent.trim();
if ((t === '放弃' || t === '不再提醒' || t === '新建图文')
&& el.offsetParent !== null && el.children.length === 0) {
el.click();
return 'dismissed: ' + t;
}
}
return 'no popup';
}""")
browser(action="screenshot", path="/tmp/douyin_step3_publish_page.png")
目标:在发布页面填入标题和描述(含话题标签)
找到标题输入区(优先使用 snapshot 中的 ref):
# 方法1:通过 placeholder 定位(推荐)
browser(action="act", kind="fill", ref="{title_input_ref}", text="{标题文字}")
# 方法2:通过 evaluate 直接操作
browser(action="act", kind="evaluate", fn="""() => {
const sel = 'input[placeholder*="标题"]';
const el = document.querySelector(sel);
if (el) {
el.focus();
el.select();
el.value = '';
// 触发 React 的 onChange
const nativeInputValueSetter = Object.getOwnPropertyDescriptor(window.HTMLInputElement.prototype, 'value').set;
nativeInputValueSetter.call(el, arguments[0]);
el.dispatchEvent(new Event('input', { bubbles: true }));
el.dispatchEvent(new Event('change', { bubbles: true }));
return 'title filled';
}
return 'title input not found';
}""")
注意:抖音是 React SPA,直接
.value = xxx不会触发状态更新。必须用nativeInputValueSetter或type动作。
2026-04-17 实战验证结论: 抖音描述区使用 Slate.js (
data-slate-editor="true"),不是普通 textarea。
- ❌
innerText = xxx→ 视觉显示但 Slate 状态不更新,暂存后丢失- ❌
document.execCommand('insertText')多次调用 → 文本叠加,无法清空已有内容- ❌
ClipboardEvent('paste')→ 浏览器安全策略阻止,Slate 读不到数据- ❌
new InputEvent('beforeinput')→ SlatepreventDefault()后不执行实际插入- ❌
browser act kind=type→ contenteditable div 无 Playwright ref,超时- ❌
browser act kind=fill→ 不支持 contenteditable- ✅ 唯一可靠方法:从全新页面一次性
execCommand('insertText'),且只能调用一次
正确流程(必须在全新空白编辑器上执行):
# Step 1: 聚焦描述区
browser(action="act", kind="evaluate", fn="""() => {
const desc = document.querySelector('[data-slate-editor="true"]');
if (!desc) return 'not found';
desc.focus();
return 'focused';
}""")
# Step 2: 一次性插入文本(只能执行一次!)
browser(action="act", kind="evaluate", fn="""() => {
const desc = document.querySelector('[data-slate-editor="true"]');
if (!desc) return 'not found';
const text = '你的描述文字(建议≤200字,含#话题标签)';
document.execCommand('insertText', false, text);
// 触发 blur 确保 Slate 最终提交状态
desc.blur();
return 'inserted: ' + desc.innerText.length + ' chars';
}""")
# Step 3: 验证字数计数器已更新(从 0/N 变为实际字数/N)
browser(action="snapshot")
# 检查描述区域文本中是否显示 "实际字数 / 1000"
验证要点:
0 / 1000 变为 实际字数 / 1000 → ✅ React 状态已更新0 / 1000 → ❌ 文本未写入 Slate 状态,暂存后会丢失注意事项:
# 时抖音可能弹出话题搜索面板,此时需先点击面板外部关闭execCommand('insertText') 在已有内容的 Slate 编辑器上无法正确清空(selectAll+delete 无效)execCommand,每次都会在现有文本基础上追加直接在描述文本中包含 #话题1 #话题2 即可,Slate 会自动识别。
不要单独追加话题,会导致文本叠加问题。
browser(action="screenshot", path="/tmp/douyin_step4_content_filled.png")
目标:上传图片素材到发布页面
# 通过 snapshot 获取 file input 的 ref
browser(action="snapshot")
找到 input[type="file"][accept*="image"] 的 ref。
2026-04-17 实战验证:
file://fetch 被浏览器安全策略阻止evaluate中的DataTransfer+File构造同样被阻止- 文件必须放在
/tmp/openclaw/uploads/目录下
正确方法(已验证):
# Step 1: 复制文件到 uploads 目录
# cp /path/to/images/*.jpg /tmp/openclaw/uploads/
# Step 2: 点击上传按钮触发 file chooser
browser(action="snapshot") # 获取上传按钮 ref
browser(action="act", kind="click", ref="{upload_btn_ref}") # e.g. ref=e8 "上传图文"
# Step 3: 通过 browser upload 上传文件
browser(action="upload", paths=[
"/tmp/openclaw/uploads/img1.jpg",
"/tmp/openclaw/uploads/img2.jpg",
"/tmp/openclaw/uploads/img3.jpg"
])
# Step 4: 等待上传处理完成(页面显示"加载中"→编辑器就绪)
browser(action="act", kind="wait", timeMs=10000)
# Step 5: 验证 — snapshot 应显示"已添加N张图片"和编辑区按钮
browser(action="snapshot")
⚠️ 失败方法(不要使用):
方法 B(已废弃):通过 evaluate 直接设置 file input
browser(action="act", kind="evaluate", fn="""async () => {
const input = document.querySelector('input[type="file"][accept*="image"]');
if (!input) return 'file input not found';
const files = [
'/path/to/img1.jpg',
'/path/to/img2.jpg',
'/path/to/img3.jpg',
];
// 通过 Playwright 的 setInputFiles(如果可用)
// 或通过 DataTransfer API
const dt = new DataTransfer();
for (const path of files) {
const resp = await fetch('file://' + path);
const blob = await resp.blob();
const file = new File([blob], path.split('/').pop());
dt.items.add(file);
}
input.files = dt.files;
input.dispatchEvent(new Event('change', { bubbles: true }));
return 'files set: ' + files.length;
}""")
注意:方法 B 在某些浏览器安全策略下可能被阻止。如果方法 B 失败,使用方法 A。
图片上传后,抖音需要处理(压缩、生成缩略图等)。等待信号:
# 等待编辑器按钮出现(表示上传处理完成)
browser(action="act", kind="wait", timeMs=5000)
# 检查是否出现了"暂存离开"/"发布"按钮
browser(action="snapshot")
上传完成标志:
如果需要指定封面(从已上传图片中选择):
# 点击封面设置区域
browser(action="act", kind="click", ref="{cover_area_ref}")
# 等待封面选择弹窗
browser(action="act", kind="wait", timeMs=2000)
# 选择指定图片作为封面(通常点击图片缩略图即可)
browser(action="act", kind="click", ref="{target_image_ref}")
# 确认选择
browser(action="act", kind="click", ref="{confirm_btn_ref}")
如果上传失败:
browser(action="screenshot", path="/tmp/douyin_step5_assets_uploaded.png")
目标:点击「暂存离开」将内容保存到草稿箱
提交前先处理可能的弹窗(共创中心推广等):
browser(action="act", kind="evaluate", fn="""() => {
const els = document.querySelectorAll('*');
for (const el of els) {
const t = el.textContent.trim();
// 只关闭"我知道了"类提示,不要误关"确认"类弹窗
if (t === '我知道了' && el.offsetParent !== null && el.children.length === 0) {
el.click();
return 'closed: ' + t;
}
}
return 'no popup';
}""")
⚠️ 安全原则:只关闭明确无害的提示弹窗("我知道了")。 绝对不要关闭包含"确认""放弃"等有歧义文案的弹窗——先截图发给 Daniel 确认。
browser(action="snapshot")
在 snapshot 中查找以下任一按钮:
| 文案 | selector |
|---|---|
暂存离开 | 图文页最常见 |
存草稿 | 视频页常见 |
草稿 | 部分版本 |
# 使用 snapshot 中获取的 ref
browser(action="act", kind="click", ref="{draft_button_ref}")
点击后可能出现确认弹窗:
browser(action="act", kind="wait", timeMs=3000)
# 检查是否有"暂存"确认按钮
browser(action="act", kind="evaluate", fn="""() => {
const els = document.querySelectorAll('*');
for (const el of els) {
const t = el.textContent.trim();
if ((t === '暂存' || t === '确认' || t === '我知道了')
&& el.offsetParent !== null && el.children.length === 0) {
el.click();
return 'clicked: ' + t;
}
}
return 'no post-submit popup';
}""")
browser(action="act", kind="wait", timeMs=5000)
成功标志:
content/manage如果暂存失败:
browser(action="screenshot", path="/tmp/douyin_step6_draft_saved.png")
发布流程结束后,向 Daniel 发送标准报告:
📋 抖音发布报告
━━━━━━━━━━━━━━
📌 标题:{title}
📝 描述:{desc[:80]}...
🏷️ 话题:{tags}
🖼️ 素材:{count} 张图片 / 视频
📐 封面:{cover_status}
✅ 状态:已存草稿 / 待确认发布 / 待接管
📸 截图:{screenshot_path}
🔗 草稿管理:https://creator.douyin.com/creator-micro/content/manage
附上最终截图作为确认凭证。
如果 Daniel 确认要发布(而非只存草稿),替换 Step 6:
# 找到发布按钮
browser(action="snapshot")
# 查找 "button:has-text('发布')" 的 ref
# 点击发布
browser(action="act", kind="click", ref="{publish_button_ref}")
发布后等待成功信号(同 6.5),截图确认。
| 失败点 | 重试策略 | 停止条件 |
|---|---|---|
| 登录检测 | 重新打开页面 | 转人工扫码 |
| 二维码登录 | 等待 Daniel | 超时120秒 |
| 文件不存在 | 报告缺失文件 | 立即停止 |
| 格式不支持 | 报告并建议转换 | 立即停止 |
| 页面加载超时 | 刷新重试 | 3次失败 |
| 弹窗干扰 | 关闭提示弹窗 | 误关严重弹窗则停止 |
| 标题填写失败 | 重试 | 3次失败 |
| 描述填写失败 | 重试 | 3次失败 |
| 图片上传失败 | 指数退避重试 | 3次失败 |
| 封面设置失败 | 跳过(非阻塞) | — |
| 暂存按钮未找到 | 检查文案变体 | 3次失败 |
| 暂存后无成功信号 | 检查草稿箱 | 3次失败 |
| 验证码/滑块 | 立即停止 | 等 Daniel 处理 |
| 频率限制 | 立即停止 | 等30分钟 |
| 页面 | URL |
|---|---|
| 创作者首页 | https://creator.douyin.com/creator-micro/home |
| 图文发布 | https://creator.douyin.com/creator-micro/content/upload?default-tab=3 |
| 视频发布 | https://creator.douyin.com/creator-micro/content/upload |
| 草稿管理 | https://creator.douyin.com/creator-micro/content/manage |
| 时段 | 推荐度 |
|---|---|
| 7:00-9:00 | ⭐⭐⭐ |
| 11:30-13:00 | ⭐⭐⭐ |
| 17:30-19:00 | ⭐⭐⭐ |
| 20:00-22:00 | ⭐⭐⭐⭐⭐ |
| 22:00-00:00 | ⭐⭐⭐⭐ |
douyin-publish/
├── SKILL.md ← 本文件(workflow 主文件)
├── references/
│ ├── platform-rules.md ← 完整平台规则
│ ├── handoff-and-human-trace.md ← 接管规则与人类痕迹规范
│ └── content-style-guide.md ← 内容风格指南
└── templates/
├── desc-template.md ← 描述排版模板
└── video-script-template.md ← 视频脚本模板
避免"机器人味"
v2.0.0 (2026-04-17): 全面重构 — 从 Playwright 脚本迁移到 OpenClaw Browser 自动化 v2.0.1 (2026-04-17): Step 4 描述填写修复 — Slate.js 只能 execCommand 单次插入;Step 5 上传路径修复 v1.0.0 (2026-03-27): 初始版本,Playwright 脚本实现