- Architecture Overview
- AI System
- Memory Management
- Admin Tools
- Search Functionality
- Database Structure
- API Integration
- Best Practices
Nebula follows a modular architecture using Discord.py's cog system:
Bot Core (bot.py)
├── Memory Manager Cog
├── AI Handler Cog
├── Admin Tools Cog
└── Search Tool Cog
↓
Database Layer (database.py)
↓
SQLite Database (nebula.db)
- bot.py: Main entry point, loads cogs, handles Discord connection
- database.py: Database abstraction layer for all data operations
- ai_handler.py: Processes messages, calls OpenAI API, manages tool execution
- memory_manager.py: Handles conversation memory and token tracking
- admin_tools.py: Implements moderation commands
- search_tool.py: Google Custom Search integration
- Message Received → Bot checks if it's mentioned
- Context Gathering → Retrieves reply context if applicable
- Memory Retrieval → Loads recent conversation history
- AI Processing → Sends to OpenAI with available tools
- Tool Execution → Executes any requested tool calls
- Response Generation → Formats and sends response
- Memory Storage → Saves conversation to database
The system prompt (system.txt) defines Nebula's personality and capabilities. Key elements:
- Identity: Friendly AI admin bot
- Behavior: Personal, addressing users by name
- Capabilities: Lists available tools and features
- Guidelines: Rules for tool usage and interaction
Tools are defined in OpenAI's function calling format:
{
"type": "function",
"function": {
"name": "tool_name",
"description": "What the tool does",
"parameters": { ... }
}
}Available tools are dynamically determined based on user permissions.
- Maximum context: Limited by OpenAI model's context window
- History retrieval: Last 50 messages by default
- Token counting: Uses tiktoken for accurate GPT-4 token counts
- Automatic truncation: Older messages dropped when limit reached
# Token counting
def count_tokens(text: str) -> int:
encoding = tiktoken.encoding_for_model("gpt-4")
return len(encoding.encode(text))- Message Arrives → Count tokens
- Check Limit → Compare with 400k token limit
- Reset if Needed → Clear history if limit exceeded
- Store Message → Save to database with token count
- Update Profile → Update user statistics
!memory_stats: View current token usage!reset_memory: Clear conversation history (admin only)
When total tokens exceed 400,000:
- Entire conversation history is cleared for the channel
- Fresh start with next message
- User profiles and admin logs are preserved
@Nebula kick @username reason here
Process:
- Verify admin permissions
- Parse user mention/ID
- Check bot's role hierarchy
- Execute kick
- Log action to database
- Confirm to admin
@Nebula ban @username reason here
Process:
- Verify admin permissions
- Parse user mention/ID
- Check bot's role hierarchy
- Execute ban
- Log action to database
- Confirm to admin
Note: Bot cannot kick/ban users with roles equal to or higher than its own role.
@Nebula create a text channel called "new-channel" in "Category Name"
Supported Types:
- Text channels
- Voice channels
Process:
- Verify admin permissions
- Find category (if specified)
- Create channel
- Log action
- Return channel mention
@Nebula check activity for @username
Returns:
- User ID
- First seen date
- Last seen date
- Total message count
- Messages in last 7 days
Data Source: Tracked from conversation history and user profiles
All administrative actions are logged with:
- Timestamp
- Admin who performed action
- Action type
- Target user
- Reason/details
View logs with: !admin_logs [limit]
Requires two API credentials:
- Google Search API Key
- Custom Search Engine ID
@Nebula search for "query here"
@Nebula can you search "latest news"
Search Process:
- User explicitly requests search
- AI decides to use search tool
- Query sent to Google Custom Search API
- Results formatted (title, snippet, URL)
- Response sent to user
Features:
- Up to 10 results per search
- Rich snippets included
- Direct links provided
- Available to all users (not just admins)
- Missing API credentials → Graceful error message
- No results → "No results found" message
- API errors → Error message with details
Stores all conversation messages.
CREATE TABLE conversation_history (
id INTEGER PRIMARY KEY,
guild_id TEXT,
channel_id TEXT,
user_id TEXT,
display_name TEXT,
role TEXT, -- 'user' or 'assistant'
content TEXT,
timestamp DATETIME,
token_count INTEGER
)Tracks user information and statistics.
CREATE TABLE user_profiles (
user_id TEXT PRIMARY KEY,
display_name TEXT,
guild_id TEXT,
first_seen DATETIME,
last_seen DATETIME,
message_count INTEGER
)Stores server-specific configuration (for future features).
CREATE TABLE server_settings (
guild_id TEXT PRIMARY KEY,
settings JSON,
created_at DATETIME,
updated_at DATETIME
)Logs all administrative actions.
CREATE TABLE admin_actions_log (
id INTEGER PRIMARY KEY,
guild_id TEXT,
admin_id TEXT,
admin_name TEXT,
action_type TEXT,
target_id TEXT,
target_name TEXT,
details TEXT,
timestamp DATETIME
)db.add_message(guild_id, channel_id, user_id,
display_name, role, content, token_count)history = db.get_conversation_history(guild_id, channel_id, limit=50)activity = db.get_user_activity(user_id, guild_id)db.log_admin_action(guild_id, admin_id, admin_name,
action_type, target_id, target_name, details)openai.api_key = os.getenv('OPENAI_API_KEY')
openai.base_url = os.getenv('OPENAI_BASE_URL') # Optionalresponse = await openai.ChatCompletion.acreate(
model="gpt-4-turbo-preview",
messages=messages,
tools=tools,
tool_choice="auto",
temperature=0.7,
max_tokens=2000
)- Text response:
response.choices[0].message.content - Tool calls:
response.choices[0].message.tool_calls
api_key = os.getenv('GOOGLE_SEARCH_API_KEY')
search_engine_id = os.getenv('GOOGLE_SEARCH_ENGINE_ID')url = "https://www.googleapis.com/customsearch/v1"
params = {
'key': api_key,
'cx': search_engine_id,
'q': query,
'num': 5
}- Never commit API keys to version control
- Use .env files for sensitive configuration
- Validate user permissions before admin actions
- Check role hierarchy before moderation
- Log all admin actions for audit trails
- Limit conversation history to recent messages
- Monitor token usage to prevent API overages
- Use async/await for all I/O operations
- Batch database operations when possible
- Cache frequently accessed data (if needed)
- Always address users by name for personalization
- Provide clear error messages when things fail
- Split long messages to respect Discord limits
- Show typing indicator for long operations
- Confirm admin actions with clear feedback
- Regularly backup the SQLite database
- Monitor API usage and costs
- Check admin logs periodically
- Update dependencies for security patches
- Review conversation memory token usage
- Wrap API calls in try-catch blocks
- Provide fallbacks for missing credentials
- Log errors for debugging
- Gracefully degrade when features unavailable
- Inform users of temporary issues
To use OpenAI-compatible APIs (like Azure OpenAI, local models, etc.):
OPENAI_BASE_URL=https://your-custom-endpoint.com/v1In memory_manager.py:
self.max_tokens = 400000 # Adjust as neededEdit system.txt to change:
- Personality traits
- Response style
- Tool usage guidelines
- Conversation patterns
- Define tool in
ai_handler.py - Implement execution logic
- Add to appropriate cog
- Update documentation
- Check bot is online
- Verify Message Content Intent enabled
- Ensure bot has proper channel permissions
- Check console for error messages
- Run
!memory_statsto check usage - Reset if needed with
!reset_memory - Verify database file is writable
- Check disk space
- Verify API keys are correct
- Check OpenAI account has credits
- Monitor rate limits
- Check network connectivity
- Ensure database file exists
- Check file permissions
- Verify SQLite is installed
- Try backing up and recreating database
Potential features for future versions:
- Custom command prefix per server
- Role-based permissions (not just admin)
- Scheduled tasks/reminders
- Advanced search filters
- Multi-language support
- Custom tool creation interface
- Web dashboard for configuration
- Backup/restore functionality
- Enhanced analytics and reporting
- Integration with other APIs
For more information, see README.md or open an issue on the project repository.