#include "stdafx.h" #include "SystemLogManager.h" #include "UserManager.h" #include #include #include #include // ¾²Ì¬³ÉÔ±³õʼ»¯ std::mutex SystemLogManager::m_mutex; // »ñÈ¡µ¥ÀýʵÀý SystemLogManager& SystemLogManager::getInstance() { static SystemLogManager instance; return instance; } // ¹¹Ô캯Êý SystemLogManager::SystemLogManager() : m_pDB(nullptr) { m_pDB = new BL::SQLiteDatabase(); } // Îö¹¹º¯Êý SystemLogManager::~SystemLogManager() { if (m_pDB) { delete m_pDB; m_pDB = nullptr; } } // ³õʼ»¯ÈÕÖ¾±í bool SystemLogManager::initSystemLogTable() { // »ñÈ¡¿ÉÖ´ÐÐÎļþ·¾¶ char szPath[MAX_PATH]; GetModuleFileName(NULL, szPath, MAX_PATH); std::string exePath(szPath); std::string dbDir = exePath.substr(0, exePath.find_last_of("\\/")) + "\\DB"; // ´´½¨ DB Ŀ¼ if (!CreateDirectory(dbDir.c_str(), NULL) && GetLastError() != ERROR_ALREADY_EXISTS) { throw std::runtime_error("´´½¨Êý¾Ý¿âĿ¼ʧ°Ü"); } // ¹¹ÔìÊý¾Ý¿â·¾¶ std::string dbPath = dbDir + "\\SystemLogManager.db"; // Á¬½ÓÊý¾Ý¿â if (!m_pDB->connect(dbPath, true)) { throw std::runtime_error("Á¬½ÓÈÕÖ¾Êý¾Ý¿âʧ°Ü"); } // ´´½¨ÈÕÖ¾±í SQL Óï¾ä const std::string createTableQuery = R"( CREATE TABLE IF NOT EXISTS system_logs ( id INTEGER PRIMARY KEY AUTOINCREMENT, log_type TEXT NOT NULL, event TEXT NOT NULL, username TEXT NOT NULL, timestamp DATETIME DEFAULT (datetime('now', 'localtime')) ) )"; return m_pDB->executeQuery(createTableQuery); } // ÖÕÖ¹Êý¾Ý¿âÁ¬½Ó void SystemLogManager::termSystemLogTable() { if (!m_pDB) { return; } m_pDB->disconnect(); } // Ìí¼ÓÈÕÖ¾£¨Ê¹Óõ±Ç°Óû§£© bool SystemLogManager::log(LogType logType, const std::string& event) { if (!m_pDB) { throw std::runtime_error("Database connection is not set."); } cleanOldLogs(); std::string username = UserManager::getInstance().getCurrentUser(); if (username.empty()) { username = "SYSTEM"; } std::ostringstream query; query << "INSERT INTO system_logs (log_type, event, username) VALUES (" << "'" << logTypeToString(logType) << "', " << "'" << event << "', " << "'" << username << "')"; std::lock_guard lock(m_mutex); return m_pDB->executeQuery(query.str()); } // Ìí¼ÓÈÕÖ¾£¨Ö¸¶¨Óû§£© bool SystemLogManager::log(LogType logType, const std::string& event, const std::string& username) { if (!m_pDB) { throw std::runtime_error("Database connection is not set."); } cleanOldLogs(); std::ostringstream query; query << "INSERT INTO system_logs (log_type, event, username) VALUES (" << "'" << logTypeToString(logType) << "', " << "'" << event << "', " << "'" << username << "')"; std::lock_guard lock(m_mutex); return m_pDB->executeQuery(query.str()); } // »ñÈ¡ÈÕÖ¾ÄÚÈÝ std::vector> SystemLogManager::getLogs(int startPosition, int count) { if (!m_pDB) { throw std::runtime_error("Database connection is not set."); } std::ostringstream query; if (startPosition == -1 && count == -1) { query << "SELECT id, log_type, event, username, datetime(timestamp, 'localtime') FROM system_logs"; } else { query << "SELECT id, log_type, event, username, datetime(timestamp, 'localtime') FROM system_logs " << "LIMIT " << count << " OFFSET " << startPosition; } return m_pDB->fetchResults(query.str()); } // »ñȡɸѡºóµÄÈÕÖ¾Êý¾Ý std::vector> SystemLogManager::getFilteredLogs( const std::string& logType, const std::string& username, const std::string& description, const std::string& startTime, const std::string& endTime, int pageNumber, int pageSize) { if (!m_pDB) { throw std::runtime_error("Database connection is not set."); } std::ostringstream query; query << "SELECT id, log_type, event, username, datetime(timestamp, 'localtime') FROM system_logs WHERE 1=1"; if (logType != "ALL") { query << " AND log_type = '" << logType << "'"; } if (username != "ALL") { query << " AND username = '" << username << "'"; } if (!description.empty()) { query << " AND event LIKE '%" << description << "%'"; } if (!startTime.empty()) { query << " AND timestamp >= '" << startTime << "'"; } if (!endTime.empty()) { query << " AND timestamp <= '" << endTime << "'"; } int offset = (pageNumber - 1) * pageSize; query << " ORDER BY timestamp DESC LIMIT " << pageSize << " OFFSET " << offset; return m_pDB->fetchResults(query.str()); } // »ñÈ¡·ûºÏÌõ¼þµÄÈÕÖ¾×ÜÊý int SystemLogManager::getTotalLogCount( const std::string& logType, const std::string& username, const std::string& description, const std::string& startTime, const std::string& endTime) { if (!m_pDB) { throw std::runtime_error("Database connection is not set."); } std::ostringstream query; query << "SELECT COUNT(*) FROM system_logs WHERE 1=1"; if (logType != "ALL") { query << " AND log_type = '" << logType << "'"; } if (username != "ALL") { query << " AND username = '" << username << "'"; } if (!description.empty()) { query << " AND event LIKE '%" << description << "%'"; } if (!startTime.empty()) { query << " AND timestamp >= '" << startTime << "'"; } if (!endTime.empty()) { query << " AND timestamp <= '" << endTime << "'"; } auto results = m_pDB->fetchResults(query.str()); return (!results.empty() && !results[0].empty()) ? std::stoi(results[0][0]) : 0; } // ÇåÀí³¬¹ýÖ¸¶¨ÌìÊýµÄ¾ÉÈÕÖ¾ void SystemLogManager::cleanOldLogs(int daysToKeep) { if (!m_pDB) { throw std::runtime_error("Database connection is not set."); } std::ostringstream query; query << "DELETE FROM system_logs WHERE timestamp < datetime('now', '-" << daysToKeep << " days')"; m_pDB->executeQuery(query.str()); } // ת»»ÈÕÖ¾ÀàÐÍΪ×Ö·û´® std::string SystemLogManager::logTypeToString(LogType logType) { switch (logType) { case LogType::Info: return "ÐÅÏ¢"; case LogType::Error: return "´íÎó"; case LogType::Operation: return "²Ù×÷"; default: return "δ֪"; } }