executing-plans
executing-plans
Use when executing an implementation plan in the current session as the implementer yourself — your human partner chose inline execution, or no subagent tool is available
discordbotList channels, read recent messages, send channel messages, and send a single user-initiated DM on Discord using the user's own bot via the Discord REST API.
Independent GitHub snapshot · Automated classification · Original documentation governs
We drive the Discord API
with curl + jq using the user's bot token in $DISCORDBOT_TOKEN. The
auth header is Authorization: Bot $DISCORDBOT_TOKEN — note the literal
Bot prefix (NOT Bearer). Base URL is https://discord.com/api/v10.
This acts as the user's registered bot, so it can only see and act in
servers (guilds) the bot has been invited to and only where it has the
relevant permission (View Channels / Send Messages / Read Message History).
A 403 Forbidden (code 50001 "Missing Access" / 50013 "Missing
Permissions") almost always means the bot isn't in that server or lacks the
permission — tell the user to invite the bot or grant the permission rather
than retrying.
Errors are JSON {"code": <n>, "message": "<reason>"}. A 401 means the
bot token is wrong/reset — ask the user to re-paste it at
studio.acedata.cloud/console/connectors. A 429 carries retry_after
(seconds) — sleep that long, then retry; never parallelize.
recipient_id, consent_channel_id,
consent_message_id, consent_keyword, and approved content. If any is
missing, return a draft without sending.stop, unsubscribe,
or an equivalent refusal as a permanent opt-out.curl -sS -H "Authorization: Bot $DISCORDBOT_TOKEN" \
"https://discord.com/api/v10/users/@me" \
| jq '{id, username, bot}'
curl -sS -H "Authorization: Bot $DISCORDBOT_TOKEN" \
"https://discord.com/api/v10/users/@me/guilds" \
| jq 'map({id, name})'
Channel type 0 = text, 5 = announcement; 2 = voice, 4 = category (skip
those for messaging). You need a guild id from the call above.
GUILD_ID="123456789012345678"
curl -sS -H "Authorization: Bot $DISCORDBOT_TOKEN" \
"https://discord.com/api/v10/guilds/$GUILD_ID/channels" \
| jq 'map(select(.type==0 or .type==5) | {id, name, type})'
Reading message content requires the Message Content Intent to be
enabled on the bot (Developer Portal → Bot → Privileged Gateway Intents).
Without it, content comes back empty for messages that don't mention the
bot. Needs the Read Message History permission in that channel.
CHANNEL_ID="123456789012345678"
curl -sS -H "Authorization: Bot $DISCORDBOT_TOKEN" \
"https://discord.com/api/v10/channels/$CHANNEL_ID/messages?limit=20" \
| jq 'map({id, author_id: .author.id, author: .author.username, author_bot: .author.bot, ts: .timestamp, content})'
CHANNEL_ID="123456789012345678"
curl -sS -X POST \
-H "Authorization: Bot $DISCORDBOT_TOKEN" \
-H "Content-Type: application/json" \
"https://discord.com/api/v10/channels/$CHANNEL_ID/messages" \
-d "$(jq -nc --arg c "Hello from the bot." '{content: $c}')"
CHANNEL_ID="123456789012345678"; MESSAGE_ID="987654321098765432"
curl -sS -X POST \
-H "Authorization: Bot $DISCORDBOT_TOKEN" \
-H "Content-Type: application/json" \
"https://discord.com/api/v10/channels/$CHANNEL_ID/messages" \
-d "$(jq -nc --arg c "On it!" --arg m "$MESSAGE_ID" \
'{content: $c, message_reference: {message_id: $m}}')"
Use only after applying every rule in Sending safety. The helper fetches
the source message from Discord and verifies that its non-bot author matches
RECIPIENT_ID and its complete text matches CONSENT_KEYWORD. Do not call the
Create DM endpoint directly. Matching is case-insensitive and collapses
surrounding or repeated whitespace.
RECIPIENT_ID="123456789012345678"
CONSENT_CHANNEL_ID="223456789012345678"
CONSENT_MESSAGE_ID="323456789012345678"
CONSENT_KEYWORD="details"
python3 "$SKILL_DIR/scripts/discordbot.py" send-opt-in-dm \
--recipient-id "$RECIPIENT_ID" \
--consent-channel-id "$CONSENT_CHANNEL_ID" \
--consent-message-id "$CONSENT_MESSAGE_ID" \
--consent-keyword "$CONSENT_KEYWORD" \
--content "Here are the details you requested."
The command is a dry-run unless the final argument is --confirm. In a
pre-authorized scheduled task, use final --unattended-confirm instead. The
helper validates all IDs, verifies the opt-in message, and skips an identical
message already present in the DM history. Discord may block or rate-limit bots
that open many DMs; do not retry by targeting another account.
bot + the permissions you need → open the
URL → pick a server (the user needs Manage Server there).<@USER_ID> pings a user, <#CHANNEL_ID> links a channel. Plain
text is fine for normal messages.