Skip to main content
The most common causes are missing intents or undeployed slash commands.Check privileged intents: In the Discord Developer Portal, go to BotPrivileged Gateway Intents and confirm these are all enabled:
  • Message Content Intent
  • Server Members Intent
  • Guild Voice States Intent
  • Guild Message Reactions Intent
Without Message Content Intent, the bot cannot read message text and will not respond to AI mentions.Deploy slash commands: If commands don’t appear in Discord, run:
pnpm deploy
For instant availability during development, use a guild-scoped deploy:
pnpm deploy -- --guild-id YOUR_GUILD_ID
Global commands can take up to one hour to propagate. Guild-scoped commands are available immediately.Check that the bot is running: Look for a successful login line in the bot logs:
Logged in as Volvox.Bot#0000
If you see connection errors instead, check your DISCORD_TOKEN value.
If the bot fails to start with a database error, check your DATABASE_URL format:
DATABASE_URL=postgresql://username:password@hostname:5432/database_name
Common mistakes:
  • Using postgres:// instead of postgresql:// (both work, but verify your driver accepts it)
  • Wrong port — PostgreSQL defaults to 5432
  • Database not yet created — connect with psql and run CREATE DATABASE volvoxbot;
  • SSL mismatch — set DATABASE_SSL=false if your PostgreSQL server doesn’t have TLS configured
Test your connection manually:
psql "$DATABASE_URL"
For Docker Compose: DATABASE_URL is automatically set to point at the internal db service. If you’re seeing connection errors in Docker, check that the db container is healthy:
docker compose ps db
Redis is optional. If REDIS_URL is not set, the bot logs:
Redis not configured (REDIS_URL not set) — caching disabled
This is normal. The bot operates without Redis.If REDIS_URL is set but Redis is unreachable, you’ll see repeated connection error logs. The bot retries up to 10 times before giving up. Check:
  • Is Redis running? Run redis-cli ping — it should respond with PONG.
  • Is the URL correct? Format: redis://host:6379 or redis://:password@host:6379
  • Firewall rules — make sure port 6379 is accessible from the bot
In Docker Compose, REDIS_URL is automatically set to redis://redis:6379. If Redis is unhealthy, the bot service won’t start because of the condition: service_healthy dependency.
If the bot joins a server but can’t perform actions (e.g. can’t send messages, assign roles, or delete messages), check its role permissions in Server SettingsRoles.The bot needs at minimum:
  • View Channels — to see channels and read events
  • Send Messages — to respond to commands and AI mentions
  • Read Message History — to fetch context for AI conversations
  • Manage Messages — to delete messages (purge, auto-moderation)
  • Add Reactions — for AI feedback thumbs and reaction roles
  • Manage Roles — to assign and remove roles (reaction roles, temp roles)
For moderation commands (kick, ban, timeout), the bot also needs Kick Members, Ban Members, and Moderate Members.
The bot’s role must be positioned above any roles it needs to manage in the role hierarchy. Discord prevents a bot from assigning or removing roles that are higher than its own.
AI features require a valid Anthropic API key. If the bot isn’t responding to AI mentions or moderation isn’t running:
  1. Verify ANTHROPIC_API_KEY is set correctly in .env.
  2. Check the bot logs for Anthropic API errors — look for 401 Unauthorized or 429 Too Many Requests.
  3. Confirm the channel is not in the AI channel blocklist (config.ai.blocklist) and quiet mode is not active.
  4. Verify the bot has the Message Content Intent enabled — without it, the bot can’t read message text.
If you’re using an OAuth access token instead of a standard API key, use CLAUDE_CODE_OAUTH_TOKEN and leave ANTHROPIC_API_KEY blank. Setting both causes conflicting authentication headers and the API will reject the request.
If slash commands don’t appear after running pnpm deploy:
  1. Wait — global command registration takes up to one hour. Run a guild-scoped deploy for immediate availability:
    pnpm deploy -- --guild-id YOUR_GUILD_ID
    
  2. Check DISCORD_CLIENT_ID — the deploy script needs this to be the correct application ID. Verify it matches the Application ID shown on your app’s General Information page.
  3. Restart Discord — sometimes the client caches the command list. Fully quit and reopen Discord or use a browser.
  4. Check scopes — the bot must have been invited with the applications.commands scope. Re-invite using the OAuth2 URL Generator if needed.
If you can’t log in to the web dashboard via Discord OAuth2, check these settings:NEXTAUTH_URL must match the exact URL you’re accessing the dashboard from (including protocol and port):
NEXTAUTH_URL=http://localhost:3000
Mismatches between this value and the actual URL cause NextAuth to reject the session.NEXTAUTH_SECRET must be set. Generate one with:
openssl rand -base64 32
Discord OAuth2 redirect URI — in the Discord Developer Portal, go to OAuth2Redirects and add:
http://localhost:3001/api/v1/auth/discord/callback
This must exactly match DISCORD_REDIRECT_URI in your .env. Any mismatch causes Discord to reject the OAuth2 flow.DISCORD_CLIENT_SECRET — make sure this is the client secret, not the bot token. You can regenerate it on the OAuth2General page.
If the bot process is consuming more memory than expected:
  • Enable Redis — without Redis, the bot caches config and Discord API responses in memory. Setting REDIS_URL moves that caching to Redis and significantly reduces the Node.js heap size.
  • Check the performance monitor — the bot includes a built-in performance monitor. Look at the logs for memory and CPU metrics, or check the dashboard Performance section.
  • Check conversation history — long-running channels accumulate conversation history. The bot trims history automatically, but very active channels may hold more context than others.
  • Check for slow queries — the bot logs queries slower than PG_SLOW_QUERY_MS (default 100 ms). Frequent slow queries can cause connection pool saturation and indirect memory growth.
Run docker stats (Docker) or check your process manager’s memory view to see actual RSS and heap usage over time.
The migration runner tracks applied migrations in the pgmigrations table. If a migration fails mid-run:
  1. Check the error output — it usually identifies the failing SQL statement.
  2. Fix the underlying issue (e.g. insufficient database permissions or missing extension).
  3. Run pnpm migrate again — already-applied migrations are skipped.
pg_trgm extension not found — migration 004_performance_indexes installs the pg_trgm extension. If your PostgreSQL user doesn’t have superuser privileges, this will fail. Connect as a superuser and run:
CREATE EXTENSION IF NOT EXISTS pg_trgm;
pgcrypto extension not found — same issue as above for migration 006_command_usage. Run:
CREATE EXTENSION IF NOT EXISTS pgcrypto;

Build docs developers (and LLMs) love