refactor(log): reduce function calls

This commit is contained in:
whaffman 2025-10-08 17:21:48 +02:00
parent f222cce4ff
commit c401b5fbbd
8 changed files with 65 additions and 56 deletions

View File

@ -4,15 +4,6 @@
#include <sstream> // for basic_ostream, operator<<, basic_stringstream, basic_istream, basic_istringstream, right, istringstream, stringstream #include <sstream> // for basic_ostream, operator<<, basic_stringstream, basic_istream, basic_istringstream, right, istringstream, stringstream
#include <utility> // for get #include <utility> // for get
Log::Level Channel::getLogLevel() const
{
return logLevel_;
}
void Channel::setLogLevel(Log::Level level)
{
logLevel_ = level;
}
std::string Channel::printContext(const std::map<std::string, std::string> &context) std::string Channel::printContext(const std::map<std::string, std::string> &context)
{ {

View File

@ -18,10 +18,10 @@ class Channel
const std::map<std::string, std::string> &context = {}) = 0; const std::map<std::string, std::string> &context = {}) = 0;
protected: protected:
[[nodiscard]] Log::Level getLogLevel() const;
[[nodiscard]] static std::string printContext(const std::map<std::string, std::string> &context); [[nodiscard]] static std::string printContext(const std::map<std::string, std::string> &context);
void setLogLevel(Log::Level level);
private: private:
Log::Level logLevel_{Log::Level::Trace};
}; };

View File

@ -9,10 +9,9 @@
struct tm; struct tm;
FileChannel::FileChannel(const std::string &filename, std::ios_base::openmode mode, Log::Level logLevel) FileChannel::FileChannel(const std::string &filename, std::ios_base::openmode mode)
: filename_(filename), fileStream_(filename, mode) : filename_(filename), fileStream_(filename, mode)
{ {
setLogLevel(logLevel);
if (!fileStream_.is_open()) if (!fileStream_.is_open())
{ {
std::cerr << "Failed to open log file: " << filename << '\n'; std::cerr << "Failed to open log file: " << filename << '\n';
@ -30,10 +29,7 @@ FileChannel::~FileChannel()
void FileChannel::log(const Log::Level &logLevel, const std::string &message, void FileChannel::log(const Log::Level &logLevel, const std::string &message,
const std::map<std::string, std::string> &context) const std::map<std::string, std::string> &context)
{ {
if (logLevel < getLogLevel())
{
return;
}
if (!fileStream_.is_open()) if (!fileStream_.is_open())
{ {
std::cerr << "Log file is not open: " << filename_ << '\n'; std::cerr << "Log file is not open: " << filename_ << '\n';

View File

@ -10,7 +10,7 @@
class FileChannel : public Channel class FileChannel : public Channel
{ {
public: public:
FileChannel(const std::string &filename, std::ios_base::openmode mode, Log::Level logLevel = Log::Level::Trace); FileChannel(const std::string &filename, std::ios_base::openmode mode);
FileChannel(const FileChannel &other) = delete; FileChannel(const FileChannel &other) = delete;
FileChannel(FileChannel &&other) = delete; FileChannel(FileChannel &&other) = delete;

View File

@ -1,7 +1,6 @@
#include <webserv/log/Log.hpp>
#include <webserv/log/Channel.hpp> // for Channel #include <webserv/log/Channel.hpp> // for Channel
#include <webserv/log/FileChannel.hpp> // for FileChannel #include <webserv/log/FileChannel.hpp> // for FileChannel
#include <webserv/log/Log.hpp>
#include <webserv/log/StdoutChannel.hpp> // for StdoutChannel #include <webserv/log/StdoutChannel.hpp> // for StdoutChannel
#include <chrono> // for duration_cast, operator-, steady_clock, duration, seconds #include <chrono> // for duration_cast, operator-, steady_clock, duration, seconds
@ -16,7 +15,7 @@ Log::Log()
start_time_ = std::chrono::steady_clock::now(); start_time_ = std::chrono::steady_clock::now();
} }
void Log::setStdoutChannel(Log::Level logLevel) void Log::setStdoutChannel()
{ {
Log &log = getInstance(); Log &log = getInstance();
if (log.channels_.contains("stdout")) if (log.channels_.contains("stdout"))
@ -25,7 +24,7 @@ void Log::setStdoutChannel(Log::Level logLevel)
} }
try try
{ {
log.channels_["stdout"] = std::make_unique<StdoutChannel>(logLevel); log.channels_["stdout"] = std::make_unique<StdoutChannel>();
} }
catch (const std::exception &e) catch (const std::exception &e)
{ {
@ -33,7 +32,7 @@ void Log::setStdoutChannel(Log::Level logLevel)
} }
} }
void Log::setFileChannel(const std::string &filename, std::ios_base::openmode mode, Log::Level logLevel) void Log::setFileChannel(const std::string &filename, std::ios_base::openmode mode)
{ {
Log &log = getInstance(); Log &log = getInstance();
if (log.channels_.contains("file")) if (log.channels_.contains("file"))
@ -42,7 +41,7 @@ void Log::setFileChannel(const std::string &filename, std::ios_base::openmode mo
} }
try try
{ {
log.channels_["file"] = std::make_unique<FileChannel>(filename, mode, logLevel); log.channels_["file"] = std::make_unique<FileChannel>(filename, mode);
} }
catch (const std::exception &e) catch (const std::exception &e)
{ {
@ -56,7 +55,7 @@ Log &Log::getInstance()
return instance; return instance;
} }
void Log::log(Log::Level level, const std::string &message, const std::map<std::string, std::string> &context) void Log::log(Level level, const std::string &message, const std::map<std::string, std::string> &context)
{ {
for (auto &it : channels_) for (auto &it : channels_)
{ {
@ -75,36 +74,61 @@ int Log::getElapsedTime()
void Log::trace(const std::string &message, const std::map<std::string, std::string> &context) void Log::trace(const std::string &message, const std::map<std::string, std::string> &context)
{ {
getInstance().log(Log::Level::Trace, message, context); if constexpr (COMPILE_TIME_LOG_LEVEL > Level::Trace)
{
return;
}
getInstance().log(Level::Trace, message, context);
} }
void Log::debug(const std::string &message, const std::map<std::string, std::string> &context) void Log::debug(const std::string &message, const std::map<std::string, std::string> &context)
{ {
getInstance().log(Log::Level::Debug, message, context); if constexpr (COMPILE_TIME_LOG_LEVEL > Level::Debug)
{
return;
}
getInstance().log(Level::Debug, message, context);
} }
void Log::info(const std::string &message, const std::map<std::string, std::string> &context) void Log::info(const std::string &message, const std::map<std::string, std::string> &context)
{ {
getInstance().log(Log::Level::Info, message, context); if constexpr (COMPILE_TIME_LOG_LEVEL > Level::Info)
{
return;
}
getInstance().log(Level::Info, message, context);
} }
void Log::warning(const std::string &message, const std::map<std::string, std::string> &context) void Log::warning(const std::string &message, const std::map<std::string, std::string> &context)
{ {
getInstance().log(Log::Level::Warn, message, context); if constexpr (COMPILE_TIME_LOG_LEVEL > Level::Warn)
{
return;
}
getInstance().log(Level::Warn, message, context);
} }
void Log::error(const std::string &message, const std::map<std::string, std::string> &context) void Log::error(const std::string &message, const std::map<std::string, std::string> &context)
{ {
getInstance().log(Log::Level::Error, message, context); if constexpr (COMPILE_TIME_LOG_LEVEL > Level::Error)
{
return;
}
getInstance().log(Level::Error, message, context);
} }
void Log::fatal(const std::string &message, const std::map<std::string, std::string> &context) void Log::fatal(const std::string &message, const std::map<std::string, std::string> &context)
{ {
getInstance().log(Log::Level::Fatal, message, context); if constexpr (COMPILE_TIME_LOG_LEVEL > Level::Fatal)
{
return;
}
getInstance().log(Level::Fatal, message, context);
} }
std::string Log::logLevelToString(Log::Level level) std::string Log::logLevelToString(Level level)
{ {
for (const auto &mapping : LOG_LEVEL_MAP) for (const auto &mapping : LOG_LEVEL_MAP)
{ {
if (mapping.level == level) if (mapping.level == level)
@ -115,7 +139,7 @@ std::string Log::logLevelToString(Log::Level level)
return "UNKNOWN"; return "UNKNOWN";
} }
const char *Log::logLevelToColor(Log::Level level) const char *Log::logLevelToColor(Level level)
{ {
for (const auto &mapping : LOG_LEVEL_MAP) for (const auto &mapping : LOG_LEVEL_MAP)
{ {
@ -127,7 +151,7 @@ const char *Log::logLevelToColor(Log::Level level)
return RESET_COLOR; // Default to reset return RESET_COLOR; // Default to reset
} }
std::string Log::logLevelToColoredString(Log::Level level) std::string Log::logLevelToColoredString(Level level)
{ {
return std::string(Log::logLevelToColor(level)) + Log::logLevelToString(level) + RESET_COLOR; return std::string(Log::logLevelToColor(level)) + Log::logLevelToString(level) + RESET_COLOR;
} }
@ -141,5 +165,5 @@ Log::Level Log::stringToLogLevel(const std::string &level)
return mapping.level; return mapping.level;
} }
} }
return Log::Level::Info; // Default fallback return Level::Info; // Default fallback
} }

View File

@ -29,9 +29,15 @@ constexpr const char *extractFilename(const char *path)
#define LOCATION \ #define LOCATION \
(std::string(extractFilename(__FILE__)) + ":" + std::to_string(__LINE__) + " (" + std::string(__FUNCTION__) + ")") (std::string(extractFilename(__FILE__)) + ":" + std::to_string(__LINE__) + " (" + std::string(__FUNCTION__) + ")")
class Log class Log
{ {
public: public:
Log(const Log &other) = delete;
Log(Log &&other) = delete;
Log &operator=(const Log &other) = delete;
Log &operator=(Log &&other) = delete;
enum class Level : uint8_t enum class Level : uint8_t
{ {
Trace = 0, Trace = 0,
@ -42,16 +48,12 @@ class Log
Fatal = 5 Fatal = 5
}; };
Log(const Log &other) = delete;
Log(Log &&other) = delete;
Log &operator=(const Log &other) = delete;
Log &operator=(Log &&other) = delete;
void log(Level level, const std::string &message, const std::map<std::string, std::string> &context); void log(Level level, const std::string &message, const std::map<std::string, std::string> &context);
static void setFileChannel(const std::string &filename, std::ios_base::openmode mode = std::ios_base::app, static constexpr Log::Level COMPILE_TIME_LOG_LEVEL = Log::Level::Info;
Level logLevel = Level::Trace);
static void setStdoutChannel(Level logLevel = Level::Trace); static void setFileChannel(const std::string &filename, std::ios_base::openmode mode = std::ios_base::app);
static void setStdoutChannel();
static int getElapsedTime(); static int getElapsedTime();
@ -65,7 +67,7 @@ class Log
static std::string logLevelToString(Level level); static std::string logLevelToString(Level level);
static const char *logLevelToColor(Level level); static const char *logLevelToColor(Level level);
static std::string logLevelToColoredString(Level level); static std::string logLevelToColoredString(Level level);
static Log::Level stringToLogLevel(const std::string &level); static Level stringToLogLevel(const std::string &level);
private: private:
Log(); Log();
@ -78,7 +80,7 @@ class Log
struct LevelMapping struct LevelMapping
{ {
Log::Level level; Level level;
std::string_view name; std::string_view name;
const char *color; const char *color;
}; };
@ -93,3 +95,5 @@ class Log
constexpr static const char *RESET_COLOR = "\033[0m"; constexpr static const char *RESET_COLOR = "\033[0m";
}; };

View File

@ -5,18 +5,12 @@
#include <iomanip> // for operator<<, setfill, setw #include <iomanip> // for operator<<, setfill, setw
#include <iostream> // for basic_ostream, operator<<, basic_ostream::operator<<, cerr, cout, flush, ostream #include <iostream> // for basic_ostream, operator<<, basic_ostream::operator<<, cerr, cout, flush, ostream
StdoutChannel::StdoutChannel(Log::Level logLevel)
{
setLogLevel(logLevel);
}
void StdoutChannel::log(const Log::Level &logLevel, const std::string &message, void StdoutChannel::log(const Log::Level &logLevel, const std::string &message,
const std::map<std::string, std::string> &context) const std::map<std::string, std::string> &context)
{ {
if (logLevel < getLogLevel())
{
return;
}
std::ostream &out = (logLevel >= Log::Level::Warn) ? std::cerr : std::cout; std::ostream &out = (logLevel >= Log::Level::Warn) ? std::cerr : std::cout;
out << "[" << std::setw(3) << std::setfill('0') << Log::getElapsedTime() << "] "; out << "[" << std::setw(3) << std::setfill('0') << Log::getElapsedTime() << "] ";
std::string prefix = "[" + Log::logLevelToColoredString(logLevel) + "] "; std::string prefix = "[" + Log::logLevelToColoredString(logLevel) + "] ";

View File

@ -9,7 +9,7 @@
class StdoutChannel : public Channel class StdoutChannel : public Channel
{ {
public: public:
StdoutChannel(Log::Level logLevel = Log::Level::Trace); StdoutChannel() = default;
StdoutChannel(const StdoutChannel &other) = delete; StdoutChannel(const StdoutChannel &other) = delete;
StdoutChannel(StdoutChannel &&other) = delete; StdoutChannel(StdoutChannel &&other) = delete;