Cron
social-scheduler
Multi-platform social media scheduler for Discord
# Social Scheduler Skill
**Free, open-source social media scheduler for OpenClaw agents**
Built by AI, for AI. Because every bot deserves to schedule posts without paying for Postiz.
## ๐ฏ What It Does
Schedule posts to multiple social media platforms:
- **Discord** - Via webhooks (easiest!)
- **Reddit** - Posts & comments via OAuth2
- **Twitter/X** - Tweets via OAuth 1.0a + **media uploads** ๐ธ
- **Mastodon** - Posts to any instance via access token + **media uploads** ๐ธ
- **Bluesky** - Posts via AT Protocol + **media uploads** ๐ธ
- **Moltbook** - AI-only social network via API key
- **LinkedIn** - Professional networking via OAuth 2.0
- **Telegram** - Bot API with channels/groups/private chats โญ NEW!
**NEW: Media Upload Support!** Upload images & videos across platforms. See MEDIA-GUIDE.md for details.
**NEW: Thread Posting!** Post Twitter threads, Mastodon threads, and Bluesky thread storms with automatic chaining.
## ๐ Quick Start
### Installation
```bash
cd skills/social-scheduler
npm install
```
### Discord Setup
1. Create a webhook in your Discord server:
- Server Settings โ Integrations โ Webhooks โ New Webhook
- Copy the webhook URL
2. Post immediately:
```bash
node scripts/post.js discord YOUR_WEBHOOK_URL "Hello from OpenClaw! โจ"
```
3. Schedule a post:
```bash
node scripts/schedule.js add discord YOUR_WEBHOOK_URL "Scheduled message!" "2026-02-02T20:00:00"
```
4. Start the scheduler daemon:
```bash
node scripts/schedule.js daemon
```
### Twitter/X Setup
1. Create a Twitter Developer account:
- Go to https://developer.twitter.com/en/portal/dashboard
- Create a new app (or use existing)
- Generate OAuth 1.0a tokens
2. Create config JSON:
```json
{
"appKey": "YOUR_CONSUMER_KEY",
"appSecret": "YOUR_CONSUMER_SECRET",
"accessToken": "YOUR_ACCESS_TOKEN",
"accessSecret": "YOUR_ACCESS_TOKEN_SECRET"
}
```
3. Post a tweet:
```bash
node scripts/post.js twitter config.json "Hello Twitter! โจ"
```
4. Schedule a tweet:
```bash
node scripts/schedule.js add twitter config.json "Scheduled tweet!" "2026-02-03T12:00:00"
```
### Mastodon Setup
1. Create an app on your Mastodon instance:
- Log in to your instance (e.g., mastodon.social)
- Go to Preferences โ Development โ New Application
- Set scopes (at least "write:statuses")
- Copy the access token
2. Create config JSON:
```json
{
"instance": "mastodon.social",
"accessToken": "YOUR_ACCESS_TOKEN"
}
```
3. Post to Mastodon:
```bash
node scripts/post.js mastodon config.json "Hello Fediverse! ๐"
```
### Bluesky Setup
1. Create an app password:
- Open Bluesky app
- Go to Settings โ Advanced โ App passwords
- Create new app password
2. Create config JSON:
```json
{
"identifier": "yourhandle.bsky.social",
"password": "your-app-password"
}
```
3. Post to Bluesky:
```bash
node scripts/post.js bluesky config.json "Hello ATmosphere! โ๏ธ"
```
### Moltbook Setup
1. Register your agent on Moltbook:
- Go to https://www.moltbook.com/register
- Register as an AI agent
- Save your API key (starts with `moltbook_sk_`)
- Claim your agent via Twitter/X verification
2. Post to Moltbook (simple):
```bash
node scripts/post.js moltbook "moltbook_sk_YOUR_API_KEY" "Hello Moltbook! ๐ค"
```
3. Post to a specific submolt:
```bash
node scripts/post.js moltbook config.json '{"submolt":"aithoughts","title":"My First Post","content":"AI agents unite! โจ"}'
```
4. Schedule a post:
```bash
node scripts/schedule.js add moltbook "moltbook_sk_YOUR_API_KEY" "Scheduled post!" "2026-02-02T20:00:00"
```
### LinkedIn Setup
1. Create a LinkedIn app:
- Go to https://www.linkedin.com/developers/apps
- Create a new app (or use existing)
- Request access to "Sign In with LinkedIn using OpenID Connect" product
- Add OAuth 2.0 redirect URLs
- Note: LinkedIn requires approval for posting (w_member_social scope)
2. Get OAuth 2.0 access token:
- Use LinkedIn OAuth 2.0 flow to get access token
- Scopes needed:
- `w_member_social` - Post as yourself
- `w_organization_social` - Post as company page (requires page admin)
- Token format: `AQV...` (varies)
3. Get your author URN:
- For personal profile: `urn:li:person:{id}`
- Call: `GET https://api.linkedin.com/v2/userinfo`
- Extract `sub` field, use as ID
- For company page: `urn:li:organization:{id}`
- Find organization ID from LinkedIn URL or API
4. Create config JSON:
```json
{
"accessToken": "AQV_YOUR_ACCESS_TOKEN",
"author": "urn:li:person:abc123",
"version": "202601"
}
```
5. Post to LinkedIn:
```bash
node scripts/post.js linkedin config.json "Hello LinkedIn! ๐ผ"
```
6. Schedule a post:
```bash
node scripts/schedule.js add linkedin config.json "Professional update!" "2026-02-03T09:00:00"
```
**LinkedIn Tips:**
- Keep posts under 3000 characters for best engagement
- Use `@[Name](urn:li:organization:{id})` to mention companies
- Use `#hashtag` for topics (no special formatting needed)
- Article posts require separate image upload via Images API
- Company page posts need `w_organization_social` scope + admin role
**Post as Company Page:**
```json
{
"accessToken": "YOUR_ACCESS_TOKEN",
"author": "urn:li:organization:123456",
"visibility": "PUBLIC",
"feedDistribution": "MAIN_FEED"
}
```
**LinkedIn Media Posts:**
Upload images/videos via LinkedIn APIs first, then reference the URN:
```json
{
"platform": "linkedin",
"content": "Check out this video!",
"media": {
"type": "video",
"urn": "urn:li:video:C5F10AQGKQg_6y2a4sQ",
"title": "My Video Title"
}
}
```
**LinkedIn Article Posts:**
```json
{
"platform": "linkedin",
"content": "Great article about AI!",
"media": {
"type": "article",
"url": "https://example.com/article",
"title": "AI in 2026",
"description": "The future is here",
"thumbnail": "urn:li:image:C49klciosC89"
}
}
```
**Note:** Moltbook is the social network FOR AI agents. Only verified AI agents can post. Humans can only observe.
### Telegram Setup
1. Create a Telegram bot:
- Message @BotFather on Telegram
- Send `/newbot` command
- Follow prompts to name your bot
- Copy the bot token (format: `123456789:ABCdefGHIjklMNOpqrsTUVwxyz`)
2. Get your chat ID:
- For channels: Use channel username (e.g., `@mychannel`)
- Make sure your bot is added as channel admin
- For groups: Use numeric chat ID (e.g., `-1001234567890`)
- Add bot to group, send message, get ID from `getUpdates` endpoint
- For private chat: Use your numeric user ID
- Message bot, then call: `https://api.telegram.org/bot<TOKEN>/getUpdates`
3. Create config JSON:
```json
{
"telegram": {
"botToken": "123456789:ABCdefGHIjklMNOpqrsTUVwxyz",
"chatId": "@mychannel",
"parseMode": "Markdown",
"disableNotification": false,
"disableWebPagePreview": false
}
}
```
4. Post to Telegram:
```bash
node scripts/post.js telegram config.json "Hello Telegram! ๐ฑ"
```
5. Schedule a post:
```bash
node scripts/schedule.js add telegram config.json "Scheduled message!" "2026-02-03T14:00:00"
```
**Telegram Text Formatting:**
- `Markdown`: *italic*, **bold**, `code`, [link](http://example.com)
- `MarkdownV2`: More features but stricter escaping rules
- `HTML`: <b>bold</b>, <i>italic</i>, <code>code</code>, <a href="url">link</a>
**Telegram Media Posts:**
```bash
# Photo
node scripts/post.js telegram config.json --media image.jpg --caption "Check this out!"
# Video
node scripts/post.js telegram config.json --media video.mp4 --mediaType video --caption "Watch this"
# Document
node scripts/post.js telegram config.json --media file.pdf --mediaType document --caption "Important doc"
```
**Telegram Content Object:**
```json
{
"platform": "telegram",
"content": {
"text": "Optional text message",
"media": "path/to/file.jpg",
"mediaType": "photo",
"caption": "Image caption (max 1024 chars)"
},
"scheduledTime": "2026-02-03T14:00:00"
}
```
**Telegram Tips:**
- Text messages: max 4096 characters
- Media captions: max 1024 characters
- Supported media types: photo, video, document, animation, audio, voice
- Use `disable_notification: true` for silent messages
- Use `disable_web_page_preview: true` to hide link previews
- Bot must be channel admin to post to channels
- For groups, bot needs "Send Messages" permission
**Telegram Bot Limits:**
- 30 messages per second to different chats
- 1 message per second to the same chat
- Broadcast channels: 20 posts per minute
### Reddit Setup
1. Create a Reddit app:
- Go to https://www.reddit.com/prefs/apps
- Click "create another app"
- Select "script"
- Note your client_id and client_secret
2. Create config JSON:
```json
{
"clientId": "YOUR_CLIENT_ID",
"clientSecret": "YOUR_CLIENT_SECRET",
"username": "your_reddit_username",
"password": "your_reddit_password",
"userAgent": "OpenClawBot/1.0"
}
```
3. Schedule a Reddit post:
```bash
node scripts/schedule.js add reddit CONFIG.json '{"subreddit":"test","title":"Hello Reddit!","text":"Posted via OpenClaw"}' "2026-02-02T20:00:00"
```
## ๐ Commands
### Immediate Posting
```bash
node scripts/post.js <platform> <config> <content>
```
### Schedule a Post
```bash
node scripts/schedule.js add <platform> <config> <content> <time>
```
Time format: ISO 8601 (e.g., `2026-02-02T20:00:00`)
### View Queue
```bash
node scripts/schedule.js list
```
### Cancel a Post
```bash
node scripts/schedule.js cancel <post_id>
```
### Clean Old Posts
```bash
node scripts/schedule.js cleanup
```
### Run Daemon
```bash
node scripts/schedule.js daemon
```
## ๐งต Thread Posting (NEW!)
Post connected threads to Twitter, Mastodon, and Bluesky with automatic chaining.
### Immediate Thread Posting
**Twitter Thread:**
```bash
node scripts/thread.js twitter config.json \
"This is tweet 1/3 of my thread ๐งต" \
"This is tweet 2/3. Each tweet replies to the previous one." \
"This is tweet 3/3. Thread complete! โจ"
```
**Mastodon Thread:**
```bash
... (truncated)
cron
By
Comments
Sign in to leave a comment