Discord Bot
A character answers in Discord text channels, one server-started chat per channel, while you are away from the machine.
Discord Bot puts one of your characters in Discord text channels. Each channel gets its own chat, started and run by the server, so it keeps answering with no browser open. The chats show in your chats list and can be opened to watch.
Only want a "Chatting with …" status on your own Discord profile? That is the Discord Rich Presence service.
| Cost | Free (your LLM usage aside). |
| Hosting | Built in. Text only: no voice channels. |
| Requires | A Discord application of your own, and a server where you have Manage Server. |
| Who can add it | Administrators, and shared accounts. |
Experimental. Explicit characters can't be used.
Setup
Create the Discord application
In the Discord Developer Portal: New Application, then on the Bot tab copy the token, turn on Message Content Intent and leave Requires OAuth2 Code Grant off. Under Installation, tick Guild Install.
The application's name and icon are what people see on Discord.
Add the service
Manage Modules → Add Modules → Discord Bot → Install. Fill in:
- Bot token — from the Bot tab.
- Channel IDs — turn on Developer Mode in Discord, right-click a channel, Copy Channel ID. One entry per channel.
- Character — who answers.
- Scenario — leave on Auto unless you have your own.
Save.
Invite the bot
Press Get invite link and open it. It asks only for View Channel, Send Messages and Read Message History.
For a private channel: Edit Channel → Permissions, +, and find the bot under Roles.
Check it
Send test message posts into every listed channel and reports what Discord said. The service's Test walks the whole chain — token, servers, channels, character, connection, message content — and says which link is broken.
One install is one Discord application answering as one character. For a second character, create a second application and add the service again.
How it answers
Answer decides when the character speaks. Messages it does not answer are still kept, so it knows what was said.
| Choice | Behaviour |
|---|---|
| Only when mentioned (default) | Answers an @mention, or a message containing the character's name. |
| When mentioned, or when it has something to add | Mentions are answered at once. Otherwise it waits for the room to go quiet, then your Action Inference service decides whether to reply. The more often it stays silent, the longer it waits before checking again. |
| Every message | Answers everything. Best in a channel made for the bot. |
- Messages arriving together are answered as one turn. It pauses as if typing, and holds back while someone else is typing (up to Answer anyway after).
- Replies are posted one Discord message per line; code blocks stay whole.
- The last 20 messages of the channel are loaded when its chat starts.
- Images posted in the channel (PNG, JPEG, GIF, WebP, up to 8 MB) are passed to the chat. Earlier history is text only.
- Other bots are ignored, including other Voxta bots.
What a bot chat leaves out
- No voice: text-to-speech and speech-to-text are not loaded, which leaves the GPU to the LLM.
- Augmentations run only if the character or scenario names them explicitly. Automatic ones (and a
*selection) are off. - The clock is UTC, so your time zone is not published.
The Auto scenario
On first start, Auto writes a scenario called Discord into your library: the character is in a channel with several people, talking to Discord Users, and waits before replying. It is yours to edit afterwards. Its template can use {{ variables.discord_channel }}, {{ variables.discord_channel_id }} and {{ variables.discord_server }}.
Running and stopping
- Start the bot automatically is on by default. Start bot / Stop bot override it until the server restarts.
- Check status shows whether Discord accepted the connection and what it has seen.
- New conversation closes the channel chats and starts fresh, reloading recent history.
- Configuration → Chat Bridges lists every bot and whether it is running.
- If replies fail (no credit, a model that will not load), the channel is told once, and the bot keeps trying.
Limits
Concurrent chats. Every channel is a chat, and an account may run 2 at once by default. A channel over the limit is retried every 30 seconds. To raise it, set ChatSessions:MaxConcurrentChatsPerUser in appsettings.User.json.
Rate limits. Messages per person, per hour (default 50) and Messages per channel, per hour (default 200). Past them the channel is told once and further messages are ignored for a while. 0 means no limit.
Encryption. With encryption on, the bot only runs while the account is unlocked. Device mode: always. Password mode: from sign-in until the key is released, about an hour after your last activity. It reconnects by itself.
Run it on a shared account
A bot is best given a shared account of its own, with its own characters, services and chats. An administrator creates one in Administration → Users Management → Create Shared Account, then uses Act as to step into it and add the service there. Nobody signs in to a shared account; administrators it is granted to act as it.
Shared accounts only use Device-mode encryption, so a bot there is not stopped by a locked key.
Pacing (advanced)
| Setting | Default | Notes |
|---|---|---|
| Collect messages for (ms) | 1500 | Wait for more messages before answering, when idle. |
| Backoff step (ms) | 10000 | "Something to add" mode only: the wait grows by one step each time it stays silent, up to six. |
| Typing pause, shortest / longest (ms) | 2000 / 5000 | Before answering and between lines, picked at random in this range. |
| Answer anyway after (ms) | 20000 | The most someone typing can hold a reply back. |
Troubleshooting
- Connected, but never answers: turn on Message Content Intent, then restart the bot. Without it every message arrives empty.
- Invite says success, nothing joins: you need Manage Server on that Discord server. Otherwise turn off Requires OAuth2 Code Grant on the Bot tab and tick Guild Install.
- Token rejected: Discord refuses the connection and the bot does not retry until you fix the token.