Skip to content
Developers
Menu

Differences from Discord

Palloo follows Discord's model closely, so most bots port well. These are the differences that will trip a port up.

On this page

Authentication and setup

Discord Palloo
Authorization: Bot <token> Authorization: Bearer <token>. Bot is refused with 401.
An application with a bot user, created in the Developer Portal A bot created in Settings, Bots of your own account. There is no separate application.
An OAuth2 invite link with the bot scope and a permissions value No invite link. A server manager adds the bot by its ID in Server settings, Add a bot, and picks its permissions there.
Bots are public unless you turn that off Bots are private by default: only the owner can add them. Turn on Public to let others.
Privileged intents, which need approval once a bot is verified Two owner switches: Read message content and Presence intent. No approval step.

REST API

  • The base URL is https://api.palloo.app/v1 (Discord's is https://discord.com/api/v10), and servers are communities: /communities/{id}, community_id. Discord's guild is Palloo's community everywhere.
  • IDs are ULIDs, 26 character strings such as 01J9ZQ3V5K8M2N4P6R8T0W2Y4A, not numeric snowflakes. Like snowflakes they sort by creation time, so compare them as strings.
  • Permission bits have different values. The idea is the same (a 64-bit set as a decimal string, with roles, overwrites and Administrator working as on Discord), but View Channel is 1, Send Messages is 2 and so on. Do not copy Discord's constants; use the permission table.
  • Unknown fields are refused with 400 invalid_body. Payloads with Discord-only fields fail instead of the fields being ignored.
  • Errors are strings. {"error": {"code": "missing_permission", "message": "..."}} instead of numeric codes. See Errors.
  • Rate limits have no X-RateLimit-* headers, no buckets and no global limit flag. A refused request is 429 with Retry-After in whole seconds. See Rate limits.
  • Hidden things answer 404. A server the bot is not in, or a channel it cannot view, looks exactly like one that does not exist.
  • Messages have content and attachments. There are no embeds, components, stickers, reactions, polls or text-to-speech, and no replies to other messages.

Gateway

  • Ops are names, not numbers: hello, identify, ready, heartbeat, heartbeat_ack, dispatch. ready is its own op rather than a dispatch.
  • identify takes only {"token"}. There are no intents bits, no shards and no connection properties.
  • Heartbeats carry no sequence number, and there is no resume. After a reconnect you identify again and catch up over REST from the last_message_id of each channel in ready.
  • The gateway URL is fixed (wss://api.palloo.app/v1/gateway). There is no GET /gateway/bot to call first.
  • Event names are lower case (message_create, member_add, community_create) and payloads use the REST shapes.

See Gateway.

Slash commands and interactions

  • Interactions arrive only over the gateway. There is no interactions endpoint URL for HTTP delivery, and so no request signatures to verify.
  • Answers need both the bot's token and the interaction token: POST /interactions/{id}/{token}/callback.
  • Response types are names: {"type": "message"} answers, {"type": "deferred"} defers. Discord's numeric types 4 and 5 are not accepted.
  • Ephemeral is a boolean, "ephemeral": true, not flags: 64.
  • Complete a deferred answer with PATCH .../response and follow up with POST .../followups, rather than through the webhook endpoints.
  • Registering a command with an existing name replaces it. There is no bulk overwrite.
  • Option types are string, integer, boolean, user, channel and role. There are no subcommands, number, mentionable or attachment options, no autocomplete, no choices, and no buttons, select menus, modals or context menu commands.
  • "The bot is thinking" and failures are shown only to the person who used the command.
  • An answer everyone can see needs Send Messages for the bot in that channel, which is stricter than Discord.

See Slash commands and interactions.

Webhooks

  • Posting answers 204 with no body. There is no ?wait=true to get the message back, and no thread_id.
  • Only content and username (plus files and their attachments descriptions). No embeds, avatar_url, tts or allowed_mentions; @everyone and @here never ping from a webhook.
  • Besides the token in the URL, you can send it as Authorization: Webhook <token> and keep it out of URLs.
  • File uploads use the same payload_json and files[n] multipart format as Discord.

See Incoming webhooks.

Bots as members

  • A bot cannot accept invites or create servers. It joins only when someone adds it.
  • Two bots can never DM each other. A bot and a person who share a server can, under the person's privacy settings.
  • Deleting a bot keeps its messages, shown as from "Deleted bot".