From 11c7b00933c4d183234015d2c2a89b442e55b730 Mon Sep 17 00:00:00 2001 From: Pavel Artsishevsky Date: Fri, 11 Oct 2024 15:26:02 +0200 Subject: [PATCH] Add {function}, {time} and {thread} placeholders Signed-off-by: Pavel Artsishevsky --- include/log/pattern.h | 32 ++++++++++++++++++++++++++++++-- include/log/record.h | 3 +++ include/log/sink.h | 6 +++++- src/main.cpp | 4 ++-- 4 files changed, 40 insertions(+), 5 deletions(-) diff --git a/include/log/pattern.h b/include/log/pattern.h index b62817c..99532f0 100644 --- a/include/log/pattern.h +++ b/include/log/pattern.h @@ -165,7 +165,17 @@ class Pattern { */ struct Placeholder { /** @brief Log pattern field types. */ - enum class Type : std::uint8_t { None, Category, Level, File, Line, Message }; + enum class Type : std::uint8_t { + None, + Category, + Level, + File, + Line, + Message, + Function, + Time, + Thread + }; /** @brief Field alignment options. */ enum class Align : std::uint8_t { None, Left, Right, Center }; @@ -196,6 +206,8 @@ class Pattern { [[fallthrough]]; case Placeholder::Type::File: [[fallthrough]]; + case Placeholder::Type::Function: + [[fallthrough]]; case Placeholder::Type::Message: return true; default: @@ -217,15 +229,21 @@ class Pattern { static constexpr std::array Level{'l', 'e', 'v', 'e', 'l', '\0'}; static constexpr std::array File{'f', 'i', 'l', 'e', '\0'}; static constexpr std::array Line{'l', 'i', 'n', 'e', '\0'}; + static constexpr std::array Function{'f', 'u', 'n', 'c', 't', 'i', 'o', 'n', '\0'}; + static constexpr std::array Time{'t', 'i', 'm', 'e', '\0'}; + static constexpr std::array Thread{'t', 'h', 'r', 'e', 'a', 'd', '\0'}; static constexpr std::array Message{'m', 'e', 's', 's', 'a', 'g', 'e', '\0'}; public: /** @brief List of placeholder names. */ - static constexpr std::array List{ + static constexpr std::array List{ {{Placeholder::Type::Category, Placeholders::Category.data()}, {Placeholder::Type::Level, Placeholders::Level.data()}, {Placeholder::Type::File, Placeholders::File.data()}, {Placeholder::Type::Line, Placeholders::Line.data()}, + {Placeholder::Type::Function, Placeholders::Function.data()}, + {Placeholder::Type::Time, Placeholders::Time.data()}, + {Placeholder::Type::Thread, Placeholders::Thread.data()}, {Placeholder::Type::Message, Placeholders::Message.data()}}}; }; @@ -314,10 +332,20 @@ class Pattern { format_string( result, std::get(item.value), record.location.filename); break; + case Placeholder::Type::Function: + format_string( + result, std::get(item.value), record.location.function); + break; case Placeholder::Type::Line: result.format_runtime( std::get(item.value), record.location.line); break; + case Placeholder::Type::Time: + result.format_runtime(std::get(item.value), record.time); + break; + case Placeholder::Type::Thread: + result.format_runtime(std::get(item.value), record.thread_id); + break; case Placeholder::Type::Message: std::visit( Util::Types::Overloaded{ diff --git a/include/log/record.h b/include/log/record.h index 6d0f93d..4823132 100644 --- a/include/log/record.h +++ b/include/log/record.h @@ -8,6 +8,7 @@ #include "util/unicode.h" #include +#include #include #include #include @@ -182,6 +183,8 @@ struct Record { Level level = {}; ///< Log level. Location location = {}; ///< Source code location. RecordStringView category = {}; ///< Log category. + std::chrono::system_clock::time_point time = {}; ///< Event time. + std::size_t thread_id = {}; ///< Thread ID. std::variant, RecordStringView> message = RecordStringView{}; ///< Log message. }; diff --git a/include/log/sink.h b/include/log/sink.h index ac0dc26..a0447d4 100644 --- a/include/log/sink.h +++ b/include/log/sink.h @@ -10,11 +10,13 @@ #include "pattern.h" #include "record.h" +#include #include #include #include #include #include +#include #include #include #include @@ -333,7 +335,9 @@ class SinkDriver final { RecordType record = {level, {location.file_name(), location.function_name(), location.line()}, - std::move(category)}; + std::move(category), + std::chrono::system_clock::now(), + std::hash{}(std::this_thread::get_id())}; // Flag to check that message has been evaluated bool evaluated = false; diff --git a/src/main.cpp b/src/main.cpp index 10828a0..8910a1e 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -21,7 +21,6 @@ #include #include #include -#include #include class null_out_buf : public std::basic_streambuf { @@ -233,7 +232,8 @@ auto main(int /*argc*/, char* /*argv*/[]) -> int auto log_root = std::make_shared>(L"main"); auto sink1 = log_root->add_sink( std::wcout, - L"!!!!! {category} [{level}] {file}|{line}: {message}", + L"!!!!! {category} [{level}] <{time:%Y-%m-%d %X}> {thread} " + L"{file}|{line}|{function}: {message}", std::make_pair(Log::Level::Trace, gen_random(5)), std::make_pair(Log::Level::Debug, gen_random(5)), std::make_pair(Log::Level::Warning, gen_random(5)),