22 KiB
GuardDen
GuardDen is a comprehensive Discord moderation bot designed to protect your community while maintaining a warm, welcoming environment. Built with privacy and self-hosting in mind, GuardDen combines AI-powered content filtering with traditional moderation tools to create a safe space for your members.
Features
Core Moderation
- Warn, Kick, Ban, Timeout - Standard moderation commands with logging
- Strike System - Configurable point-based system with automatic escalation
- Moderation History - Track all actions taken against users
- Bulk Message Deletion - Purge up to 100 messages at once
Automod
- Banned Words Filter - Block words/phrases with regex support
- Scam Detection - Automatic detection of phishing/scam links
- Anti-Spam - Rate limiting, duplicate detection, mass mention protection
- Link Filtering - Block Discord invites and suspicious URLs
AI Moderation
- Text Analysis - AI-powered content moderation using Claude or GPT
- NSFW Image Detection - Automatic flagging of inappropriate images
- NSFW-Only Filtering - Enabled by default - only filters sexual content, allows violence/harassment
- Phishing Analysis - AI-enhanced detection of scam URLs
- Configurable Sensitivity - Adjust strictness per server (0-100)
- Public In-Channel Warnings - Optional: sends temporary public channel messages when users have DMs disabled
Verification System
- Multiple Challenge Types - Button, captcha, math problems, emoji selection
- Automatic New Member Verification - Challenge users on join
- Configurable Verified Role - Auto-assign role on successful verification
- Rate Limited - Prevents verification spam
Logging
- Member joins/leaves
- Message edits and deletions
- Voice channel activity
- Ban/unban events
- All moderation actions
Quick Start
Prerequisites
- Python 3.11+
- PostgreSQL 15+
- Discord Bot Token (see setup below)
- (Optional) Anthropic or OpenAI API key for AI features
Discord Bot Setup
-
Go to the Discord Developer Portal
-
Click New Application and give it a name (e.g., "GuardDen")
-
Go to the Bot tab and click Add Bot
-
Configure Bot Settings:
- Disable Public Bot if you only want yourself to add it
- Copy the Token (click "Reset Token") - this is your
GUARDDEN_DISCORD_TOKEN
-
Enable Privileged Gateway Intents (all three required):
- Presence Intent - for user status tracking
- Server Members Intent - for member join/leave events, verification
- Message Content Intent - for reading messages (automod, AI moderation)
-
Generate Invite URL - Go to OAuth2 > URL Generator:
Scopes:
botapplications.commands
Bot Permissions:
- Manage Roles
- Kick Members
- Ban Members
- Moderate Members (timeout)
- Manage Channels
- View Channels
- Send Messages
- Manage Messages
- Embed Links
- Attach Files
- Read Message History
- Add Reactions
Or use permission integer:
1239943348294 -
Use the generated URL to invite the bot to your server
Docker Deployment (Recommended)
-
Clone the repository:
git clone https://git.hiddenden.cafe/Hiddenden/GuardDen.git cd guardden -
Create your environment file:
cp .env.example .env # Edit .env and add your Discord token -
Start with Docker Compose:
docker compose up -d
Local Development
-
Create a virtual environment:
python -m venv venv source venv/bin/activate # On Windows: venv\Scripts\activate -
Install dependencies:
pip install -e ".[dev,ai]" -
Set up environment variables:
cp .env.example .env # Edit .env with your configuration -
Start PostgreSQL (or use Docker):
docker compose up db -d -
Run the bot:
python -m guardden
Configuration
GuardDen now supports file-based configuration as the primary method for managing bot settings. This replaces Discord commands for configuration, providing better version control, easier management, and more reliable deployments.
File-Based Configuration (Recommended)
Directory Structure
config/
├── guilds/
│ ├── guild-123456789.yml # Per-server configuration
│ ├── guild-987654321.yml
│ └── default-template.yml # Template for new servers
├── wordlists/
│ ├── banned-words.yml # Custom banned words
│ ├── domain-allowlists.yml # Allowed domains whitelist
│ └── external-sources.yml # Managed wordlist sources
├── schemas/
│ ├── guild-schema.yml # Configuration validation
│ └── wordlists-schema.yml
└── templates/
└── guild-default.yml # Default configuration template
Quick Start with File Configuration
-
Create your first server configuration:
python -m guardden.cli.config guild create 123456789012345678 "My Discord Server" -
Edit the configuration file:
nano config/guilds/guild-123456789012345678.yml -
Customize settings (example):
# Basic server information guild_id: 123456789012345678 name: "My Discord Server" settings: # AI Moderation ai_moderation: enabled: true sensitivity: 80 # 0-100 (higher = stricter) nsfw_only_filtering: true # Only block sexual content, allow violence # Automod settings automod: message_rate_limit: 5 # Max messages per 5 seconds scam_allowlist: - "discord.com" - "github.com" -
Validate your configuration:
python -m guardden.cli.config guild validate 123456789012345678 -
Start the bot (configurations auto-reload):
python -m guardden
Configuration Management CLI
Guild Management:
# List all configured servers
python -m guardden.cli.config guild list
# Create new server configuration
python -m guardden.cli.config guild create <guild_id> "Server Name"
# Edit specific settings
python -m guardden.cli.config guild edit <guild_id> ai_moderation.sensitivity 75
python -m guardden.cli.config guild edit <guild_id> ai_moderation.nsfw_only_filtering true
# Validate configurations
python -m guardden.cli.config guild validate
python -m guardden.cli.config guild validate <guild_id>
# Backup configuration
python -m guardden.cli.config guild backup <guild_id>
Migration from Discord Commands:
# Export existing Discord command settings to files
python -m guardden.cli.config migrate from-database
# Verify migration was successful
python -m guardden.cli.config migrate verify
Wordlist Management:
# View wordlist status
python -m guardden.cli.config wordlist info
# View available templates
python -m guardden.cli.config template info
Key Configuration Options
AI Moderation Settings:
ai_moderation:
enabled: true # Enable AI content analysis
sensitivity: 80 # 0-100 scale (higher = stricter)
confidence_threshold: 0.7 # 0.0-1.0 confidence required
nsfw_only_filtering: true # true = only sexual content (DEFAULT), false = all content
log_only: false # true = log only, false = take action
notifications:
send_in_channel_warnings: false # Send temporary PUBLIC channel messages when DMs fail (DEFAULT: false)
NSFW-Only Filtering Guide (Default: Enabled):
true= Only block sexual/nude content, allow violence and other content types (DEFAULT)false= Block ALL inappropriate content (sexual, violence, harassment, hate speech)
Public In-Channel Warnings (Default: Disabled):
- IMPORTANT: These messages are PUBLIC and visible to everyone in the channel, NOT private
- When enabled and a user has DMs disabled, sends a temporary public message in the channel
- Messages auto-delete after 10 seconds to minimize clutter
- Privacy Warning: The user's violation and reason will be visible to all users for 10 seconds
- Set to
trueonly if you prefer public transparency over privacy
Automod Configuration:
automod:
message_rate_limit: 5 # Max messages per time window
message_rate_window: 5 # Time window in seconds
duplicate_threshold: 3 # Duplicate messages to trigger
scam_allowlist: # Domains that bypass scam detection
- "discord.com"
- "github.com"
Banned Words Management:
Edit config/wordlists/banned-words.yml:
global_patterns:
- pattern: "badword"
action: delete
is_regex: false
category: profanity
guild_patterns:
123456789: # Specific server overrides
- pattern: "server-specific-rule"
action: warn
override_global: false
Hot-Reloading
Configuration changes are automatically detected and applied without restarting the bot:
- ✅ Edit YAML files directly
- ✅ Changes apply within seconds
- ✅ Invalid configs are rejected with error logs
- ✅ Automatic rollback on errors
Environment Variables
| Variable | Description | Default |
|---|---|---|
GUARDDEN_DISCORD_TOKEN |
Your Discord bot token | Required |
GUARDDEN_DISCORD_PREFIX |
Default command prefix | ! |
GUARDDEN_ALLOWED_GUILDS |
Comma-separated guild allowlist | (empty = all) |
GUARDDEN_OWNER_IDS |
Comma-separated owner user IDs | (empty = admins) |
GUARDDEN_DATABASE_URL |
PostgreSQL connection URL | postgresql://guardden:guardden@localhost:5432/guardden |
GUARDDEN_LOG_LEVEL |
Logging level | INFO |
GUARDDEN_AI_PROVIDER |
AI provider (anthropic/openai/none) | none |
GUARDDEN_ANTHROPIC_API_KEY |
Anthropic API key (if using Claude) | - |
GUARDDEN_OPENAI_API_KEY |
OpenAI API key (if using GPT) | - |
GUARDDEN_WORDLIST_ENABLED |
Enable managed wordlist sync | true |
GUARDDEN_WORDLIST_UPDATE_HOURS |
Managed wordlist sync interval | 168 |
GUARDDEN_WORDLIST_SOURCES |
JSON array of wordlist sources | (empty = defaults) |
Per-Guild Settings
Each server can be configured via YAML files in config/guilds/:
General Settings:
- Command prefix and locale
- Channel IDs (log, moderation, welcome)
- Role IDs (mute, verified, moderator)
Content Moderation:
- AI moderation (enabled, sensitivity, NSFW-only mode)
- Automod thresholds and rate limits
- Banned words and domain allowlists
- Strike system and escalation actions
Member Verification:
- Verification challenges (button, captcha, math, emoji)
- Auto-role assignment
All settings support hot-reloading - edit files and changes apply immediately!
Commands
Note: Configuration commands (
!config,!ai,!automod, etc.) have been replaced with file-based configuration. See the Configuration section above for managing settings via YAML files and the CLI tool.
Moderation
| Command | Permission | Description |
|---|---|---|
!warn <user> [reason] |
Kick Members | Warn a user |
!strike <user> [points] [reason] |
Kick Members | Add strikes to a user |
!strikes <user> |
Kick Members | View user's strikes |
!timeout <user> <duration> [reason] |
Moderate Members | Timeout a user (e.g., 1h, 30m, 7d) |
!untimeout <user> |
Moderate Members | Remove timeout |
!kick <user> [reason] |
Kick Members | Kick a user |
!ban <user> [reason] |
Ban Members | Ban a user |
!unban <user_id> [reason] |
Ban Members | Unban a user by ID |
!purge <amount> |
Manage Messages | Delete multiple messages (max 100) |
!modlogs <user> |
Kick Members | View moderation history |
Configuration Management
Configuration is now managed via YAML files instead of Discord commands. Use the CLI tool:
# Configuration Management CLI
python -m guardden.cli.config guild create <guild_id> "Server Name"
python -m guardden.cli.config guild list
python -m guardden.cli.config guild edit <guild_id> <setting> <value>
python -m guardden.cli.config guild validate [guild_id]
# Migration from old Discord commands
python -m guardden.cli.config migrate from-database
python -m guardden.cli.config migrate verify
# Wordlist management
python -m guardden.cli.config wordlist info
Read-only Status Commands (Still Available):
| Command | Description |
|---|---|
!config |
View current configuration (read-only) |
!ai |
View AI moderation settings (read-only) |
!automod |
View automod status (read-only) |
!bannedwords |
List banned words (read-only) |
Configuration Examples:
# Set AI sensitivity to 75 (0-100 scale)
python -m guardden.cli.config guild edit 123456789 ai_moderation.sensitivity 75
# Enable NSFW-only filtering (only block sexual content)
python -m guardden.cli.config guild edit 123456789 ai_moderation.nsfw_only_filtering true
# Add domain to scam allowlist
Edit config/wordlists/domain-allowlists.yml
# Add banned word pattern
Edit config/wordlists/banned-words.yml
Whitelist Management (Admin only)
| Command | Description |
|---|---|
!whitelist |
View all whitelisted users |
!whitelist add @user |
Add a user to the whitelist (bypasses all moderation) |
!whitelist remove @user |
Remove a user from the whitelist |
!whitelist clear |
Clear the entire whitelist |
What is the whitelist?
- Whitelisted users bypass ALL moderation checks (automod and AI moderation)
- Useful for trusted members, bots, or staff who need to post content that might trigger filters
- Users with "Manage Messages" permission are already exempt from moderation
Diagnostics (Admin only)
| Command | Description |
|---|---|
!health |
Check database and AI provider status |
Verification (Admin only)
| Command | Description |
|---|---|
!verify |
Request verification (for users) |
!verify setup |
View verification setup status |
!verify enable |
Enable verification for new members |
!verify disable |
Disable verification |
!verify role @role |
Set the verified role |
!verify type <type> |
Set verification type (button/captcha/math/emoji) |
!verify test [type] |
Test a verification challenge |
!verify reset @user |
Reset verification for a user |
CI (Gitea Actions)
Workflows live under .gitea/workflows/ and mirror the previous GitHub Actions
pipeline for linting, tests, and Docker builds.
Project Structure
guardden/
├── src/guardden/
│ ├── bot.py # Main bot class
│ ├── config.py # Settings management
│ ├── cogs/ # Discord command groups
│ │ ├── admin.py # Configuration commands (read-only)
│ │ ├── ai_moderation.py # AI-powered moderation
│ │ ├── automod.py # Automatic moderation
│ │ ├── events.py # Event logging
│ │ ├── moderation.py # Moderation commands
│ │ └── verification.py # Member verification
│ ├── models/ # Database models
│ │ ├── guild.py # Guild settings, banned words
│ │ └── moderation.py # Logs, strikes, notes
│ ├── services/ # Business logic
│ │ ├── ai/ # AI provider implementations
│ │ ├── automod.py # Content filtering
│ │ ├── database.py # DB connections
│ │ ├── guild_config.py # Config caching
│ │ ├── file_config.py # File-based configuration system
│ │ ├── config_migration.py # Migration from DB to files
│ │ ├── ratelimit.py # Rate limiting
│ │ └── verification.py # Verification challenges
│ └── cli/ # Command-line tools
│ └── config.py # Configuration management CLI
├── config/ # File-based configuration
│ ├── guilds/ # Per-server configuration files
│ ├── wordlists/ # Banned words and allowlists
│ ├── schemas/ # Configuration validation schemas
│ └── templates/ # Configuration templates
├── tests/ # Test suite
├── migrations/ # Database migrations
├── docker-compose.yml # Docker deployment
├── pyproject.toml # Dependencies
├── README.md # This file
└── MIGRATION.md # Migration guide for file-based config
Verification System
GuardDen includes a verification system to protect your server from bots and raids.
Challenge Types
| Type | Description |
|---|---|
button |
Simple button click (default, easiest) |
captcha |
Text-based captcha code entry |
math |
Solve a simple math problem |
emoji |
Select the correct emoji from options |
Setup
- Create a verified role in your server
- Configure the role permissions (verified members get full access)
- Set up verification:
!verify role @Verified !verify type captcha !verify enable
How It Works
- New member joins the server
- Bot sends verification challenge via DM (or channel if DMs disabled)
- Member completes the challenge
- Bot assigns the verified role
- Member gains access to the server
AI Moderation
GuardDen supports AI-powered content moderation using either Anthropic's Claude or OpenAI's GPT models.
Setup
-
Set the AI provider in your environment:
GUARDDEN_AI_PROVIDER=anthropic # or "openai" GUARDDEN_ANTHROPIC_API_KEY=sk-ant-... # if using Claude GUARDDEN_OPENAI_API_KEY=sk-... # if using OpenAI -
Enable AI moderation per server:
!ai enable !ai sensitivity 50 # 0=lenient, 100=strict !ai nsfw true # Enable NSFW image detection
Content Categories
The AI analyzes content for:
- Harassment - Personal attacks, bullying
- Hate Speech - Discrimination, slurs
- Sexual Content - Explicit material
- Violence - Threats, graphic content
- Self-Harm - Suicide/self-injury content
- Scams - Phishing, fraud attempts
- Spam - Promotional, low-quality content
How It Works
- Messages are analyzed by the AI provider
- Results include confidence scores and severity ratings
- Actions are taken based on guild sensitivity settings
- All AI actions are logged to the mod log channel
NSFW-Only Filtering Mode (Enabled by Default)
Default Behavior: GuardDen is configured to only filter sexual/NSFW content by default. This allows communities to have mature discussions about violence, politics, and controversial topics while still maintaining a "safe for work" environment.
When enabled (DEFAULT):
- ✅ Blocked: Sexual content, nude images, explicit material
- ❌ Allowed: Violence, harassment, hate speech, self-harm content
When disabled (strict mode):
- ✅ Blocked: All inappropriate content categories
To change to strict mode:
# Edit config/guilds/guild-<id>.yml
ai_moderation:
nsfw_only_filtering: false
This default is useful for:
- Gaming communities (violence in gaming discussions)
- Mature discussion servers (politics, news)
- Communities with specific content policies that allow violence but prohibit sexual material
Public In-Channel Warnings (Disabled by Default)
IMPORTANT PRIVACY NOTICE: In-channel warnings are PUBLIC and visible to all users in the channel, NOT private messages. This is a Discord API limitation.
When enabled and users have DMs disabled, moderation warnings are sent as temporary public messages in the channel where the violation occurred.
How it works:
- Bot tries to DM the user about the violation
- If DM fails (user has DMs disabled):
- If
send_in_channel_warnings: true: Sends a PUBLIC temporary message in the channel mentioning the user - If
send_in_channel_warnings: false(DEFAULT): Silent failure, no notification sent - Message includes violation reason and any timeout information
- Message auto-deletes after 10 seconds
- If
- If DM succeeds, no channel message is sent
To enable in-channel warnings:
# Edit config/guilds/guild-<id>.yml
notifications:
send_in_channel_warnings: true
Considerations:
Pros:
- Users are always notified of moderation actions, even with DMs disabled
- Public transparency about what content is not allowed
- Educational for other members
Cons:
- NOT PRIVATE - Violation details visible to all users for 10 seconds
- May embarrass users publicly
- Could expose sensitive moderation information
- Privacy-conscious communities may prefer silent failures
Development
Running Tests
pytest
pytest -v # Verbose output
pytest tests/test_automod.py # Specific file
pytest -k "test_scam" # Filter by name
Code Quality
ruff check src tests # Linting
ruff format src tests # Formatting
mypy src # Type checking
License
MIT License - see LICENSE file for details.
Support
- Issues: Report bugs at https://github.com/anthropics/claude-code/issues
- Documentation: See
docs/directory - Configuration Help: Check
CLAUDE.mdfor developer guidance
Roadmap
- AI-powered content moderation (Claude/OpenAI integration)
- NSFW image detection
- NSFW-only filtering mode (default)
- Optional public in-channel warnings when DMs disabled
- Verification/captcha system
- Rate limiting
- Voice channel moderation
- Slash commands with true ephemeral messages
- Custom notification templates
- Advanced analytics dashboard