Discord
Everything Discord lives in discord.yml. There are two ways an alert can leave the server, and
DaisyFilter always prefers the first:
| Bot | Webhook fallback | |
|---|---|---|
| Sends | Metadata and the masked preview; the message itself only via Reveal, or if you turn show-full-message on | Metadata and the masked preview only |
| Staff can act from Discord | Yes — buttons on every alert | No |
| Needs a bot application | Yes | No |
| Used when | It is configured and connected | The bot could not deliver |
The webhook is a safety net, not a second feed — nothing is ever posted twice. It takes over when
the bot is not configured, is not connected, or when Discord rejects a specific post. It inherits the
bot’s min-severity and enforced-only, so an outage cannot quietly change which incidents staff
hear about.
It stays metadata-only even during a failover. A webhook URL usually points somewhere less restricted than the bot’s channel, so an outage must not become the moment player content starts going there. A failover alert therefore tells you less than the bot’s would have.
Set only the webhook URL and no bot token, and it behaves as a plain metadata log, without the JDA
download. There is no separate webhook.yml: everything Discord lives in this one file.
Who sees the message
Section titled “Who sees the message”By default an alert shows the masked preview — who, category, severity, and the action buttons —
plus a Reveal full message button. Only roles mapped daisyfilter.view.raw can use it, and the
message is returned privately to whoever clicked, so nobody else in the channel sees it.
That is the arrangement you want for a shared logs channel: a moderator can mute or kick straight from the alert without the whole team reading what a child typed, and a senior staff member can pull up the exact wording when a flag needs judging.
show-full-message: true puts the message straight into the alert instead. Turn it on only where
every member of the channel is already trusted with exact evidence, because:
- The channel’s permissions become the only access control. The roles map stops protecting message content — anyone who can read the channel reads every flagged message, including people added later.
- Discord history does not expire. DaisyFilter purges its own records after 30 days; alerts stay until someone deletes them, and it cannot be undone after the fact.
- Content lives on Discord’s servers under Discord’s terms. If your players are children, or you have data-protection obligations, that is a decision to take deliberately.
Setting it up
Section titled “Setting it up”- Create an application at https://discord.com/developers/applications, add a bot, and copy the token. No privileged intents are required.
- Invite it to your server with Send Messages in the alert channel.
- Fill in
discord.yml— or open the dashboard and click Integrations, which writes the same settings without touching the file. - Restart. The token and the
enabledswitch are read once, when the gateway connects; everything else takes effect immediately.
enabled: truebot-token: "..."guild-id: "112233445566778899"alert-channel-id: "998877665544332211"min-severity: 3enforced-only: trueshow-full-message: false # true puts the message in the alert for everyonelink-required: trueroles: "112233445566778899": # Moderator role ID - daisyfilter.punish.mute - daisyfilter.punish.kick "998877665544332211": # Admin role ID - daisyfilter.punish.banwebhook: url: "https://discord.com/api/webhooks/..." # optional fallbackQuote the role IDs. Unquoted, YAML reads a snowflake as a number rather than text. DaisyFilter compares them as text either way, so it works — but quoted is what the file should look like.
Who can punish
Section titled “Who can punish”Two things must both hold.
A linked account. Run /df link in game; you get a one-time code, valid five minutes. Run
/link <code> in Discord. The code is generated in game on purpose — redeeming it proves the Discord
user controls that Minecraft account, which is the claim worth establishing before handing out
punishment powers.
The link supplies the identity written to the staff audit log, so a punishment issued from Discord is
indistinguishable from one issued in game in /daisyfilter audit. That is deliberate: they have
identical consequences for the player.
A mapped role. Permissions come only from the roles map — never from the staff member’s in-game
rank, which cannot be consulted while they are offline. An unlisted role grants nothing, and there is
no inheritance: mapping daisyfilter.admin does not confer daisyfilter.punish.ban. List every
node you intend to grant.
The role map is editable only in the file, not from the GUI. It decides who can punish, so a change should be reviewable.
Everything is re-checked when a button is clicked, not when the alert was posted. Revoking a Discord role immediately disarms buttons that were posted before you revoked it, and a user who cannot use an action is told which permission is missing rather than having the click silently ignored.
What the buttons do
Section titled “What the buttons do”Each alert carries a button per enabled punishment profile from actions.yml, so the actions match
what the in-game punish menu offers. Profiles with durations (mute, temp ban) open a short prompt
pre-filled with the first preset. A Reveal full message button appears whenever the alert is not
already showing the message.
Replies are ephemeral — only the clicker sees them. One short public line is added to the alert recording who acted and what they did, so the channel shows an incident as handled at a glance.
Troubleshooting
Section titled “Troubleshooting”Nothing is posted. Check enabled, the token, and alert-channel-id, then that the bot can see
and post in that channel. Incidents below min-severity, and monitor-only ones while
enforced-only: true, are dropped by design.
/link does not appear in Discord. Slash commands are registered against guild-id when the
gateway connects. If it is blank or wrong, the command is registered globally instead and can take up
to an hour to appear.
A button says the action is unavailable. The message names the reason — usually the profile is
disabled in actions.yml, or the clicker’s Discord role is not mapped to that permission.
First boot is slow or fails offline. JDA and the database drivers are fetched from Maven Central by Paper’s library loader on first start, then cached. This happens whether or not Discord is enabled.