reddit-post
Compare original and translation side by side
🇺🇸
Original
English🇨🇳
Translation
ChineseReddit Posting Skill (AppleScript Chrome Control)
Reddit发帖技能(AppleScript Chrome控制)
Post to Reddit by controlling the user's real Chrome via AppleScript. No Playwright, no Selenium, no API tokens.
通过AppleScript控制用户的真实Chrome浏览器在Reddit发帖。无需使用Playwright、Selenium,也不需要API令牌。
How It Works
工作原理
Claude Code → osascript → Chrome (real browser, logged in) → Reddit /api/submit- Same-origin fetch with cookies → undetectable
- Reddit's endpoint for text/link posts
/api/submit - Modhash from for CSRF protection
/api/me.json
Claude Code → osascript → Chrome (真实浏览器,已登录) → Reddit /api/submit- 携带Cookie的同源请求 → 无法被检测
- 使用Reddit的端点发布文字/链接帖
/api/submit - 从获取Modhash以实现CSRF防护
/api/me.json
Prerequisites
前置条件
- macOS only (AppleScript is a macOS technology)
- Chrome: View → Developer → Allow JavaScript from Apple Events (restart Chrome after enabling)
- User logged into Reddit in Chrome
- 仅支持macOS(AppleScript是macOS专属技术)
- Chrome浏览器:依次点击「视图」→「开发者」→「允许来自Apple事件的JavaScript」(启用后需重启Chrome)
- 用户已在Chrome中登录Reddit账号
Method Detection (Run First)
方法检测(先运行)
bash
WINDOWS=$(osascript -e 'tell application "Google Chrome" to return count of windows' 2>/dev/null)
if [ "$WINDOWS" = "0" ] || [ -z "$WINDOWS" ]; then
echo "METHOD 2 (System Events + Console)"
else
echo "METHOD 1 (execute javascript)"
fiSee skill for full Method 1 vs Method 2 details.
reddit-cultivatebash
WINDOWS=$(osascript -e 'tell application "Google Chrome" to return count of windows' 2>/dev/null)
if [ "$WINDOWS" = "0" ] || [ -z "$WINDOWS" ]; then
echo "METHOD 2 (System Events + Console)"
else
echo "METHOD 1 (execute javascript)"
fi查看技能以了解方法1与方法2的完整区别。
reddit-cultivatePosting Workflow
发帖流程
Step 1: Get Modhash
步骤1:获取Modhash
bash
osascript -e 'tell application "Google Chrome" to tell active tab of first window to execute javascript "fetch(\"/api/me.json\",{credentials:\"include\"}).then(r=>r.json()).then(d=>{document.title=\"UH:\"+d.data.modhash})"'
sleep 2
osascript -e 'tell application "Google Chrome" to return title of active tab of first window'bash
osascript -e 'tell application "Google Chrome" to tell active tab of first window to execute javascript "fetch(\"/api/me.json\",{credentials:\"include\"}).then(r=>r.json()).then(d=>{document.title=\"UH:\"+d.data.modhash})"'
sleep 2
osascript -e 'tell application "Google Chrome" to return title of active tab of first window'Step 2: Submit Post
步骤2:提交帖子
Navigate Chrome to reddit.com first (same-origin requirement), then submit:
javascript
(async()=>{
try {
let body = new URLSearchParams({
sr: "SideProject", // subreddit name (no r/ prefix)
kind: "self", // "self" for text, "link" for URL
title: "Your post title",
text: "Your post body with **markdown** support",
uh: "MODHASH_HERE",
api_type: "json",
resubmit: "true"
});
let resp = await fetch("/api/submit", {
method: "POST",
credentials: "include",
headers: {"Content-Type": "application/x-www-form-urlencoded"},
body: body.toString()
});
let result = await resp.json();
document.title = "POSTED:" + JSON.stringify(result);
} catch(e) {
document.title = "ERR:" + e.message;
}
})()For link posts, change:
javascript
kind: "link",
url: "https://github.com/your/repo", // instead of text先将Chrome导航至reddit.com(满足同源要求),再提交内容:
javascript
(async()=>{
try {
let body = new URLSearchParams({
sr: "SideProject", // subreddit名称(无需r/前缀)
kind: "self", // "self"表示文字帖,"link"表示链接帖
title: "Your post title",
text: "Your post body with **markdown** support",
uh: "MODHASH_HERE",
api_type: "json",
resubmit: "true"
});
let resp = await fetch("/api/submit", {
method: "POST",
credentials: "include",
headers: {"Content-Type": "application/x-www-form-urlencoded"},
body: body.toString()
});
let result = await resp.json();
document.title = "POSTED:" + JSON.stringify(result);
} catch(e) {
document.title = "ERR:" + e.message;
}
})()若发布链接帖,请修改:
javascript
kind: "link",
url: "https://github.com/your/repo", // 替换text字段Step 3: Extract Post Link
步骤3:提取帖子链接
The response contains — the direct link to the new post.
result.json.data.url响应结果中包含——新帖子的直接链接。
result.json.data.urlStep 4: Add Flair (if required)
步骤4:添加标签(若需要)
Some subreddits require flair. After posting, use:
javascript
(async()=>{
try {
// First get available flairs
let resp = await fetch("/r/SUBREDDIT/api/link_flair_v2", {credentials: "include"});
let flairs = await resp.json();
document.title = "FLAIRS:" + JSON.stringify(flairs.map(f => ({id: f.id, text: f.text})));
} catch(e) {
document.title = "ERR:" + e.message;
}
})()Then apply flair:
javascript
(async()=>{
try {
let body = new URLSearchParams({
link: "t3_POST_ID",
flair_template_id: "FLAIR_ID",
uh: "MODHASH"
});
await fetch("/api/selectflair", {
method: "POST",
credentials: "include",
headers: {"Content-Type": "application/x-www-form-urlencoded"},
body: body.toString()
});
document.title = "FLAIR_SET";
} catch(e) {
document.title = "ERR:" + e.message;
}
})()部分子版块要求添加标签。发帖后使用以下代码:
javascript
(async()=>{
try {
// 先获取可用标签
let resp = await fetch("/r/SUBREDDIT/api/link_flair_v2", {credentials:"include"});
let flairs = await resp.json();
document.title = "FLAIRS:" + JSON.stringify(flairs.map(f => ({id: f.id, text: f.text})));
} catch(e) {
document.title = "ERR:" + e.message;
}
})()然后应用标签:
javascript
(async()=>{
try {
let body = new URLSearchParams({
link: "t3_POST_ID",
flair_template_id: "FLAIR_ID",
uh: "MODHASH"
});
await fetch("/api/selectflair", {
method: "POST",
credentials: "include",
headers: {"Content-Type": "application/x-www-form-urlencoded"},
body: body.toString()
});
document.title = "FLAIR_SET";
} catch(e) {
document.title = "ERR:" + e.message;
}
})()Step 5: Session Summary
步骤5:会话总结
Always end with the post link:
| Sub | Title | Post Link |
|---|---|---|
| r/SideProject | "Your title" | https://www.reddit.com/r/SideProject/comments/abc123/... |
务必以帖子链接结尾:
| 子版块 | 标题 | 帖子链接 |
|---|---|---|
| r/SideProject | "Your title" | https://www.reddit.com/r/SideProject/comments/abc123/... |
Spam Filter Avoidance
规避垃圾过滤器
Words to AVOID in titles/body
标题/正文中需避免的词汇
| Avoid | Use Instead |
|---|---|
| crawl, crawled, crawling | compiled, cataloged, indexed, collected |
| scrape, scraping | gathered, extracted, retrieved |
| bot, automated | tool, script, program |
| free (overused) | open source, MIT licensed |
| hack, hacks | tips, techniques, methods |
| 需避免 | 替代词汇 |
|---|---|
| crawl, crawled, crawling | compiled, cataloged, indexed, collected |
| scrape, scraping | gathered, extracted, retrieved |
| bot, automated | tool, script, program |
| free(滥用) | open source, MIT licensed |
| hack, hacks | tips, techniques, methods |
Content Triggers to Avoid
需避免的内容触发点
- Multiple external links (max 1-2)
- URL shorteners (bit.ly, tinyurl)
- New account + promotional content
- Same content across multiple subreddits quickly
- Excessive self-promotion language
- 多个外部链接(最多1-2个)
- URL短链接(bit.ly、tinyurl等)
- 新账号发布推广内容
- 短时间内在多个子版块发布相同内容
- 过度的自我推广话术
Best Subreddits for Open Source Projects
适合推广开源项目的子版块
| Subreddit | Members | Best For | Notes |
|---|---|---|---|
| r/coolgithubprojects | 60K | GitHub repos | Designed for this! |
| r/SideProject | 453K | Side projects | Very welcoming |
| r/opensource | 100K+ | Open source tools | Technical audience |
| r/programming | 6M+ | Dev tools | High competition |
| r/Python | 1.5M+ | Python tools | Active community |
| r/webdev | 2M+ | Web tools | "Showoff Saturday" only |
| r/selfhosted | 400K+ | Self-hosted tools | Great engagement |
| 子版块 | 成员数 | 适用场景 | 备注 |
|---|---|---|---|
| r/coolgithubprojects | 6万 | GitHub仓库 | 专为该场景设计! |
| r/SideProject | 45.3万 | 副业项目 | 社区氛围友好 |
| r/opensource | 10万+ | 开源工具 | 受众技术水平较高 |
| r/programming | 600万+ | 开发工具 | 竞争激烈 |
| r/Python | 150万+ | Python工具 | 社区活跃度高 |
| r/webdev | 200万+ | Web工具 | 仅在“Showoff Saturday”发布 |
| r/selfhosted | 40万+ | 自托管工具 | 互动性强 |
Best Times to Post (US Eastern Time)
最佳发帖时间(美国东部时间)
| Day | Best Time |
|---|---|
| Monday | 6-8 AM |
| Tuesday | 7-9 AM |
| Wednesday | 8-10 AM |
| Thursday | 7-9 AM |
| Friday | 6-8 AM |
| Saturday | 7-9 AM |
| Sunday | 8-10 AM |
Post 30 minutes BEFORE peak times for momentum building.
| 日期 | 最佳时间 |
|---|---|
| 周一 | 6-8点 |
| 周二 | 7-9点 |
| 周三 | 8-10点 |
| 周四 | 7-9点 |
| 周五 | 6-8点 |
| 周六 | 7-9点 |
| 周日 | 8-10点 |
建议在高峰时段前30分钟发帖,以积累热度。
Post Templates
发帖模板
Open Source Project Announcement
开源项目公告
Title: I built [PROJECT_NAME] - [one-line description] (open source)
Body:
Hey everyone,
I created [PROJECT_NAME] to solve [PROBLEM].
**What it does:**
- Feature 1
- Feature 2
- Feature 3
**Tech stack:** [Languages/frameworks]
**Links:**
- GitHub: [single link]
Happy to answer any questions!Title: I built [PROJECT_NAME] - [one-line description] (open source)
Body:
Hey everyone,
I created [PROJECT_NAME] to solve [PROBLEM].
**What it does:**
- Feature 1
- Feature 2
- Feature 3
**Tech stack:** [Languages/frameworks]
**Links:**
- GitHub: [single link]
Happy to answer any questions!Tool/Resource Share
工具/资源分享
Title: [TOOL_NAME]: [what it does] - free and open source
Body:
Built this because [reason/pain point].
**Features:**
- [List 3-5 key features]
**How to use:**
[Brief code example or instructions]
GitHub: [link]
Feedback welcome!Title: [TOOL_NAME]: [what it does] - free and open source
Body:
Built this because [reason/pain point].
**Features:**
- [List 3-5 key features]
**How to use:**
[Brief code example or instructions]
GitHub: [link]
Feedback welcome!Cross-Posting Strategy
交叉发帖策略
Stagger posts across subreddits for maximum reach:
- Day 1: Primary subreddit (most relevant)
- Day 2-3: Secondary subreddit (different audience)
- Day 4-5: General subreddit (r/SideProject, etc.)
Never post to multiple subreddits on the same day — triggers spam detection.
错开时间在不同子版块发帖以扩大覆盖范围:
- 第1天:主帖子版块(最相关的)
- 第2-3天:次要子版块(受众不同)
- 第4-5天:综合子版块(如r/SideProject等)
切勿在同一天内多个子版块发布相同内容——会触发垃圾检测。
Error Recovery
错误排查
| Issue | Solution |
|---|---|
| "Post removed by filters" | Rewrite without trigger words, reduce links |
| "You're doing that too much" | Wait 10-15 min, need more karma |
| "This community requires flair" | Use /api/selectflair after posting |
| "Title too long" | Keep under 300 characters |
| Post not visible | Check if shadowbanned: profile in incognito |
| Modhash expired | Re-fetch from /api/me.json |
| 问题 | 解决方案 |
|---|---|
| “Post removed by filters” | 修改内容,移除触发词汇,减少链接数量 |
| “You're doing that too much” | 等待10-15分钟,需要更多 karma(积分) |
| “This community requires flair” | 发帖后使用/api/selectflair接口添加标签 |
| “Title too long” | 控制在300字符以内 |
| 帖子不可见 | 检查是否被影子封禁:在隐身模式查看个人主页 |
| Modhash过期 | 重新从/api/me.json获取 |
Why AppleScript (Not Playwright)
为什么选择AppleScript(而非Playwright)
| Tool | Problem |
|---|---|
| Playwright | |
| Selenium | Same detection issue |
| curl + API | IP blocked after few requests |
| AppleScript | Controls real Chrome, undetectable, cookies included |
| 工具 | 问题 |
|---|---|
| Playwright | |
| Selenium | 存在相同的检测问题 |
| curl + API | 几次请求后IP会被封禁 |
| AppleScript | 控制真实Chrome浏览器,无法被检测,自动携带Cookie |