Skip to content

Conversation

@SorynTech
Copy link
Owner

@SorynTech SorynTech commented Jan 9, 2026

In this Pull request I (@SorynTech) have updated the Database functions within Moderationbot.py

Summary by CodeRabbit

  • New Features
    • Added comprehensive moderation tracking commands: warn, warnings, clearwarnings, case, cases, updatecase, modnote, and modnotes for enhanced server management.
    • Implemented automatic username logging for all moderation actions, improving audit trails and accountability.
    • Added ability to retrieve and manage moderation notes and historical warning data.

✏️ Tip: You can customize this high-level summary in your review settings.

Signed-off-by: Soryn Tech <zippydrawzstudioz@gmail.com>
@coderabbitai
Copy link
Contributor

coderabbitai bot commented Jan 9, 2026

📝 Walkthrough

Walkthrough

The pull request adds username logging fields to moderation database tables and extends the moderation bot with new database-backed commands for creating cases, warnings, and notes. New query and management functions retrieve, clear, and delete moderation records, with enhanced user and moderator name propagation throughout the system.

Changes

Cohort / File(s) Summary
Database Schema Updates
Moderationbot.py
Added user_name and moderator_name columns to moderation tables (moderation_cases, moderation_warnings, moderation_notes); updated table creation logic to accommodate new fields.
Core Moderation Functions
Moderationbot.py
Extended create_mod_case, add_warning, and add_mod_note functions to accept optional user_name and moderator_name parameters; enhanced insertion logic and error handling.
Moderation Query & Management Functions
Moderationbot.py
Added get_user_warnings, clear_user_warnings, get_user_mod_notes, delete_mod_note functions for retrieving, clearing, and removing moderation records; introduced close_database for graceful connection closure.
Moderation Command Handlers
Moderationbot.py
Introduced new slash commands (warn, warnings, clearwarnings, case, cases, updatecase, modnote, modnotes) with database-backed logging and ephemeral embed responses; updated existing command handlers to utilize stored names with fallback retrieval.

Sequence Diagram(s)

sequenceDiagram
    participant User
    participant Bot as Moderationbot
    participant DB as Database
    
    User->>Bot: Trigger moderation command<br/>(e.g., /warn user reason)
    activate Bot
    Bot->>DB: Insert moderation record<br/>(user_id, moderator_id, names)
    activate DB
    DB-->>Bot: Return record ID/status
    deactivate DB
    Bot->>DB: Query related records<br/>(for display context)
    activate DB
    DB-->>Bot: Return moderation history
    deactivate DB
    Bot-->>User: Send ephemeral embed response<br/>(with case details & history)
    deactivate Bot
Loading

Estimated code review effort

🎯 4 (Complex) | ⏱️ ~45 minutes

Possibly related PRs

Poem

🐰 A rabbit hops through warnings cleared,
With names and cases newly tracked,
Each mod note stored, no more feared—
The database has mod's back!
Commands bloom like garden rows.

