FiveM Discord Integration: Webhooks, Logs and Roles

Discord is the command centre for almost every FiveM roleplay community. Done well, it gives your staff live logs, lets players join based on their Discord role, and pushes server status without anyone touching the panel. Done badly, it leaks webhook URLs, spams rate limits, and grants admin to the wrong people. This guide walks through the three pieces that matter most: webhooks for logging, ACE permissions tied to Discord roles, and the bot token / status setup, all checked against the official Cfx.re documentation.

1. Discord webhooks for FiveM logs

A Discord webhook is the simplest way to push events (joins, bans, kicks, transactions) into a channel. In Discord, open Channel Settings → Integrations → Webhooks → New Webhook, name it, choose the channel, and copy the webhook URL. Treat that URL like a password: anyone who has it can post to your channel.

FiveM sends to a webhook server-side using the native PerformHttpRequest function. Per the Cfx.re docs, its signature is PerformHttpRequest(url, callback, method, data, headers, options), where the callback receives statusCode, body, headers, errorData in that order. A minimal logger looks like this:

-- server-side script (e.g. resources/[local]/mylogs/server.lua)
local webhook = GetConvar("discord_log_webhook", "")

local function logToDiscord(title, message, color)
    if webhook == "" then return end
    local embed = {{
        ["title"] = title,
        ["description"] = message,
        ["color"] = color or 16711680
    }}
    PerformHttpRequest(webhook, function(statusCode, body, headers, errorData)
        -- 204 = success, anything else = inspect statusCode/errorData
    end, "POST", json.encode({embeds = embed}), {["Content-Type"] = "application/json"})
end

AddEventHandler("playerConnecting", function(name)
    logToDiscord("Player Connecting", ("`%s` is connecting."):format(name))
end)

Notice the webhook URL is read from a convar instead of being hard-coded. Put it in your server.cfg with set (not the public-facing sets) so it stays server-side:

# server.cfg - keep secrets out of version control
set discord_log_webhook "https://discord.com/api/webhooks/XXXX/YYYY"
ensure mylogs

Discord enforces rate limits, so don’t fire a webhook on every movement or tick. Batch events or queue them; a 429 response in statusCode means you’re being throttled. If you’d rather not write Lua, txAdmin and most logging resources expose a webhook field in their config — the same URL goes there.

2. ACE permissions via Discord roles

FiveM’s access control (ACE) system is the correct foundation for permissions — it’s what gates quit, txAdmin, and most admin menus. You define principals and grant them aces in server.cfg. Natively, you can map a player’s Discord ID directly to a group using the discord: identifier:

# server.cfg
add_ace group.admin command allow          # admins can run all commands
add_ace group.admin command.quit deny      # except a few

# attach a specific Discord user to the admin group
add_principal identifier.discord:123456789012345678 group.admin

That static approach works, but it’s per-user and manual. To grant permissions based on a Discord role (so promoting someone in Discord promotes them in-game), you need a resource that reads your guild via a bot token. The popular community options are DiscordAcePerms (documented on Badger) and similar role-to-ACE scripts. They follow the same pattern: install to resources/, grant the resource permission to add/remove principals, start it, and map role IDs to ACE groups.

# server.cfg - per DiscordAcePerms install steps
add_ace resource.DiscordAcePerms command.add_principal allow
add_ace resource.DiscordAcePerms command.remove_principal allow
ensure DiscordAcePerms

Inside the resource config you map Discord role IDs to groups, e.g. a role to group.admin and another to group.police. Because the exact config file name and the bot-token convar differ between versions of these third-party resources, always follow the README shipped with the version you downloaded rather than copying a tutorial verbatim. The one constant is that a bot must be in your guild with permission to read members.

3. Bot token and server status (txAdmin)

You don’t always need a custom resource — txAdmin (bundled with the server artifacts) has a built-in Discord bot. First create the bot in the Discord Developer Portal: New Application → Bot → Reset Token, copy the token, and enable the Server Members Intent (required for role checks). Then in txAdmin go to Settings → Discord, enable the bot, paste the token and your Server (Guild) ID, and optionally set an announcements channel.

For a live status embed that auto-updates player counts, type /status add in the target Discord channel. To gate joining by Discord membership or role, use Settings → Player Manager (the whitelist mode), where “Discord Role” restricts entry to specific role IDs. txAdmin’s role gating and a separate ACE-role resource solve different problems — one controls who can join, the other controls what they can do in-game.

MethodUse caseNeeds bot token?
Webhook + PerformHttpRequestLogging events to a channelNo
add_principal identifier.discord:Static per-user ACE grantNo
DiscordAcePerms / role-to-ACEDynamic in-game perms from Discord rolesYes
txAdmin Discord botStatus embed, announcements, join whitelistYes

Putting it together on your server

A typical RP stack runs all three: webhooks for action logs, a role-to-ACE resource for staff permissions, and the txAdmin bot for status and whitelisting. Keep tokens and webhook URLs in server.cfg with set, never sets, and never commit them. If you’re choosing where to run all this, our dedicated FiveM hosting plans ship with txAdmin pre-installed and full server.cfg access, and our FiveM documentation covers the panel side step by step. If you’re still assembling your framework, see our QBCore install guide and the admin menu setup guide, which both build on the ACE system covered here.

Frequently asked questions

Do Discord webhooks need a bot token?

No. Webhooks are a separate, simpler mechanism — you just create the webhook URL in Discord channel settings and POST to it with PerformHttpRequest. A bot token is only required when something needs to read your guild, such as checking a member’s roles for ACE permissions or running the txAdmin status bot.

Why aren’t my Discord roles granting in-game permissions?

The most common causes are a missing Server Members Intent on the bot, a bot that isn’t actually in your guild, an incorrect Guild ID, or role IDs that don’t match. Confirm the resource has command.add_principal allowed in server.cfg, then check the server console for errors when a player connects.

Is PerformHttpRequest the official way to send webhooks?

Yes — PerformHttpRequest is a documented Cfx.re native used server-side to make outbound HTTP calls, including Discord webhook POSTs. Always send JSON with the Content-Type: application/json header and inspect the statusCode in the callback to detect rate limiting or errors.

Ready to play?

Run your own FiveM server with XGamingServer

Spin up an always-on FiveM server your friends can join in minutes — no port-forwarding, no tech headaches.

99.9%Uptime SLA
< 5 minInstant setup
24/7Human support
DDoSProtected
Instant setup Your server is live in minutes with a one-click control panel.
Mods & plugins Install mods, plugins and workshop content in a few clicks.
DDoS protected Enterprise DDoS mitigation keeps your server online 24/7.
Low-latency hardware Premium CPUs & NVMe SSDs for lag-free multiplayer.
Free backups Automatic backups so your world is never lost.
Real human support Gamers helping gamers — 24/7, no bots, no scripts.

Pick your FiveM plan & play in minutes

See all plans
Starter $8.40/mo 4 GB RAM Renews $12/mo Buy now
Rookie $17.50/mo 8 GB RAM Renews $25/mo Buy now
Pro $24.50/mo 12 GB RAM Renews $35/mo Buy now