From 02dcde6f540048b1b3be7b16f561444a8a5539aa Mon Sep 17 00:00:00 2001 From: SimolZimol <70102430+SimolZimol@users.noreply.github.com> Date: Sun, 24 Aug 2025 01:22:14 +0200 Subject: [PATCH] deleted: database_optimization_plan.md --- database_optimization_plan.md | 177 ---------------------------------- 1 file changed, 177 deletions(-) delete mode 100644 database_optimization_plan.md diff --git a/database_optimization_plan.md b/database_optimization_plan.md deleted file mode 100644 index b19350b..0000000 --- a/database_optimization_plan.md +++ /dev/null @@ -1,177 +0,0 @@ -# Database Connection Management Improvements for Bot -# Diese Datei zeigt die empfohlenen Änderungen für bot.py um das "Too many connections" Problem zu lösen - -## Problem Analyse: -# 1. Bot Pool: 30 Verbindungen -# 2. App direktverbindungen ohne Pool (jetzt mit Pool: 15) -# 3. Neue Warning-Funktionen verwenden viele DB-Verbindungen -# 4. get_user_warnings() wird häufig aufgerufen und öffnet jedes Mal neue Connections -# 5. Context-Archivierung kann große Datenmengen verarbeiten - -## Lösungsansätze implementiert: - -### 1. App.py Connection Pool (✅ Implementiert): -- Connection Pool mit 15 Verbindungen für Flask App -- Context Manager für sichere Verbindungsverwaltung -- Automatische Verbindungsfreigabe -- Fallback für Pool-Probleme - -### 2. Optimierungen für Bot.py (Empfohlen): -# Diese Änderungen sollten in bot.py implementiert werden: - -```python -# Verbesserte get_user_warnings Funktion mit Connection Pooling -async def get_user_warnings(user_id, guild_id, active_only=True): - """Retrieves warning records for a user - OPTIMIZED VERSION""" - connection = None - cursor = None - try: - connection = connect_to_database() # Nutzt bereits den Pool - cursor = connection.cursor() - - # Single query statt multiple calls - select_query = """ - SELECT id, moderator_id, reason, created_at, message_id, message_content, - message_attachments, message_author_id, message_channel_id, context_messages, aktiv - FROM user_warnings - WHERE user_id = %s AND guild_id = %s {} - ORDER BY created_at DESC - """.format("AND aktiv = TRUE" if active_only else "") - - cursor.execute(select_query, (user_id, guild_id)) - results = cursor.fetchall() - - warnings = [] - for row in results: - warnings.append({ - "id": row[0], - "moderator_id": row[1], - "reason": row[2], - "created_at": row[3], - "message_id": row[4], - "message_content": row[5], - "message_attachments": row[6], - "message_author_id": row[7], - "message_channel_id": row[8], - "context_messages": row[9], - "aktiv": row[10] - }) - - return warnings - - except Exception as e: - logger.error(f"Error getting user warnings: {e}") - return [] - finally: - if cursor: - cursor.close() - if connection: - close_database_connection(connection) # Gibt Connection an Pool zurück -``` - -### 3. Connection Caching für häufige Abfragen: -# Implementiere Caching für Warning-Abfragen: - -```python -import asyncio -from functools import lru_cache - -# Cache für häufige Warning-Abfragen (5 Minuten TTL) -warning_cache = {} -cache_ttl = 300 # 5 Minuten - -async def get_user_warnings_cached(user_id, guild_id, active_only=True): - """Cached version of get_user_warnings""" - cache_key = f"{user_id}_{guild_id}_{active_only}" - current_time = asyncio.get_event_loop().time() - - # Check cache - if cache_key in warning_cache: - cached_data, timestamp = warning_cache[cache_key] - if current_time - timestamp < cache_ttl: - return cached_data - - # Fetch fresh data - warnings = await get_user_warnings(user_id, guild_id, active_only) - warning_cache[cache_key] = (warnings, current_time) - - # Clean old cache entries - if len(warning_cache) > 1000: # Limit cache size - old_keys = [k for k, (_, ts) in warning_cache.items() - if current_time - ts > cache_ttl] - for k in old_keys: - del warning_cache[k] - - return warnings -``` - -### 4. Batch Operations für Context Messages: -# Reduziere DB-Aufrufe bei Context-Archivierung: - -```python -async def batch_insert_warnings(warning_data_list): - """Insert multiple warnings in a single transaction""" - if not warning_data_list: - return - - connection = None - cursor = None - try: - connection = connect_to_database() - cursor = connection.cursor() - - insert_query = """ - INSERT INTO user_warnings (user_id, guild_id, moderator_id, reason, created_at, - message_id, message_content, message_attachments, - message_author_id, message_channel_id, context_messages, aktiv) - VALUES (%s, %s, %s, %s, %s, %s, %s, %s, %s, %s, %s, %s) - """ - - cursor.executemany(insert_query, warning_data_list) - connection.commit() - - except Exception as e: - logger.error(f"Error in batch insert warnings: {e}") - if connection: - connection.rollback() - finally: - if cursor: - cursor.close() - if connection: - close_database_connection(connection) -``` - -### 5. Pool Monitoring: -# Überwache Pool-Status: - -```python -def monitor_connection_pool(): - """Monitor connection pool status""" - try: - pool_size = pool.pool_size - # This is tricky to get exact usage, but we can log pool creation - logger.info(f"Connection pool status - Size: {pool_size}") - return pool_size - except Exception as e: - logger.error(f"Error monitoring pool: {e}") - return 0 -``` - -## Sofortige Maßnahmen: -1. ✅ App.py mit Connection Pool ausgestattet (15 Verbindungen) -2. 🔄 Bot Pool von 30 auf 25 reduzieren (Gesamtlimit: 40 statt 50+) -3. 🔄 Warning-Cache implementieren -4. 🔄 Batch-Operations für große Datensätze - -## Connection Limits: -- MySQL Standard: 151 gleichzeitige Verbindungen -- Bot Pool: 30 → empfohlen 25 -- App Pool: 15 -- Reserve für andere Clients: 111 -- Sicherheitspuffer: sollte ausreichend sein - -Das Problem tritt auf, weil: -1. Neue Warning-Funktionen häufige DB-Zugriffe machen -2. Context-Archivierung große Datenmengen verarbeitet -3. get_user_warnings() wird oft aufgerufen (account, viewwarn Commands) -4. App und Bot konkurrieren um Verbindungen