🚥 Pre-merge checks | ✅ 2 | ❌ 1
❌ Failed checks (1 warning)
Check name Status Explanation Resolution
Title check ⚠️ Warning The PR title '@coderabbitai Generate me a PR title' is not an actual title but a command/placeholder requesting title generation, making it unsuitable as a meaningful PR title. Replace with a descriptive title that summarizes the main changes, such as 'Add comprehensive moderation logging and tracking commands' or 'Extend moderation database functions with username logging'.
✅ Passed checks (2 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Docstring Coverage ✅ Passed Docstring coverage is 100.00% which is sufficient. The required threshold is 80.00%.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing touches
  • 📝 Generate docstrings

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

Copy link
Contributor

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 0

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (6)
Moderationbot.py (6)

316-322: Potential NameError if get_db_connection() fails.

If get_db_connection() raises an exception before conn is assigned, the except block will fail with NameError: name 'conn' is not defined when accessing conn.rollback().

🐛 Proposed fix
+    conn = None
     try:
         print(f"💾 [DATABASE] Creating moderation case...")
         # ... rest of try block
         conn = get_db_connection()
         # ...
     except Exception as e:
         print(f"❌ [DATABASE] Error creating mod case: {type(e).__name__}")
         print(f"   💥 Details: {e}")
-        if conn:
+        if conn is not None:
             conn.rollback()
             return_db_connection(conn)
         return None

444-450: Same NameError risk as create_mod_case.

The conn variable may be undefined if an exception occurs before it's assigned.

🐛 Proposed fix
 def add_warning(guild_id: int, user_id: int, moderator_id: int, reason: str,
                 user_name: str = None, moderator_name: str = None) -> Optional[int]:
     """Add a warning to a user"""
     if db_pool is None:
         print("⚠️  Database pool not initialized - skipping warning creation")
         return None

+    conn = None
     try:
         # ... existing code ...

513-519: Consistent pattern of potential NameError across database functions.

The same conn undefined issue exists in clear_user_warnings, add_mod_note, and delete_mod_note. Initialize conn = None before the try block in all these functions.


675-692: Duplicate close_database function definition.

close_database() is defined twice: once at lines 632-650 and again at lines 675-692. The second definition shadows the first. Remove one of the duplicates.

🐛 Proposed fix

Remove the duplicate definition at lines 675-692:

-def close_database():
-    """
-    Close all database connections and clean up the connection pool.
-    Called when the bot shuts down.
-    """
-    global db_pool
-
-    try:
-        if db_pool is None:
-            print("✅ No database pool to close")
-            return
-
-        # Close all connections in the pool
-        db_pool.closeall()
-        print("✅ All database connections closed successfully")
-
-    except Exception as e:
-        print(f"❌ Error closing database connections: {e}")

1739-1765: Database initialization is missing from on_ready.

The init_moderation_database() function is defined but never called. According to the comments at lines 660-664, it should be called in the on_ready event. Without this, db_pool will remain None and all moderation commands will fail with "Moderation tracking is not enabled."

🐛 Proposed fix

Add the database initialization call in on_ready:

 @bot.event
 async def on_ready():
     global bot_start_time, commands_synced
     bot_start_time = datetime.now()
     print(f'[{datetime.now()}] {bot.user} has connected to Discord!', flush=True)

+    # Initialize moderation database
+    db_initialized = init_moderation_database()
+    if db_initialized:
+        print("✅ Moderation tracking enabled")
+    else:
+        print("⚠️ Moderation tracking disabled")
+
     if not commands_synced:
         try:

3682-3709: New moderation commands are missing from error handlers.

The new commands (slash_warn, slash_warnings, slash_clearwarnings, slash_case, slash_cases, slash_updatecase, slash_modnote, slash_modnotes) are not included in the error handler decorator chain starting at line 3682. This means permission errors won't be handled consistently for these commands.

🐛 Proposed fix

Add the new commands to the error handler decorators:

 @slash_ban.error
 @slash_kick.error
 # ... existing decorators ...
 @slash_rolemembers.error
+@slash_warn.error
+@slash_warnings.error
+@slash_clearwarnings.error
+@slash_case.error
+@slash_cases.error
+@slash_updatecase.error
+@slash_modnote.error
+@slash_modnotes.error
 async def permission_error(interaction: discord.Interaction, error: app_commands.AppCommandError):
🧹 Nitpick comments (2)
Moderationbot.py (2)

3299-3303: Use specific exception type instead of bare except.

Bare except clauses catch all exceptions including KeyboardInterrupt and SystemExit, which can hide bugs.

♻️ Suggested fix
-            except:
+            except (discord.NotFound, discord.HTTPException):
                 mod_name = f"Unknown (ID: {warning['moderator_id']})"

3393-3412: Good fallback pattern for fetching user/moderator names.

The logic correctly prioritizes stored names and falls back to fetching when needed. However, use specific exception types (discord.NotFound, discord.HTTPException) instead of bare except clauses on lines 3399 and 3409.

📜 Review details

Configuration used: defaults

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 844c7c8 and e243b37.

📒 Files selected for processing (1)
  • Moderationbot.py
🧰 Additional context used
🧠 Learnings (1)
📓 Common learnings
Learnt from: SorynTech
Repo: SorynTech/Discord-Moderation-Bot- PR: 0
File: :0-0
Timestamp: 2025-12-30T01:12:13.273Z
Learning: Remind SorynTech to add database support in the next PR they submit to the Discord-Moderation-Bot repository.
🪛 Ruff (0.14.10)
Moderationbot.py

268-268: PEP 484 prohibits implicit Optional

Convert to T | None

(RUF013)


269-269: PEP 484 prohibits implicit Optional

Convert to T | None

(RUF013)


269-269: PEP 484 prohibits implicit Optional

Convert to T | None

(RUF013)


290-290: f-string without any placeholders

Remove extraneous f prefix

(F541)


314-314: Consider moving this statement to an else block

(TRY300)


316-316: Do not catch blind exception: Exception

(BLE001)


414-414: PEP 484 prohibits implicit Optional

Convert to T | None

(RUF013)


414-414: PEP 484 prohibits implicit Optional

Convert to T | None

(RUF013)


421-421: f-string without any placeholders

Remove extraneous f prefix

(F541)


442-442: Consider moving this statement to an else block

(TRY300)


444-444: Do not catch blind exception: Exception

(BLE001)


479-479: Do not catch blind exception: Exception

(BLE001)


485-485: PEP 484 prohibits implicit Optional

Convert to T | None

(RUF013)


511-511: Consider moving this statement to an else block

(TRY300)


513-513: Do not catch blind exception: Exception

(BLE001)


527-527: PEP 484 prohibits implicit Optional

Convert to T | None

(RUF013)


527-527: PEP 484 prohibits implicit Optional

Convert to T | None

(RUF013)


534-534: f-string without any placeholders

Remove extraneous f prefix

(F541)


555-555: Consider moving this statement to an else block

(TRY300)


557-557: Do not catch blind exception: Exception

(BLE001)


592-592: Do not catch blind exception: Exception

(BLE001)


618-618: Consider moving this statement to an else block

(TRY300)


620-620: Do not catch blind exception: Exception

(BLE001)


648-648: Do not catch blind exception: Exception

(BLE001)


3232-3232: f-string without any placeholders

Remove extraneous f prefix

(F541)


3295-3295: Loop control variable i not used within loop body

Rename unused i to _i

(B007)


3302-3302: Do not use bare except

(E722)


3347-3347: String contains ambiguous (INFORMATION SOURCE). Did you mean i (LATIN SMALL LETTER I)?

(RUF001)


3399-3399: Do not use bare except

(E722)


3409-3409: Do not use bare except

(E722)


3493-3493: Do not use bare except

(E722)


3505-3505: f-string without any placeholders

Remove extraneous f prefix

(F541)


3641-3641: String contains ambiguous (INFORMATION SOURCE). Did you mean i (LATIN SMALL LETTER I)?

(RUF001)


3664-3664: Do not use bare except

(E722)

🔇 Additional comments (5)
Moderationbot.py (5)

138-233: Good addition of username logging fields.

Storing user_name and moderator_name in the database is a good practice for moderation bots, as users may leave servers or change their usernames, making ID-only lookups less useful for historical records.


3171-3249: Good implementation of the /warn command.

The command properly:

  • Uses asyncio.to_thread for database operations to avoid blocking
  • Passes usernames for logging
  • Handles DM failures gracefully

3440-3507: Good implementation of the /cases command.

The command properly handles pagination with a limit cap and uses stored moderator names with fallback.


3559-3611: Good implementation of moderation notes feature.

The /modnote command correctly stores notes with user and moderator names, and uses ephemeral responses to keep notes private.


3797-3812: Good job adding database support as previously discussed.

Based on learnings, this PR addresses the reminder to add database support to the Discord moderation bot. The implementation provides a solid foundation for moderation tracking with warnings, cases, and notes.

Key improvements needed before merge:

  1. Call init_moderation_database() in on_ready
  2. Remove duplicate close_database function
  3. Initialize conn = None before try blocks in database functions

@SorynTech SorynTech merged commit 081ab2a into main Jan 9, 2026
1 check passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants