Since v1.3.0, thread_safe_writer is the recommended base class for custom writers. It eliminates boilerplate mutex code and ensures consistent thread-safety.
#include <kcenon/common/interfaces/logger_interface.h>
#include <iostream>
#include <vector>
#include <map>
namespace ci = kcenon::common::interfaces;
public:
return "memory";
}
std::lock_guard<std::mutex> lock(
get_mutex());
}
std::lock_guard<std::mutex> lock(
get_mutex());
}
std::lock_guard<std::mutex> lock(
get_mutex());
}
protected:
{
}
}
private:
};
public:
for (int i = 0; i <= static_cast<int>(kcenon::common::interfaces::log_level::trace); ++i) {
counts_[
static_cast<kcenon::common::interfaces::log_level
>(i)] = 0;
}
}
return "counted_console";
}
size_t get_count(kcenon::common::interfaces::log_level level)
const {
std::lock_guard<std::mutex> lock(
get_mutex());
return (it !=
counts_.end()) ? it->second : 0;
}
std::lock_guard<std::mutex> lock(
get_mutex());
size_t total = 0;
for (
const auto& [level, count] :
counts_) {
total += count;
}
return total;
}
std::lock_guard<std::mutex> lock(
get_mutex());
std::cout << "\n=== Log Statistics ===" << std::endl;
std::cout <<
"Fatal: " <<
counts_.at(kcenon::common::interfaces::log_level::fatal) << std::endl;
std::cout <<
"Error: " <<
counts_.at(kcenon::common::interfaces::log_level::error) << std::endl;
std::cout <<
"Warning: " <<
counts_.at(kcenon::common::interfaces::log_level::warning) << std::endl;
std::cout <<
"Info: " <<
counts_.at(kcenon::common::interfaces::log_level::info) << std::endl;
std::cout <<
"Debug: " <<
counts_.at(kcenon::common::interfaces::log_level::debug) << std::endl;
std::cout <<
"Trace: " <<
counts_.at(kcenon::common::interfaces::log_level::trace) << std::endl;
}
protected:
{
auto level =
static_cast<kcenon::common::interfaces::log_level
>(
static_cast<int>(entry.
level));
switch (level) {
case kcenon::common::interfaces::log_level::fatal:
case kcenon::common::interfaces::log_level::error:
std::cerr << "\033[31m" << formatted << "\033[0m" << std::endl;
break;
case kcenon::common::interfaces::log_level::warning:
std::cout << "\033[33m" << formatted << "\033[0m" << std::endl;
break;
default:
std::cout << formatted << std::endl;
break;
}
} else {
if (level <= kcenon::common::interfaces::log_level::error) {
std::cerr << formatted << std::endl;
} else {
std::cout << formatted << std::endl;
}
}
}
std::cout.flush();
std::cerr.flush();
}
private:
mutable std::map<kcenon::common::interfaces::log_level, size_t>
counts_;
};
std::cout << "=== Custom Writer Example (thread_safe_writer) ===" << std::endl;
std::cout << std::endl;
std::cout << "--- Example 1: Memory Writer ---" << std::endl;
{
.
add_writer(
"memory", std::make_unique<memory_writer>())
std::cerr << "Failed to create logger" << std::endl;
return 1;
}
logger->log(ci::log_level::info, std::string(
"First message"));
logger->log(ci::log_level::warning, std::string(
"Second message"));
logger->log(ci::log_level::error, std::string(
"Third message"));
std::cout << "Logged 3 messages to memory writer" << std::endl;
}
std::cout << std::endl;
std::cout << "--- Example 2: Counted Console Writer ---" << std::endl;
{
auto counted_writer = std::make_unique<counted_console_writer>();
auto* counted_ptr = counted_writer.get();
std::cerr << "Failed to create logger" << std::endl;
return 1;
}
logger->log(ci::log_level::debug, std::string(
"Debug message 1"));
logger->log(ci::log_level::debug, std::string(
"Debug message 2"));
logger->log(ci::log_level::info, std::string(
"Info message"));
logger->log(ci::log_level::warning, std::string(
"Warning message"));
logger->log(ci::log_level::error, std::string(
"Error message"));
counted_ptr->print_stats();
}
std::cout << std::endl;
std::cout << "=== Custom Writer Example Complete ===" << std::endl;
return 0;
}
A console writer that counts messages per log level.
kcenon::common::VoidResult flush_impl() override
Implementation of flush operation (override in derived classes)
std::string get_name() const override
kcenon::common::VoidResult write_entry_impl(const log_entry &entry) override
Implementation of structured write operation (override in derived classes)
size_t total_count() const
Get total message count.
void print_stats() const
Print statistics summary.
size_t get_count(kcenon::common::interfaces::log_level level) const
Get count for a specific log level.
std::map< kcenon::common::interfaces::log_level, size_t > counts_
std::string format_log_entry(const log_entry &entry) const
Format a log entry using the current formatter.
bool use_color() const
Get current color output setting.
Builder pattern for logger construction with validation.
logger_builder & with_min_level(log_level level)
result< std::unique_ptr< logger > > build()
logger_builder & add_writer(const std::string &name, log_writer_ptr writer)
Add a writer to the logger.
Base class providing automatic thread-safety for writer implementations.
std::mutex & get_mutex() const
Access the writer mutex for extended operations.
A custom writer that stores log entries in memory.
kcenon::common::VoidResult flush_impl() override
Implementation of flush operation.
std::vector< std::string > entries_
size_t size() const
Get count of stored entries.
kcenon::common::VoidResult write_entry_impl(const log_entry &entry) override
Implementation of write operation.
std::vector< std::string > get_entries() const
Get all stored log entries.
std::string get_name() const override
void clear()
Clear all stored entries.
Console writer for logging to stdout/stderr.
Data structures for representing log entries and source locations kcenon.
Builder pattern implementation for flexible logger configuration kcenon.
Represents a single log entry with all associated metadata.
log_level level
Severity level of the log message.
Thread-safe base class for writer implementations kcenon.