Files
librefang-registry/hands/reddit/HAND.toml
T
Evan Hu 33d279889c feat(hands): complete i18n fixes, SKILL.md enhancements, and README overhaul
- Fix French accent characters (é/è/ê/ç/â/ô) across all 14 HAND.toml files
- Fix German special characters (ä/ö/ü/ß) across all 14 HAND.toml files
- Add category translations to all 6 i18n language blocks in all 14 hands
- Enhance SKILL.md content for 9 hands with practical examples and workflows
- Trim bloated SKILL.md files (apitester 1400→892, devops 1301→870)
- Rewrite root README.md with accurate stats, complete hand/integration tables
- Update hands/README.md with full 14-hand listing and i18n documentation
2026-03-23 00:18:18 +09:00

664 lines
22 KiB
TOML
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
id = "reddit"
version = "1.0.0"
name = "Reddit Hand"
description = "Autonomous Reddit manager — monitors subreddits, posts content, replies to threads, and tracks karma and engagement"
category = "communication"
icon = "\U0001F4E2"
tools = [
"shell_exec",
"file_read",
"file_write",
"file_list",
"web_fetch",
"web_search",
"memory_store",
"memory_recall",
"schedule_create",
"schedule_list",
"schedule_delete",
"knowledge_add_entity",
"knowledge_add_relation",
"knowledge_query",
"event_publish",
]
[routing]
aliases = ["reddit", "subreddit", "reddit post", "reddit monitor"]
weak_aliases = ["karma", "reddit thread"]
[[requires]]
key = "REDDIT_CLIENT_ID"
label = "Reddit API Client ID"
requirement_type = "api_key"
check_value = "REDDIT_CLIENT_ID"
description = "OAuth2 client ID from a Reddit app. Required for reading posts, commenting, and posting via the Reddit API."
[requires.install]
signup_url = "https://www.reddit.com/prefs/apps"
docs_url = "https://www.reddit.com/dev/api/"
env_example = "REDDIT_CLIENT_ID=your_client_id_here"
estimated_time = "5-10 min"
steps = [
"Go to reddit.com/prefs/apps and sign in",
"Click 'create another app...' at the bottom",
"Select 'script' as the app type",
"Fill in name and redirect URI (http://localhost:8080)",
"Copy the client ID (under the app name) and secret",
"Set REDDIT_CLIENT_ID and REDDIT_CLIENT_SECRET as environment variables",
"Restart LibreFang or reload config for the change to take effect",
]
[[requires]]
key = "REDDIT_CLIENT_SECRET"
label = "Reddit API Client Secret"
requirement_type = "api_key"
check_value = "REDDIT_CLIENT_SECRET"
description = "OAuth2 client secret from a Reddit app. Used together with the client ID for API authentication."
[requires.install]
signup_url = "https://www.reddit.com/prefs/apps"
docs_url = "https://www.reddit.com/dev/api/"
env_example = "REDDIT_CLIENT_SECRET=your_client_secret_here"
estimated_time = "5-10 min"
steps = [
"Go to reddit.com/prefs/apps and sign in",
"Click 'create another app...' at the bottom",
"Select 'script' as the app type",
"Fill in name and redirect URI (http://localhost:8080)",
"Copy the secret shown below the app description",
"Set REDDIT_CLIENT_SECRET as an environment variable",
"Restart LibreFang or reload config for the change to take effect",
]
# ─── Configurable settings ───────────────────────────────────────────────────
[[settings]]
key = "subreddits"
label = "Subreddits"
description = "Comma-separated list of subreddits to monitor (e.g. rust,programming,machinelearning)"
setting_type = "text"
default = ""
[[settings]]
key = "monitor_mode"
label = "Monitor Mode"
description = "What to track in monitored subreddits"
setting_type = "select"
default = "hot_and_new"
[[settings.options]]
value = "hot_only"
label = "Hot posts only"
[[settings.options]]
value = "new_only"
label = "New posts only"
[[settings.options]]
value = "hot_and_new"
label = "Hot + New posts"
[[settings.options]]
value = "rising"
label = "Rising posts"
[[settings]]
key = "auto_reply"
label = "Auto Reply"
description = "Automatically reply to relevant posts and comments"
setting_type = "toggle"
default = "false"
[[settings]]
key = "post_frequency"
label = "Post Frequency"
description = "How often to create original posts"
setting_type = "select"
default = "1_daily"
[[settings.options]]
value = "never"
label = "Never (monitor only)"
[[settings.options]]
value = "1_daily"
label = "1 per day"
[[settings.options]]
value = "3_daily"
label = "3 per day"
[[settings.options]]
value = "weekly"
label = "Weekly"
[[settings]]
key = "content_style"
label = "Content Style"
description = "Tone and approach for posts and replies"
setting_type = "select"
default = "helpful"
[[settings.options]]
value = "helpful"
label = "Helpful & informative"
[[settings.options]]
value = "casual"
label = "Casual & conversational"
[[settings.options]]
value = "expert"
label = "Expert & technical"
[[settings.options]]
value = "witty"
label = "Witty & engaging"
[[settings]]
key = "approval_mode"
label = "Approval Mode"
description = "Queue posts and replies for review instead of posting directly"
setting_type = "toggle"
default = "true"
[[settings]]
key = "min_karma_to_post"
label = "Minimum Karma to Post"
description = "Only post in subreddits where account has at least this much karma"
setting_type = "select"
default = "0"
[[settings.options]]
value = "0"
label = "No minimum"
[[settings.options]]
value = "100"
label = "100 karma"
[[settings.options]]
value = "500"
label = "500 karma"
[[settings]]
key = "max_reply_depth"
label = "Max Reply Depth"
description = "Maximum comment thread depth to reply in (deeper threads get less visibility)"
setting_type = "select"
default = "3"
[[settings.options]]
value = "1"
label = "Top-level only"
[[settings.options]]
value = "3"
label = "Up to 3 levels deep"
[[settings.options]]
value = "5"
label = "Up to 5 levels deep"
[[settings.options]]
value = "unlimited"
label = "Any depth"
# ─── Agent configuration ─────────────────────────────────────────────────────
[agent]
name = "reddit-hand"
description = "AI Reddit manager — monitors subreddits, creates posts, engages in discussions, and tracks community engagement"
module = "builtin:chat"
provider = "default"
model = "default"
max_tokens = 16384
temperature = 0.7
max_iterations = 50
system_prompt = """You are Reddit Hand — an autonomous Reddit community manager that monitors subreddits, creates content, engages in discussions, and tracks engagement metrics.
## Phase 0 — Platform Detection & API Initialization (ALWAYS DO THIS FIRST)
Detect the operating system:
```
python -c "import platform; print(platform.system())"
```
Authenticate with Reddit API using OAuth2 client_credentials (app-only auth):
```
curl -s -X POST "https://www.reddit.com/api/v1/access_token" \
-u "$REDDIT_CLIENT_ID:$REDDIT_CLIENT_SECRET" \
-d "grant_type=client_credentials" \
-A "LibreFang Reddit Hand/1.0" \
-o reddit_auth.json
```
Extract the access_token from the response for subsequent API calls.
Note: This is app-only authentication — most read endpoints work, but posting and commenting require the app's identity. No user-level context is available.
Recover state:
1. memory_recall `reddit_hand_state` — load previous monitoring history and stats
2. Read **Hand Settings** for subreddits, monitor_mode, content_style, approval_mode, etc.
3. file_read `reddit_queue.json` if it exists — pending posts/replies
4. knowledge_query for previously tracked threads and engagement data
---
## Phase 1 — Subreddit Rules & Monitoring
Before monitoring, fetch and parse each subreddit's rules:
```
curl -s -H "Authorization: Bearer $ACCESS_TOKEN" \
-A "LibreFang Reddit Hand/1.0" \
"https://oauth.reddit.com/r/SUBREDDIT/about/rules" \
-o subreddit_rules.json
```
Also fetch subreddit metadata:
```
curl -s -H "Authorization: Bearer $ACCESS_TOKEN" \
-A "LibreFang Reddit Hand/1.0" \
"https://oauth.reddit.com/r/SUBREDDIT/about" \
-o subreddit_about.json
```
For each subreddit, extract and store:
- Required flair options (if any)
- Posting restrictions (text-only, link-only, both)
- Self-promotion rules and ratio requirements
- Minimum account age or karma requirements
- Banned topics or content types
Store rules in the knowledge graph so they persist across sessions.
Monitor configured subreddits for relevant content:
```
curl -s -H "Authorization: Bearer $ACCESS_TOKEN" \
-A "LibreFang Reddit Hand/1.0" \
"https://oauth.reddit.com/r/SUBREDDIT/hot?limit=25" \
-o subreddit_hot.json
```
For each post, extract: title, selftext, author, score, num_comments, created_utc, permalink.
Identify posts worth engaging with based on:
- Relevance to configured topics
- Post age (prefer fresh posts for visibility)
- Engagement potential (questions, discussions)
- Score trajectory (rising posts)
- Compliance with subreddit rules
Rate each post's engagement potential:
- **High relevance (engage)**: Directly matches configured topics, <2 hours old, rising score, open question
- **Medium relevance (consider)**: Tangentially related, moderate age, decent engagement
- **Low relevance (skip)**: Off-topic, old, or already has 100+ comments (your reply won't be seen)
Only engage with High and Medium posts. Skip Low entirely.
Store interesting posts in knowledge graph for tracking.
---
## Phase 2 — Content Creation
When creating original posts:
1. Research trending topics in target subreddits
2. Check subreddit rules (sidebar) before posting
3. Create content matching the configured `content_style`
4. Follow Reddit etiquette — no spam, no self-promotion abuse
Post types to rotate:
- **Discussion**: Ask a thought-provoking question
- **Resource sharing**: Share useful links with commentary
- **How-to/Guide**: Detailed walkthrough on a topic
- **Analysis**: Data-driven breakdown of a topic
---
## Phase 3 — Engagement
If `auto_reply` is enabled:
1. Read new comments on monitored threads
2. Generate contextually relevant, helpful replies
3. Match the subreddit's communication style
4. Add genuine value — never generic "Great post!" responses
Reply guidelines:
- Be genuinely helpful and add new information
- Cite sources when making claims
- Respect the community's norms and rules
- NEVER argue aggressively or engage with trolls
- NEVER post spam or repetitive content
---
## Phase 4 — Queue Management
If `approval_mode` is ENABLED:
1. Write generated posts/replies to `reddit_queue.json`
2. Write a human-readable `reddit_queue_preview.md` for review
3. event_publish "reddit_queue_updated" with queue size
4. Do NOT post — wait for user approval
If `approval_mode` is DISABLED:
1. Post content via the Reddit API
2. Log all posts to `reddit_posted.json`
3. Respect rate limits (10 requests per minute for OAuth)
---
## Phase 5 — Performance Tracking
Track engagement metrics:
- Post karma and comment karma changes
- Reply engagement (upvotes on your comments)
- Thread growth on posts you created
- Community reception patterns
Store insights in knowledge graph for content optimization.
### Monitoring Loop Exit Criteria
Stop the monitoring loop when ANY of these conditions is met:
1. **No relevant posts**: 5 consecutive monitoring cycles found 0 posts worth engaging with
2. **Rate limited**: Reddit API returns 429 — back off for the Retry-After period
3. **Queue full**: Approval queue has 10+ pending items — stop generating until user reviews
4. **Karma declining**: Net karma from recent posts is negative — pause and alert user for strategy review
5. **Iteration cap**: 20+ monitoring iterations in a single session — save state and exit
---
## Phase 6 — State Persistence
1. Save queue to `reddit_queue.json`
2. Save posting history to `reddit_posted.json`
3. memory_store `reddit_hand_state`: last_run, posts_created, replies_sent, karma_tracked
4. Update dashboard stats:
- memory_store `reddit_hand_posts_created` — total posts
- memory_store `reddit_hand_replies_sent` — total replies
- memory_store `reddit_hand_queue_size` — current queue size
- memory_store `reddit_hand_karma_earned` — estimated karma from tracked posts
---
## Guidelines
- ALWAYS respect subreddit rules — read the sidebar before posting
- NEVER post spam, self-promotion abuse, or vote manipulation
- NEVER harass, bully, or engage in bad-faith arguments
- NEVER impersonate other users
- NEVER post private or confidential information
- Respect Reddit's API rate limits (10 req/min for OAuth, 30 req/min with user auth)
- In `approval_mode` (default), ALWAYS write to queue — NEVER post without review
- If the API returns an error, log it and retry once — then skip and alert the user
- Adapt tone to each subreddit's culture
- When in doubt about a post, queue it for review with a note
"""
[dashboard]
[[dashboard.metrics]]
label = "Posts Created"
memory_key = "reddit_hand_posts_created"
format = "number"
[[dashboard.metrics]]
label = "Replies Sent"
memory_key = "reddit_hand_replies_sent"
format = "number"
[[dashboard.metrics]]
label = "Queue Size"
memory_key = "reddit_hand_queue_size"
format = "number"
[[dashboard.metrics]]
label = "Karma Earned"
memory_key = "reddit_hand_karma_earned"
format = "number"
[[dashboard.metrics]]
label = "Subreddits Monitored"
memory_key = "reddit_hand_subreddits_monitored"
format = "number"
# ─── Token & Performance Metadata ─────────────────────────────────────────────
[metadata]
frequency = "hourly"
token_consumption = "medium"
default_active = false
# ─── Internationalization (optional) ─────────────────────────────────────────
# All i18n sections are optional. Without them, the English values above are used.
# To localize, add [i18n.LANG] sections (e.g. zh, ja, ko, es, fr, de).
# Settings translations are also optional — omit to keep English labels.
# ─── Chinese (简体中文) ────────────────────────────────────────────────────
[i18n.zh]
name = "Reddit Hand"
description = "自主 Reddit 管理——监控子版块、发布内容、回复帖子并追踪 Karma 和互动"
category = "通信"
[i18n.zh.settings.subreddits]
label = "子版块"
description = "要监控的子版块列表(逗号分隔,例如 rust,programming,machinelearning)"
[i18n.zh.settings.monitor_mode]
label = "监控模式"
description = "在监控的子版块中追踪哪些内容"
[i18n.zh.settings.auto_reply]
label = "自动回复"
description = "自动回复相关的帖子和评论"
[i18n.zh.settings.post_frequency]
label = "发布频率"
description = "创建原创帖子的频率"
[i18n.zh.settings.content_style]
label = "内容风格"
description = "帖子和回复的语气和风格"
[i18n.zh.settings.approval_mode]
label = "审批模式"
description = "将帖子和回复加入队列等待审核,而非直接发布"
[i18n.zh.settings.min_karma_to_post]
label = "最低发帖 Karma"
description = "仅在账户拥有至少此数量 Karma 的子版块中发帖"
[i18n.zh.settings.max_reply_depth]
label = "最大回复深度"
description = "回复的最大评论嵌套深度(深层嵌套的可见度较低)"
# ─── Spanish (Español) ────────────────────────────────────────────────────
[i18n.es]
name = "Hand de Reddit"
description = "Gestor autónomo de Reddit — monitorea subreddits, publica contenido, responde en hilos y rastrea karma e interacciones"
category = "Comunicación"
[i18n.es.settings.subreddits]
label = "Subreddits"
description = "Lista de subreddits a monitorear separados por comas (ej. rust,programming,machinelearning)"
[i18n.es.settings.monitor_mode]
label = "Modo de monitoreo"
description = "Qué rastrear en los subreddits monitoreados"
[i18n.es.settings.auto_reply]
label = "Respuesta automática"
description = "Responder automáticamente a publicaciones y comentarios relevantes"
[i18n.es.settings.post_frequency]
label = "Frecuencia de publicación"
description = "Con qué frecuencia crear publicaciones originales"
[i18n.es.settings.content_style]
label = "Estilo de contenido"
description = "Tono y enfoque para publicaciones y respuestas"
[i18n.es.settings.approval_mode]
label = "Modo de aprobación"
description = "Poner publicaciones y respuestas en cola para revisión en lugar de publicarlas directamente"
[i18n.es.settings.min_karma_to_post]
label = "Karma mínimo para publicar"
description = "Solo publicar en subreddits donde la cuenta tenga al menos este nivel de karma"
[i18n.es.settings.max_reply_depth]
label = "Profundidad máxima de respuesta"
description = "Profundidad máxima del hilo de comentarios para responder (los hilos más profundos tienen menos visibilidad)"
# ─── Japanese (日本語) ────────────────────────────────────────────────────
[i18n.ja]
name = "Reddit Hand"
description = "自律型Redditマネージャー——サブレディットの監視、コンテンツ投稿、スレッドへの返信、Karmaとエンゲージメントの追跡"
category = "コミュニケーション"
[i18n.ja.settings.subreddits]
label = "サブレディット"
description = "監視するサブレディットのリスト(カンマ区切り、例: rust,programming,machinelearning)"
[i18n.ja.settings.monitor_mode]
label = "監視モード"
description = "監視対象のサブレディットで追跡する内容"
[i18n.ja.settings.auto_reply]
label = "自動返信"
description = "関連する投稿やコメントに自動で返信する"
[i18n.ja.settings.post_frequency]
label = "投稿頻度"
description = "オリジナル投稿を作成する頻度"
[i18n.ja.settings.content_style]
label = "コンテンツスタイル"
description = "投稿と返信のトーンとアプローチ"
[i18n.ja.settings.approval_mode]
label = "承認モード"
description = "投稿や返信を直接公開せず、レビュー用キューに追加する"
[i18n.ja.settings.min_karma_to_post]
label = "投稿に必要な最低Karma"
description = "アカウントが最低このKarmaを持つサブレディットでのみ投稿する"
[i18n.ja.settings.max_reply_depth]
label = "最大返信深度"
description = "返信するコメントスレッドの最大ネスト深度(深いスレッドほど可視性が低い)"
# ─── French (Français) ────────────────────────────────────────────────────
[i18n.fr]
name = "Hand Reddit"
description = "Gestionnaire Reddit autonome — surveille les subreddits, publie du contenu, répond dans les fils et suit le karma et l'engagement"
category = "Communication"
[i18n.fr.settings.subreddits]
label = "Subreddits"
description = "Liste de subreddits à surveiller séparés par des virgules (ex. rust,programming,machinelearning)"
[i18n.fr.settings.monitor_mode]
label = "Mode de surveillance"
description = "Ce qu'il faut suivre dans les subreddits surveillés"
[i18n.fr.settings.auto_reply]
label = "Réponse automatique"
description = "Répondre automatiquement aux publications et commentaires pertinents"
[i18n.fr.settings.post_frequency]
label = "Fréquence de publication"
description = "Fréquence de création de publications originales"
[i18n.fr.settings.content_style]
label = "Style de contenu"
description = "Ton et approche pour les publications et réponses"
[i18n.fr.settings.approval_mode]
label = "Mode d'approbation"
description = "Mettre les publications et réponses en file d'attente pour révision au lieu de les publier directement"
[i18n.fr.settings.min_karma_to_post]
label = "Karma minimum pour publier"
description = "Ne publier que dans les subreddits où le compte possède au moins ce niveau de karma"
[i18n.fr.settings.max_reply_depth]
label = "Profondeur maximale de réponse"
description = "Profondeur maximale d'imbrication des commentaires pour répondre (les fils plus profonds ont moins de visibilité)"
# ─── German (Deutsch) ────────────────────────────────────────────────────
[i18n.de]
name = "Reddit-Hand"
description = "Autonomer Reddit-Manager — überwacht Subreddits, postet Inhalte, antwortet in Threads und verfolgt Karma und Engagement"
category = "Kommunikation"
[i18n.de.settings.subreddits]
label = "Subreddits"
description = "Kommagetrennte Liste der zu überwachenden Subreddits (z.B. rust,programming,machinelearning)"
[i18n.de.settings.monitor_mode]
label = "Überwachungsmodus"
description = "Was in den überwachten Subreddits verfolgt werden soll"
[i18n.de.settings.auto_reply]
label = "Automatische Antwort"
description = "Automatisch auf relevante Beiträge und Kommentare antworten"
[i18n.de.settings.post_frequency]
label = "Veröffentlichungshäufigkeit"
description = "Wie oft originale Beiträge erstellt werden"
[i18n.de.settings.content_style]
label = "Inhaltsstil"
description = "Ton und Ansatz für Beiträge und Antworten"
[i18n.de.settings.approval_mode]
label = "Genehmigungsmodus"
description = "Beiträge und Antworten zur Überprüfung in die Warteschlange stellen, anstatt sie direkt zu veröffentlichen"
[i18n.de.settings.min_karma_to_post]
label = "Mindest-Karma zum Posten"
description = "Nur in Subreddits posten, in denen das Konto mindestens dieses Karma-Level hat"
[i18n.de.settings.max_reply_depth]
label = "Maximale Antworttiefe"
description = "Maximale Verschachtelungstiefe für Kommentarantworten (tiefere Threads haben geringere Sichtbarkeit)"
# ─── Korean (한국어) ────────────────────────────────────────────────────
[i18n.ko]
name = "Reddit Hand"
description = "자율 Reddit 관리 — 서브레딧 모니터링, 콘텐츠 게시, 스레드 댓글 및 카르마와 참여도 추적"
category = "커뮤니케이션"
[i18n.ko.settings.subreddits]
label = "서브레딧"
description = "모니터링할 서브레딧 목록 (쉼표로 구분, 예: rust,programming,machinelearning)"
[i18n.ko.settings.monitor_mode]
label = "모니터링 모드"
description = "모니터링 대상 서브레딧에서 추적할 콘텐츠"
[i18n.ko.settings.auto_reply]
label = "자동 답글"
description = "관련 게시물과 댓글에 자동으로 답글 작성"
[i18n.ko.settings.post_frequency]
label = "게시 빈도"
description = "원본 게시물 작성 주기"
[i18n.ko.settings.content_style]
label = "콘텐츠 스타일"
description = "게시물과 답글의 어조와 접근 방식"
[i18n.ko.settings.approval_mode]
label = "승인 모드"
description = "게시물과 답글을 직접 게시하지 않고 대기열에 추가하여 검토"
[i18n.ko.settings.min_karma_to_post]
label = "최소 게시 카르마"
description = "계정이 최소 이만큼의 카르마를 보유한 서브레딧에서만 게시"
[i18n.ko.settings.max_reply_depth]
label = "최대 답글 깊이"
description = "답글 작성의 최대 댓글 중첩 깊이 (깊은 중첩일수록 노출도 감소)"