114 lines
3.0 KiB
C++
114 lines
3.0 KiB
C++
|
#include "XNLogger.h"
|
||
|
|
||
|
XNLogger::XNLogger()
|
||
|
: consoleOutputEnabled{true, true, true, true},
|
||
|
fileOutputEnabled{true, true, true, true} {
|
||
|
// 获取当前工作目录
|
||
|
XN_PATH currentDir = XNGetCurrentPath();
|
||
|
XN_PATH logDirPath = currentDir / "log";
|
||
|
|
||
|
// 创建 log 文件夹
|
||
|
if (!std::filesystem::exists(logDirPath)) {
|
||
|
std::filesystem::create_directories(logDirPath);
|
||
|
}
|
||
|
|
||
|
// 创建以当前日期和时间命名的日志文件
|
||
|
auto now = std::chrono::system_clock::now();
|
||
|
auto time = std::chrono::system_clock::to_time_t(now);
|
||
|
std::stringstream ss;
|
||
|
ss << std::put_time(std::localtime(&time), "%Y%m%d_%H%M%S");
|
||
|
std::string logFileName = "log_" + ss.str() + ".log";
|
||
|
|
||
|
logFilePath = (logDirPath / logFileName).string();
|
||
|
logFile.open(logFilePath, std::ios::app);
|
||
|
}
|
||
|
|
||
|
XNLogger::~XNLogger() {
|
||
|
if (logFile.is_open()) {
|
||
|
logFile.close();
|
||
|
}
|
||
|
}
|
||
|
|
||
|
std::string XNLogger::getCurrentTimeString() const {
|
||
|
auto now = std::chrono::system_clock::now();
|
||
|
auto time = std::chrono::system_clock::to_time_t(now);
|
||
|
auto ms = std::chrono::duration_cast<std::chrono::milliseconds>(
|
||
|
now.time_since_epoch()) %
|
||
|
1000;
|
||
|
|
||
|
std::stringstream ss;
|
||
|
ss << std::put_time(std::localtime(&time), "%Y-%m-%d %H:%M:%S");
|
||
|
ss << '.' << std::setfill('0') << std::setw(3) << ms.count();
|
||
|
return ss.str();
|
||
|
}
|
||
|
|
||
|
void XNLogger::log(LogLevel level, const std::string &message) {
|
||
|
std::lock_guard<std::mutex> locker(mutex);
|
||
|
std::string logMessage = "[" + getCurrentTimeString() + "] [" +
|
||
|
logLevelToString(level) + "] " + message;
|
||
|
|
||
|
std::string coloredMessage;
|
||
|
|
||
|
// 根据日志等级设置颜色
|
||
|
switch (level) {
|
||
|
case Debug:
|
||
|
coloredMessage = COLOR_DEBUG + logMessage + COLOR_RESET;
|
||
|
break;
|
||
|
case Info:
|
||
|
coloredMessage = COLOR_INFO + logMessage + COLOR_RESET;
|
||
|
break;
|
||
|
case Warning:
|
||
|
coloredMessage = COLOR_WARNING + logMessage + COLOR_RESET;
|
||
|
break;
|
||
|
case Error:
|
||
|
coloredMessage = COLOR_ERROR + logMessage + COLOR_RESET;
|
||
|
break;
|
||
|
default:
|
||
|
coloredMessage = logMessage; // 默认无颜色
|
||
|
break;
|
||
|
}
|
||
|
|
||
|
// 控制台输出
|
||
|
if (consoleOutputEnabled[level]) {
|
||
|
if (level == Time) {
|
||
|
// 如果是时间日志,则不换行,回退到该行开始
|
||
|
std::cout << coloredMessage << "\r" << std::flush;
|
||
|
} else {
|
||
|
std::cout << coloredMessage << std::endl;
|
||
|
}
|
||
|
}
|
||
|
|
||
|
// 文件输出
|
||
|
if (fileOutputEnabled[level] && logFile.is_open()) {
|
||
|
if (level == Time) {
|
||
|
logFile << logMessage << "\r" << std::flush;
|
||
|
} else {
|
||
|
logFile << logMessage << std::endl;
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
|
||
|
void XNLogger::enableConsoleOutput(LogLevel level, bool enable) {
|
||
|
consoleOutputEnabled[level] = enable;
|
||
|
}
|
||
|
|
||
|
void XNLogger::enableFileOutput(LogLevel level, bool enable) {
|
||
|
fileOutputEnabled[level] = enable;
|
||
|
}
|
||
|
|
||
|
std::string XNLogger::logLevelToString(LogLevel level) const {
|
||
|
switch (level) {
|
||
|
case Debug:
|
||
|
return "DEBUG";
|
||
|
case Info:
|
||
|
return "INFO";
|
||
|
case Warning:
|
||
|
return "WARNING";
|
||
|
case Error:
|
||
|
return "ERROR";
|
||
|
case Time:
|
||
|
return "TIME";
|
||
|
default:
|
||
|
return "UNKNOWN";
|
||
|
}
|
||
|
}
|