Implement database path validation in BotDataViewer and BotIntegration

- Added validation for the database path using the validate_safe_path function to ensure paths are safe and relative to the bot root.
- Enhanced error handling to log warnings when invalid paths are detected, defaulting to 'bot_data.db' if necessary.
- This change improves the robustness of database connections across the application.
This commit is contained in:
agessaman
2025-12-28 09:23:37 -08:00
parent f4cd1a27e5
commit c2bd1f06e3
2 changed files with 71 additions and 0 deletions
+41
View File
@@ -24,6 +24,7 @@ sys.path.insert(0, project_root)
from modules.db_manager import DBManager
from modules.repeater_manager import RepeaterManager
from modules.security_utils import validate_safe_path
class BotDataViewer:
"""Complete web interface using Flask-SocketIO 5.x best practices"""
@@ -178,6 +179,13 @@ class BotDataViewer:
# Get database path from config
db_path = self.config.get('Database', 'path', fallback='bot_data.db')
# Validate and resolve database path relative to bot root
try:
db_path = str(validate_safe_path(db_path, base_dir=str(self.bot_root), allow_absolute=False))
except ValueError as e:
self.logger.warning(f"Invalid database path: {e}, using default: bot_data.db")
db_path = 'bot_data.db'
# Connect to database and create table if it doesn't exist
conn = sqlite3.connect(db_path, timeout=30)
cursor = conn.cursor()
@@ -388,6 +396,13 @@ class BotDataViewer:
# Get database path
db_path = self.config.get('Database', 'path', fallback='bot_data.db')
# Validate and resolve database path relative to bot root
try:
db_path = str(validate_safe_path(db_path, base_dir=str(self.bot_root), allow_absolute=False))
except ValueError:
# If validation fails, use default (already set above)
pass
conn = sqlite3.connect(db_path, timeout=30)
cursor = conn.cursor()
@@ -1413,6 +1428,13 @@ class BotDataViewer:
# Get database path
db_path = self.config.get('Database', 'path', fallback='bot_data.db')
# Validate and resolve database path relative to bot root
try:
db_path = str(validate_safe_path(db_path, base_dir=str(self.bot_root), allow_absolute=False))
except ValueError:
# If validation fails, use default (already set above)
pass
# Connect to database with timeout to prevent hanging
conn = sqlite3.connect(db_path, timeout=30)
cursor = conn.cursor()
@@ -1525,6 +1547,13 @@ class BotDataViewer:
# Get database path
db_path = self.config.get('Database', 'path', fallback='bot_data.db')
# Validate and resolve database path relative to bot root
try:
db_path = str(validate_safe_path(db_path, base_dir=str(self.bot_root), allow_absolute=False))
except ValueError:
# If validation fails, use default (already set above)
pass
# Use timeout to prevent hanging
conn = sqlite3.connect(db_path, timeout=30)
cursor = conn.cursor()
@@ -2004,6 +2033,12 @@ class BotDataViewer:
# Get database file size
import os
db_path = self.config.get('Database', 'path', fallback='bot_data.db')
# Validate and resolve database path relative to bot root
try:
db_path = str(validate_safe_path(db_path, base_dir=str(self.bot_root), allow_absolute=False))
except ValueError:
# If validation fails, use default (already set above)
pass
try:
db_size_bytes = os.path.getsize(db_path)
if db_size_bytes < 1024:
@@ -2060,6 +2095,12 @@ class BotDataViewer:
# Get initial database size
import os
db_path = self.config.get('Database', 'path', fallback='bot_data.db')
# Validate and resolve database path relative to bot root
try:
db_path = str(validate_safe_path(db_path, base_dir=str(self.bot_root), allow_absolute=False))
except ValueError:
# If validation fails, use default (already set above)
pass
initial_size = os.path.getsize(db_path)
# Perform VACUUM to reclaim unused space
+30
View File
@@ -11,6 +11,7 @@ import sys
import os
import re
from pathlib import Path
from ..security_utils import validate_safe_path
class BotIntegration:
"""Simple bot integration for web viewer compatibility"""
@@ -36,6 +37,14 @@ class BotIntegration:
# Get database path from config
db_path = self.bot.config.get('Database', 'path', fallback='bot_data.db')
# Validate and resolve database path relative to bot root
try:
base_dir = str(self.bot.bot_root) if hasattr(self.bot, 'bot_root') else '.'
db_path = str(validate_safe_path(db_path, base_dir=base_dir, allow_absolute=False))
except ValueError as e:
self.bot.logger.warning(f"Invalid database path: {e}, using default: bot_data.db")
db_path = 'bot_data.db'
# Connect to database and create table if it doesn't exist
conn = sqlite3.connect(db_path)
cursor = conn.cursor()
@@ -99,6 +108,13 @@ class BotIntegration:
# Store in database for web viewer to read
db_path = self.bot.config.get('Database', 'path', fallback='bot_data.db')
# Validate and resolve database path relative to bot root
try:
base_dir = str(self.bot.bot_root) if hasattr(self.bot, 'bot_root') else '.'
db_path = str(validate_safe_path(db_path, base_dir=base_dir, allow_absolute=False))
except ValueError:
# If validation fails, use default (already set above)
pass
conn = sqlite3.connect(db_path)
cursor = conn.cursor()
@@ -149,6 +165,13 @@ class BotIntegration:
# Store in database for web viewer to read
db_path = self.bot.config.get('Database', 'path', fallback='bot_data.db')
# Validate and resolve database path relative to bot root
try:
base_dir = str(self.bot.bot_root) if hasattr(self.bot, 'bot_root') else '.'
db_path = str(validate_safe_path(db_path, base_dir=base_dir, allow_absolute=False))
except ValueError:
# If validation fails, use default (already set above)
pass
conn = sqlite3.connect(db_path)
cursor = conn.cursor()
@@ -176,6 +199,13 @@ class BotIntegration:
# Store in database for web viewer to read
db_path = self.bot.config.get('Database', 'path', fallback='bot_data.db')
# Validate and resolve database path relative to bot root
try:
base_dir = str(self.bot.bot_root) if hasattr(self.bot, 'bot_root') else '.'
db_path = str(validate_safe_path(db_path, base_dir=base_dir, allow_absolute=False))
except ValueError:
# If validation fails, use default (already set above)
pass
conn = sqlite3.connect(db_path)
cursor = conn.cursor()